找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1182|回复: 2
收起左侧

51单片机单系统电梯程序与Proteus仿真图设计

[复制链接]
ID:1084143 发表于 2023-6-16 08:47 | 显示全部楼层 |阅读模式
这是我一个星期完成的电梯设计,内含上下行电梯、电梯紧急停止、内部故障报警系统等内容。
内部包含电路设计图(含注释),电路源代码等,请大家多多指教。
仿真原理图如下(proteus仿真工程文件可到本帖附件中下载)
51hei.gif

单片机源程序如下:
  1. #include <REG51.H>
  2. #include <INTRINS.H>

  3. unsigned char ucMotorDrvPuls;
  4. unsigned char FORREV=1;
  5. unsigned char STOPCUR=0;
  6. unsigned char CURFLR=1;
  7. unsigned char count=0;

  8. #define UCTIMES 8
  9. #define OUTPUT P2
  10. #define COUNT 8

  11. sbit UP1=P3^4;
  12. sbit DOWN2=P3^3;
  13. sbit UP2=P3^2;
  14. sbit DOWN3=P3^1;
  15. sbit UP3=P3^0;
  16. sbit DOWN4=P1^7;
  17. sbit FLOOR1=P1^0;
  18. sbit FLOOR2=P1^1;
  19. sbit FLOOR3=P1^2;
  20. sbit FLOOR4=P1^3;
  21. sbit START=P1^4;
  22. sbit STOP=P1^5;
  23. sbit ALARM=P1^6;

  24. sbit alarmBit=P0^4;
  25. sbit upLight=P0^5;
  26. sbit downLight=P0^6;

  27. void time(unsigned int ucMs);
  28. void outPress();
  29. unsigned char inPress();  
  30. unsigned char elevator();  
  31. void storeUP(unsigned char);  
  32. void storeDOWN(unsigned char);  

  33. void time (unsigned int ucMs);

  34. void initLights(void);

  35. void setFloor(int floor);

  36. void setUpLight();

  37. void setDownLight();

  38. void setStopLight();

  39. void setAlarmLight();

  40. void setAlarmLight();

  41. void offAlarmLight();


  42. int alarmSwitch=1;

  43. unsigned char UP_req[5]={0,0,0,0,0};  
  44. unsigned char DOWN_req[5]={0,0,0,0,0};

  45. void position(void)
  46. {
  47.         OUTPUT=0x01|(P2&0xf0);time(200);
  48.         OUTPUT=0x02|(P2&0xf0);time(200);
  49.         OUTPUT=0x04|(P2&0xf0);time(200);
  50.         OUTPUT=0x08|(P2&0xf0);time(200);
  51.         ucMotorDrvPuls=0x11;
  52.         OUTPUT=0x01|(P2&0xf0);
  53. }



  54. void main(void)
  55. {
  56.         time(100);
  57.         initLights();
  58.   position();
  59.         ucMotorDrvPuls=0x11;
  60.         OUTPUT=0x00|(P2&0xf0);
  61.         setFloor(CURFLR);
  62.         setUpLight();
  63.         time(100);
  64.         
  65.         while(1)// 主循环
  66.         {
  67.                 outPress();//按下电梯外按钮
  68.                 while(STOPCUR==1)
  69.                 {
  70.                         outPress();
  71.                         inPress();
  72.                 }
  73.         
  74.                 if(inPress())  //按下电梯内楼层按钮
  75.     {
  76.      while(START)  //等待启动按键按下
  77.                 {
  78.                         outPress();
  79.                         inPress();
  80.                 }
  81.         }
  82.                
  83.           while(1) //电机运转循环
  84.                 {
  85.                         if(UP_req[1]==0&&UP_req[2]==0&&UP_req[3]==0&&
  86.                         DOWN_req[2]==0&&DOWN_req[3]==0&&DOWN_req[4]==0)
  87.                 {
  88.                         break;
  89.                 }
  90.                
  91.                 if(FORREV)  //上
  92.                 {
  93.                         setUpLight(); //上行灯亮
  94.                         
  95.                         if(STOPCUR==1){break;}  
  96.                         
  97.                         if(elevator())  //往上到达某一层
  98.                         {
  99.                           if(CURFLR==4) {setDownLight();break;}  //到达四层
  100.                         }
  101.                         OUTPUT=(ucMotorDrvPuls&0x0f)|(P2&0xf0);
  102.                         ucMotorDrvPuls=_crol_(ucMotorDrvPuls,1);
  103.                 }
  104.                 if(!FORREV)  //下
  105.                 {
  106.                         setDownLight();  //下行灯亮
  107.                         
  108.                         if(STOPCUR==1){break;}
  109.                         
  110.                         if(elevator())  //往下到达某一层
  111.                         {
  112.                                 if(CURFLR==1){setUpLight();break;}//到达一楼
  113.                         }
  114.                         OUTPUT=(ucMotorDrvPuls&0x0f)|(P2&0xf0);
  115.                         ucMotorDrvPuls=_cror_(ucMotorDrvPuls,1);
  116.                 }
  117.                
  118.                 outPress();  //按下电梯外按钮
  119.                 //if(inPress())  //按下电梯内楼层按钮
  120.                 //{
  121.                         //while(START)  //等待启动按键按下
  122.                         //{
  123.                         //        outPress();
  124.                                 inPress();  //电梯运行时,内部按钮按下,无需按启动按钮
  125.                         //}
  126.                 //}
  127.                
  128.                 time(380-UCTIMES*16);
  129.                
  130.             }  //end while-电机运转循环
  131.         
  132.           OUTPUT=0x00|(P2&0xf0);  //电机停止
  133.         
  134.     }//end while-主循环

  135.         }
  136.         
  137. //按下电梯外按钮
  138. void outPress()
  139. {
  140.         //FORREV=1;
  141.         if(!UP1)  //1楼上
  142.         {
  143.                 storeUP(1);
  144.                 if(CURFLR>1&&STOPCUR==1)
  145.                 {
  146.                         FORREV=0;  //向下运行
  147.                         STOPCUR=0;
  148.                 }
  149.                 if(CURFLR==1)
  150.                 {
  151.                         STOPCUR=1;//电梯停留在当前层
  152.                 }
  153.         }
  154.         if(!UP2) //2楼上
  155.         {
  156.                 storeUP(2);
  157.                 if(CURFLR>2&&STOPCUR==1)  //电梯在二楼以上
  158.                 {
  159.                  FORREV=0;
  160.                  STOPCUR=0;
  161.                 }
  162.                 if(CURFLR<2&&STOPCUR==1)  
  163.                 {
  164.                         FORREV=1;
  165.                         STOPCUR=0;
  166.                 }
  167.                 if(CURFLR==2)
  168.                 {
  169.                         STOPCUR=1;
  170.                 }
  171.         }
  172.         if(!UP3)  //3楼上
  173.         {
  174.                 storeUP(3);
  175.                 if(CURFLR>3&&STOPCUR==1)  //电梯在三楼以上
  176.                 {
  177.                  FORREV=0;
  178.                  STOPCUR=0;
  179.                 }
  180.                 if(CURFLR<3&&STOPCUR==1)
  181.                 {
  182.                         FORREV=1;
  183.                         STOPCUR=0;
  184.                 }
  185.                 if(CURFLR==3)
  186.                 {
  187.            STOPCUR=1;
  188.         }
  189. }
  190. if(!DOWN2) //2楼下
  191. {
  192.         storeDOWN(2);
  193.         if(CURFLR>2&&STOPCUR==1)//电梯在二楼以上
  194.         {
  195.                         FORREV=0;
  196.                         STOPCUR=0;
  197.         }
  198. if(CURFLR<2&&STOPCUR==1)
  199. {        
  200.         FORREV=1;
  201.         STOPCUR=0;
  202. }
  203. if(CURFLR==2)
  204. {
  205.         STOPCUR=1;
  206. }
  207. }
  208. if(!DOWN3)//3楼下
  209. {
  210.         storeDOWN(3);
  211.         if(CURFLR>3&&STOPCUR==1)//电梯在三楼以上
  212.         {
  213.     FORREV=0;
  214.           STOPCUR=0;
  215.         }
  216.         if(CURFLR<3&&STOPCUR==1)
  217.         {
  218.     FORREV=1;
  219.           STOPCUR=0;
  220.         }
  221.                 if(CURFLR==3)
  222.                 {
  223.                         STOPCUR=1;
  224.                 }
  225.         }
  226.   if(!DOWN4)//4楼下
  227.         {
  228.         storeDOWN(4);
  229.         if(CURFLR<4&&STOPCUR==1)
  230.    {
  231.     FORREV=1;
  232.           STOPCUR=0;
  233.           }
  234.         if(CURFLR==4)
  235.         {
  236.           STOPCUR=1;
  237.         }
  238.   }
  239. }
  240.         
  241. //按下电梯内楼层按钮
  242. unsigned char inPress()
  243. {

  244.         int i;
  245.         int flag=0;
  246.         
  247.         if(!FLOOR1)
  248.         {
  249.                 if(1<CURFLR)
  250.                 {
  251.                         STOPCUR=0;
  252.                         UP_req[1]=1;
  253.                 }
  254.                 if(1==CURFLR)
  255.                 {
  256.                         STOPCUR=1;
  257.                 }
  258.                 return 1;
  259.         }
  260.    if(!FLOOR2)
  261.         {
  262.                 if(2>CURFLR)//请求层大于当前层
  263.                 {
  264.                         UP_req[2]=1;
  265.                         STOPCUR=0;
  266.                 }
  267.                 if(2<CURFLR)
  268.                 {
  269.                         DOWN_req[2]=1;
  270.                         STOPCUR=0;
  271.                 }
  272.                  if(2==CURFLR)
  273.                 {
  274.                         STOPCUR=1;
  275.                 }
  276.                 return 1;
  277.                
  278.         }
  279.    if(!FLOOR3)
  280.         {
  281.                 if(3>CURFLR)//请求层大于当前层
  282.                 {
  283.                         UP_req[3]=1;
  284.                         STOPCUR=0;
  285.                 }
  286.                 if(3<CURFLR)
  287.                 {
  288.                         DOWN_req[3]=1;
  289.                         STOPCUR=0;
  290.                 }
  291.                  if(3==CURFLR)
  292.                 {
  293.                         STOPCUR=1;
  294.                 }
  295.                 return 1;
  296.         }
  297.         
  298.    if(!FLOOR4)
  299.         {
  300.                 if(4>CURFLR)
  301.                 {
  302.                         DOWN_req[4]=1;
  303.                         STOPCUR=0;
  304.                 }
  305.                 if(4==CURFLR)
  306.                 {
  307.                         STOPCUR=1;
  308.                 }
  309.                 return 1;
  310.         }
  311.                 if(!START)
  312.                 {
  313.                         STOPCUR=0;
  314.                         return 1;
  315.                 }
  316.   if(!STOP)//紧急停止
  317.         {
  318.     while(START)//不响应其他按钮
  319.      {
  320.        //亮灯
  321.        setStopLight();
  322.                  }
  323.       return 1;
  324.            }        
  325.       if(!ALARM)
  326.                 {
  327.      //while(START)
  328.      //{
  329.                         //亮灯
  330.                         setAlarmLight();
  331.                         //time(800);
  332.                         //灯灭
  333.                         //offAlarmLight();
  334.                         //}
  335.                         return 1;
  336.                 }
  337.                
  338.                 if(FORREV==1)
  339.                 {
  340.                         //请求上行而进去电梯内选择的是下层
  341.                         for(i=CURFLR+1;i<4;i++)
  342.                         {
  343.                                 if(UP_req[i]==1||DOWN_req[i]==1){flag=1;}
  344.                         }
  345.                         if(flag==0)//上层没有请求
  346.                         {
  347.                         FORREV=0;
  348.                         
  349.                 }
  350.         }
  351.   if(FORREV==0)
  352.         {
  353.                 //请求下行而进去电梯内选择的是上层
  354.       for(i=CURFLR-1;i>=1;i--)
  355.                         {
  356.                                 if(UP_req[i]==1||DOWN_req[i]==1){flag=1;}
  357.                         }
  358.                         if(flag==0)//
  359.                 {
  360.                         FORREV=1;

  361.                         }
  362.                 }        
  363.     return 0;
  364.                 }


  365. unsigned char elevator()
  366. {
  367. count++;
  368. if (count==COUNT)
  369. {

  370.    if(FORREV==1)
  371.    {
  372.    CURFLR++;
  373.    setUpLight();//上行灯亮



  374.     if(CURFLR==2)//到达二楼        
  375.     {
  376.                         count=0;
  377.                         setFloor(2);//显示数字
  378.                         if(UP_req[2]==1)//二楼有上行请求,优先处理
  379.                         {
  380.                                 setUpLight();
  381.                                 UP_req[2]=0;
  382.                                 OUTPUT=0x00|(P2&0xf0);//电机停止
  383.                                 STOPCUR=1;
  384.                                 return 1;
  385.                         }
  386.                         if(DOWN_req[2]==1&&UP_req[3]==0&&DOWN_req[3]==0
  387.                         &&DOWN_req[4]==0)//二楼有下请求,上面两层没有请求,不再往上
  388.                         {
  389.                                 setDownLight();
  390.                                 DOWN_req[2]=0;
  391.                                 STOPCUR=1;
  392.                                 OUTPUT=0x00|(P2&0xf0);//电机停止
  393.                                 FORREV=0;
  394.                                 return 1;
  395.                         }
  396.                 }
  397.       if(CURFLR==3)//到达三楼        
  398.     {
  399.                         setFloor(3);//显示数字
  400.                         count=0;
  401.                         if(UP_req[3]==1)//三楼有上行请求,优先处理
  402.                         {
  403.                                 setUpLight();
  404.                                 UP_req[3]=0;
  405.                                 OUTPUT=0x00|(P2&0xf0);//电机停止
  406.                                 STOPCUR=1;
  407.                                 return 1;
  408.                         }
  409.                         if(DOWN_req[3]==1&&UP_req[4]==0)//三楼有下请求,四楼没有请求,不再往上
  410.                         {
  411.                                 setDownLight();
  412.                                 FORREV=0;
  413.                                 DOWN_req[3]=0;
  414.                                 STOPCUR=1;
  415.                                 OUTPUT=0x00|(P2&0xf0);//电机停止
  416.                                 return 1;
  417.                         }
  418.                 }
  419.      if(CURFLR==4)//到达四楼        
  420.     {
  421.                         setFloor(4);//显示数字
  422.                         setDownLight();
  423.                         count=0;
  424.                         if(DOWN_req[4]==1)//四楼有上行请求,四楼的请求只用向下的情况
  425.                         {
  426.                                 DOWN_req[4]=0;
  427.                                 FORREV=0;
  428.                                 OUTPUT=0x00|(P2&0xf0);//电机停止
  429.                                 STOPCUR=1;
  430.                         }
  431.                 }
  432.         }
  433.                 else//判断下行是否到达请求层,下行请求优先处理
  434.                 {
  435.                         CURFLR--;
  436.                         setDownLight();//下行灯亮
  437.                         
  438.                         
  439.                         
  440.                         if(CURFLR==1)//到达一楼
  441.                         {
  442.                                 setFloor(1);//显示数字
  443.                                 count=0;
  444.                                 if(UP_req[1]==1)//一楼没有请求,一楼的请求只有向上的情况
  445.                                 {
  446.                                         setUpLight();
  447.                                         UP_req[1]=0;
  448.                                         FORREV=1;
  449.                                         OUTPUT=0x00|(P2&0xf0);//电机停止
  450.                                                 STOPCUR=1;
  451.                         }
  452.                 }
  453.        if(CURFLR==2)//到达二楼
  454.                         {
  455.                                 setFloor(2);//显示数字
  456.                                 count=0;
  457.                                 if(DOWN_req[2]==1)//二楼有下行请求,优先处理
  458.                                 {
  459.                                         setDownLight();
  460.                                         DOWN_req[2]=0;
  461.                                         OUTPUT=0x00|(P2&0xf0);//电机停止
  462.                                         STOPCUR=1;
  463.                                         return 1;
  464.                         }
  465.                   if(UP_req[2]==1&&UP_req[1]==0)//一楼无请求,不再往下
  466.                         {
  467.                         setUpLight();
  468.                         FORREV=1;
  469.                         UP_req[2]=0;
  470.                         STOPCUR=1;
  471.       OUTPUT=0x00|(P2&0xf0);//电机停止
  472.                         }
  473.                 }
  474.                          if(CURFLR==3)//到达三楼
  475.                         {
  476.                                 setFloor(3);//显示数字
  477.                                 count=0;
  478.                                 if(DOWN_req[3]==1)//三楼有下行请求,优先处理
  479.                                 {
  480.                                         setDownLight();
  481.                                         DOWN_req[3]=0;
  482.                                         OUTPUT=0x00|(P2&0xf0);//电机停止
  483.                                         STOPCUR=1;
  484.                                         return 1;
  485.                         }
  486.                   if(UP_req[1]==0&&DOWN_req[2]==0&&UP_req[2]==0&&UP_req[3]==1)
  487.                         {
  488.                         setUpLight();
  489.                         FORREV=1;
  490.                         UP_req[3]=0;
  491.                         STOPCUR=1;
  492.       OUTPUT=0x00|(P2&0xf0);//电机停止
  493.                         }
  494.                 }
  495.         }//end if-FORREV
  496.                
  497.         return 1;
  498. }
  499. else
  500. {
  501.          return 0;
  502. }//end if-count
  503. }


  504. void storeUP(unsigned char x)
  505. {
  506.         UP_req[x]=1;
  507. }
  508. void storeDOWN(unsigned char x)
  509. {
  510.         DOWN_req[x]=1;
  511. }

  512. void initLights()
  513. {
  514.         P0=0x11;
  515. }

  516. //设置楼层显示
  517. void setFloor(int floor)
  518. {
  519.         switch(floor)
  520.         {
  521.           case 1:
  522.          {
  523.                  P0&=0xf0;//清零
  524.                  P0|=0x01;break;
  525.          }
  526.                 case 2:
  527.          {
  528.                  P0&=0xf0;//清零
  529.                  P0|=0x02;break;
  530.          }
  531.           case 3:
  532.          {
  533.                  P0&=0xf0;//清零
  534.                  P0|=0x03;break;
  535.          }
  536.           case 4:
  537.          {
  538.                  P0&=0xf0;//清零
  539.                  P0|=0x04;break;
  540.          }
  541.                 default:
  542.          {
  543.                  P0=0x06;break;
  544.          }
  545. }
  546. }

  547. //设置电梯向上运行灯
  548. void setUpLight()
  549. {
  550.         upLight=1;
  551.         downLight=0;
  552. }

  553. //设置电梯向下运行灯
  554. void setDownLight()
  555. {
  556.         upLight=0;
  557.         downLight=1;
  558. }
  559.         
  560. //设置电梯停止运行灯
  561. void setStopLight()
  562. {
  563.         upLight=0;
  564. ……………………

  565. …………限于本文篇幅 余下代码请从51黑下载附件…………
复制代码

Keil代码与Proteus8.13仿真下载:
仿真程序.7z (101.02 KB, 下载次数: 40)

评分

参与人数 1黑币 +50 收起 理由
admin + 50 共享资料的黑币奖励!

查看全部评分

回复

使用道具 举报

ID:95059 发表于 2023-7-13 19:20 | 显示全部楼层
到了怎么下车? 开门?
回复

使用道具 举报

ID:95059 发表于 2023-7-13 19:24 | 显示全部楼层
下楼梯下不来,是不是还没写完功能啊?不太会用
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表