色婷婷AⅤ一区二区三区|亚洲精品第一国产综合亚AV|久久精品官方网视频|日本28视频香蕉

          新聞中心

          EEPW首頁(yè) > 嵌入式系統(tǒng) > 設(shè)計(jì)應(yīng)用 > 第25節(jié):用LED燈和按鍵來(lái)模擬工業(yè)自動(dòng)化設(shè)備的運(yùn)動(dòng)控制

          第25節(jié):用LED燈和按鍵來(lái)模擬工業(yè)自動(dòng)化設(shè)備的運(yùn)動(dòng)控制

          作者: 時(shí)間:2016-11-22 來(lái)源:網(wǎng)絡(luò) 收藏
          開場(chǎng)白:
          前面三節(jié)講了獨(dú)立按鍵控制跑馬燈的各種狀態(tài),這一節(jié)我們要做一個(gè)機(jī)械手控制程序,這個(gè)機(jī)械手可以左右移動(dòng),最左邊有一個(gè)開關(guān)感應(yīng)器,最右邊也有一個(gè)開關(guān)感應(yīng)器。它也可以上下移動(dòng),最下面有一個(gè)開關(guān)感應(yīng)器。左右移動(dòng)是通過(guò)一個(gè)氣缸控制,上下移動(dòng)也是通過(guò)一個(gè)氣缸控制。而單片機(jī)控制氣缸,本質(zhì)上是通過(guò)三極管把信號(hào)放大,然后控制氣缸上的電磁閥。這個(gè)系統(tǒng)機(jī)械手驅(qū)動(dòng)部分的輸出和輸入信號(hào)如下:
          2個(gè)輸出IO口,分別控制2個(gè)氣缸。對(duì)于左右移動(dòng)的氣缸,當(dāng)IO口為0時(shí)往左邊跑,當(dāng)IO口為1時(shí)往右邊跑。對(duì)于上下移動(dòng)的氣缸,當(dāng)IO口為0時(shí)往上邊跑,當(dāng)IO口為1時(shí)往下邊跑。
          3個(gè)輸入IO口,分別檢測(cè)3個(gè)開關(guān)感應(yīng)器。感應(yīng)器沒(méi)有被觸發(fā)時(shí),IO口檢測(cè)為高電平1。被觸發(fā)時(shí),IO口檢測(cè)為低電平0。
          這一節(jié)繼續(xù)要教會(huì)大家兩個(gè)知識(shí)點(diǎn):
          第一點(diǎn):如何用軟件進(jìn)行開關(guān)感應(yīng)器的抗干擾處理。
          第二點(diǎn):如何用Switch語(yǔ)句搭建工業(yè)自動(dòng)控制的程序框架。還是那句話,我們只要以Switch語(yǔ)句為支點(diǎn),再?gòu)?fù)雜再繁瑣的程序都可以輕松地編寫出來(lái)。

          具體內(nèi)容,請(qǐng)看源代碼講解。

          (1)硬件平臺(tái):基于朱兆祺51單片機(jī)學(xué)習(xí)板。用矩陣鍵盤中的S1鍵作為啟動(dòng)獨(dú)立按鍵,用S5按鍵模擬左邊的開關(guān)感應(yīng)器,用S9按鍵模擬右邊的開關(guān)感應(yīng)器,用S13按鍵模擬下邊的開關(guān)感應(yīng)器。記得把輸出線P0.4一直輸出低電平,模擬獨(dú)立按鍵的觸發(fā)地GND。

          (2)實(shí)現(xiàn)功能:
          開機(jī)默認(rèn)機(jī)械手在左上方的原點(diǎn)位置。按下啟動(dòng)按鍵后,機(jī)械手從左邊開始往右邊移動(dòng),當(dāng)機(jī)械手移動(dòng)到最右邊時(shí),機(jī)械手馬上開始往下移動(dòng),最后機(jī)械手移動(dòng)到最右下角的位置時(shí),延時(shí)1秒,然后原路返回,一直返回到左上角的原點(diǎn)位置。注意:?jiǎn)?dòng)按鍵必須等機(jī)械手處于左上角原點(diǎn)位置時(shí),啟動(dòng)按鍵的觸發(fā)才有效。

          (3)源代碼講解如下:
          #include "REG52.H"

          #define const_voice_short40 //蜂鳴器短叫的持續(xù)時(shí)間

          #define const_key_time120 //按鍵去抖動(dòng)延時(shí)的時(shí)間


          #define const_sensor20 //開關(guān)感應(yīng)器去抖動(dòng)延時(shí)的時(shí)間

          #define const_1s500//1秒鐘大概的定時(shí)中斷次數(shù)

          void initial_myself();
          void initial_peripheral();
          void delay_short(unsigned int uiDelayShort);
          void delay_long(unsigned int uiDelaylong);

          void left_to_right();//從左邊移動(dòng)到右邊
          void right_to_left(); //從右邊返回到左邊
          void up_to_dowm(); //從上邊移動(dòng)到下邊
          void down_to_up(); //從下邊返回到上邊


          void run(); //設(shè)備自動(dòng)控制程序
          void hc595_drive(unsigned char ucLedStatusTemp16_09,unsigned char ucLedStatusTemp08_01);
          void led_update();//LED更新函數(shù)
          void T0_time();//定時(shí)中斷函數(shù)

          void key_service(); //按鍵服務(wù)的應(yīng)用程序
          void key_scan(); //按鍵掃描函數(shù) 放在定時(shí)中斷里
          void sensor_scan(); //開關(guān)感應(yīng)器軟件抗干擾處理函數(shù),放在定時(shí)中斷里。

          sbit hc595_sh_dr=P2^3;
          sbit hc595_st_dr=P2^4;
          sbit hc595_ds_dr=P2^5;

          sbit beep_dr=P2^7; //蜂鳴器的驅(qū)動(dòng)IO口

          sbit key_sr1=P0^0; //對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S1鍵

          sbit left_sr=P0^1; //左邊的開關(guān)感應(yīng)器 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S5鍵
          sbit right_sr=P0^2; //右邊的開關(guān)感應(yīng)器 有對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S9鍵
          sbit down_sr=P0^3; //下邊的開關(guān)感應(yīng)器 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S13鍵

          sbit key_gnd_dr=P0^4; //模擬獨(dú)立按鍵的地GND,因此必須一直輸出低電平

          unsigned char ucKeySec=0; //被觸發(fā)的按鍵編號(hào)

          unsigned intuiKeyTimeCnt1=0; //按鍵去抖動(dòng)延時(shí)計(jì)數(shù)器
          unsigned char ucKeyLock1=0; //按鍵觸發(fā)后自鎖的變量標(biāo)志


          unsigned char ucLeftSr=0;//左邊感應(yīng)器經(jīng)過(guò)軟件抗干擾處理后的狀態(tài)標(biāo)志
          unsigned char ucRightSr=0;//右邊感應(yīng)器經(jīng)過(guò)軟件抗干擾處理后的狀態(tài)標(biāo)志
          unsigned char ucDownSr=0;//下邊感應(yīng)器經(jīng)過(guò)軟件抗干擾處理后的狀態(tài)標(biāo)志

          unsigned intuiLeftCnt1=0;//左邊感應(yīng)器軟件抗干擾所需的計(jì)數(shù)器變量
          unsigned intuiLeftCnt2=0;

          unsigned intuiRightCnt1=0;//右邊感應(yīng)器軟件抗干擾所需的計(jì)數(shù)器變量
          unsigned intuiRightCnt2=0;

          unsigned intuiDownCnt1=0; //下邊軟件抗干擾所需的計(jì)數(shù)器變量
          unsigned intuiDownCnt2=0;

          unsigned intuiVoiceCnt=0;//蜂鳴器鳴叫的持續(xù)時(shí)間計(jì)數(shù)器

          unsigned char ucLed_dr1=0; //代表16個(gè)燈的亮滅狀態(tài),0代表滅,1代表亮
          unsigned char ucLed_dr2=0;
          unsigned char ucLed_dr3=0;
          unsigned char ucLed_dr4=0;
          unsigned char ucLed_dr5=0;
          unsigned char ucLed_dr6=0;
          unsigned char ucLed_dr7=0;
          unsigned char ucLed_dr8=0;
          unsigned char ucLed_dr9=0;
          unsigned char ucLed_dr10=0;
          unsigned char ucLed_dr11=0;
          unsigned char ucLed_dr12=0;
          unsigned char ucLed_dr13=0;
          unsigned char ucLed_dr14=0;
          unsigned char ucLed_dr15=0;
          unsigned char ucLed_dr16=0;

          unsigned char ucLed_update=1;//刷新變量。每次更改LED燈的狀態(tài)都要更新一次。



          unsigned char ucLedStatus16_09=0; //代表底層74HC595輸出狀態(tài)的中間變量
          unsigned char ucLedStatus08_01=0; //代表底層74HC595輸出狀態(tài)的中間變量



          unsigned intuiRunTimeCnt=0;//運(yùn)動(dòng)中的時(shí)間延時(shí)計(jì)數(shù)器變量
          unsigned char ucRunStep=0;//運(yùn)動(dòng)控制的步驟變量

          void main()
          {
          initial_myself();
          delay_long(100);
          initial_peripheral();
          while(1)
          {
          run(); //設(shè)備自動(dòng)控制程序
          led_update();//LED更新函數(shù)
          key_service(); //按鍵服務(wù)的應(yīng)用程序
          }

          }


          /* 注釋一:
          * 開關(guān)感應(yīng)器的抗干擾處理,本質(zhì)上類似按鍵的去抖動(dòng)處理。唯一的區(qū)別是:
          * 按鍵去抖動(dòng)關(guān)注的是IO口的一種狀態(tài),而開關(guān)感應(yīng)器關(guān)注的是IO口的兩種狀態(tài)。
          * 當(dāng)開關(guān)感應(yīng)器從原來(lái)的1狀態(tài)切換到0狀態(tài)之前,要進(jìn)行軟件濾波處理過(guò)程,一旦成功地
          * 切換到0狀態(tài)了,再想從0狀態(tài)切換到1狀態(tài)的時(shí)候,又要經(jīng)過(guò)軟件濾波處理過(guò)程,符合
          * 條件后才能切換到1的狀態(tài)。通俗的話來(lái)說(shuō),按鍵的去抖動(dòng)從1變成0難,從0變成1容易。
          * 開關(guān)感應(yīng)器從1變成0難,從0變成1也難。這里所說(shuō)的"難"是指要經(jīng)過(guò)去抖處理。
          */

          void sensor_scan() //開關(guān)感應(yīng)器軟件抗干擾處理函數(shù),放在定時(shí)中斷里。
          {
          if(left_sr==1)//左邊感應(yīng)器是高電平,說(shuō)明有可能沒(méi)有被接觸 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S5鍵
          {
          uiLeftCnt1=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句?。?!類似按鍵去抖動(dòng)程序的及時(shí)清零
          uiLeftCnt2++; //類似獨(dú)立按鍵去抖動(dòng)的軟件抗干擾處理
          if(uiLeftCnt2>const_sensor)
          {
          uiLeftCnt2=0;
          ucLeftSr=1; //說(shuō)明感應(yīng)器確實(shí)沒(méi)有被接觸
          }
          }
          else //左邊感應(yīng)器是低電平,說(shuō)明有可能被接觸到了
          {
          uiLeftCnt2=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句?。?!類似按鍵去抖動(dòng)程序的及時(shí)清零
          uiLeftCnt1++;
          if(uiLeftCnt1>const_sensor)
          {
          uiLeftCnt1=0;
          ucLeftSr=0; //說(shuō)明感應(yīng)器確實(shí)被接觸到了
          }
          }

          if(right_sr==1)//右邊感應(yīng)器是高電平,說(shuō)明有可能沒(méi)有被接觸 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S9鍵
          {
          uiRightCnt1=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句?。?!類似按鍵去抖動(dòng)程序的及時(shí)清零
          uiRightCnt2++; //類似獨(dú)立按鍵去抖動(dòng)的軟件抗干擾處理
          if(uiRightCnt2>const_sensor)
          {
          uiRightCnt2=0;
          ucRightSr=1; //說(shuō)明感應(yīng)器確實(shí)沒(méi)有被接觸
          }
          }
          else //右邊感應(yīng)器是低電平,說(shuō)明有可能被接觸到了
          {
          uiRightCnt2=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句?。。☆愃瓢存I去抖動(dòng)程序的及時(shí)清零
          uiRightCnt1++;
          if(uiRightCnt1>const_sensor)
          {
          uiRightCnt1=0;
          ucRightSr=0; //說(shuō)明感應(yīng)器確實(shí)被接觸到了
          }
          }

          if(down_sr==1)//下邊感應(yīng)器是高電平,說(shuō)明有可能沒(méi)有被接觸 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S13鍵
          {
          uiDownCnt1=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句?。?!類似按鍵去抖動(dòng)程序的及時(shí)清零
          uiDownCnt2++; //類似獨(dú)立按鍵去抖動(dòng)的軟件抗干擾處理
          if(uiDownCnt2>const_sensor)
          {
          uiDownCnt2=0;
          ucDownSr=1; //說(shuō)明感應(yīng)器確實(shí)沒(méi)有被接觸
          }
          }
          else //下邊感應(yīng)器是低電平,說(shuō)明有可能被接觸到了
          {
          uiDownCnt2=0; //在軟件濾波中,非常關(guān)鍵的語(yǔ)句!??!類似按鍵去抖動(dòng)程序的及時(shí)清零
          uiDownCnt1++;
          if(uiDownCnt1>const_sensor)
          {
          uiDownCnt1=0;
          ucDownSr=0; //說(shuō)明感應(yīng)器確實(shí)被接觸到了
          }
          }
          }


          void key_scan()//按鍵掃描函數(shù) 放在定時(shí)中斷里
          {

          if(key_sr1==1)//IO是高電平,說(shuō)明按鍵沒(méi)有被按下,這時(shí)要及時(shí)清零一些標(biāo)志位
          {
          ucKeyLock1=0; //按鍵自鎖標(biāo)志清零
          uiKeyTimeCnt1=0;//按鍵去抖動(dòng)延時(shí)計(jì)數(shù)器清零,此行非常巧妙,是我實(shí)戰(zhàn)中摸索出來(lái)的。
          }
          else if(ucKeyLock1==0)//有按鍵按下,且是第一次被按下
          {
          uiKeyTimeCnt1++; //累加定時(shí)中斷次數(shù)
          if(uiKeyTimeCnt1>const_key_time1)
          {
          uiKeyTimeCnt1=0;
          ucKeyLock1=1;//自鎖按鍵置位,避免一直觸發(fā)
          ucKeySec=1; //觸發(fā)1號(hào)鍵
          }
          }



          }


          void key_service() //按鍵服務(wù)的應(yīng)用程序
          {
          switch(ucKeySec) //按鍵服務(wù)狀態(tài)切換
          {
          case 1:// 啟動(dòng)按鍵 對(duì)應(yīng)朱兆祺學(xué)習(xí)板的S1鍵
          if(ucLeftSr==0)//處于左上角原點(diǎn)位置
          {
          ucRunStep=1; //啟動(dòng)
          uiVoiceCnt=const_voice_short; //按鍵聲音觸發(fā),滴一聲就停。
          }

          ucKeySec=0;//響應(yīng)按鍵服務(wù)處理程序后,按鍵編號(hào)清零,避免一致觸發(fā)
          break;

          }
          }



          void led_update()//LED更新函數(shù)
          {

          if(ucLed_update==1)
          {
          ucLed_update=0; //及時(shí)清零,讓它產(chǎn)生只更新一次的效果,避免一直更新。

          if(ucLed_dr1==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x01;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xfe;
          }

          if(ucLed_dr2==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x02;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xfd;
          }

          if(ucLed_dr3==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x04;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xfb;
          }

          if(ucLed_dr4==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x08;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xf7;
          }


          if(ucLed_dr5==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x10;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xef;
          }


          if(ucLed_dr6==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x20;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xdf;
          }


          if(ucLed_dr7==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x40;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0xbf;
          }


          if(ucLed_dr8==1)
          {
          ucLedStatus08_01=ucLedStatus08_01|0x80;
          }
          else
          {
          ucLedStatus08_01=ucLedStatus08_01&0x7f;
          }

          if(ucLed_dr9==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x01;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xfe;
          }

          if(ucLed_dr10==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x02;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xfd;
          }

          if(ucLed_dr11==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x04;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xfb;
          }

          if(ucLed_dr12==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x08;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xf7;
          }


          if(ucLed_dr13==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x10;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xef;
          }


          if(ucLed_dr14==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x20;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xdf;
          }


          if(ucLed_dr15==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x40;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0xbf;
          }


          if(ucLed_dr16==1)
          {
          ucLedStatus16_09=ucLedStatus16_09|0x80;
          }
          else
          {
          ucLedStatus16_09=ucLedStatus16_09&0x7f;
          }

          hc595_drive(ucLedStatus16_09,ucLedStatus08_01);//74HC595底層驅(qū)動(dòng)函數(shù)

          }
          }

          void hc595_drive(unsigned char ucLedStatusTemp16_09,unsigned char ucLedStatusTemp08_01)
          {
          unsigned char i;
          unsigned char ucTempData;
          hc595_sh_dr=0;
          hc595_st_dr=0;

          ucTempData=ucLedStatusTemp16_09;//先送高8位
          for(i=0;i<8;i++)
          {
          if(ucTempData>=0x80)hc595_ds_dr=1;
          else hc595_ds_dr=0;

          hc595_sh_dr=0; //SH引腳的上升沿把數(shù)據(jù)送入寄存器
          delay_short(15);
          hc595_sh_dr=1;
          delay_short(15);

          ucTempData=ucTempData<<1;
          }

          ucTempData=ucLedStatusTemp08_01;//再先送低8位
          for(i=0;i<8;i++)
          {
          if(ucTempData>=0x80)hc595_ds_dr=1;
          else hc595_ds_dr=0;

          hc595_sh_dr=0; //SH引腳的上升沿把數(shù)據(jù)送入寄存器
          delay_short(15);
          hc595_sh_dr=1;
          delay_short(15);

          ucTempData=ucTempData<<1;
          }

          hc595_st_dr=0;//ST引腳把兩個(gè)寄存器的數(shù)據(jù)更新輸出到74HC595的輸出引腳上并且鎖存起來(lái)
          delay_short(15);
          hc595_st_dr=1;
          delay_short(15);

          hc595_sh_dr=0; //拉低,抗干擾就增強(qiáng)
          hc595_st_dr=0;
          hc595_ds_dr=0;

          }


          void left_to_right()//從左邊移動(dòng)到右邊
          {
          ucLed_dr1=1; // 1代表左右氣缸從左邊移動(dòng)到右邊

          ucLed_update=1;//刷新變量。每次更改LED燈的狀態(tài)都要更新一次。
          }
          void right_to_left() //從右邊返回到左邊
          {
          ucLed_dr1=0; // 0代表左右氣缸從右邊返回到左邊

          ucLed_update=1;//刷新變量。每次更改LED燈的狀態(tài)都要更新一次。
          }
          void up_to_down() //從上邊移動(dòng)到下邊
          {
          ucLed_dr2=1; // 1代表上下氣缸從上邊移動(dòng)到下邊

          ucLed_update=1;//刷新變量。每次更改LED燈的狀態(tài)都要更新一次。
          }
          void down_to_up() //從下邊返回到上邊
          {
          ucLed_dr2=0; // 0代表上下氣缸從下邊返回到上邊

          ucLed_update=1;//刷新變量。每次更改LED燈的狀態(tài)都要更新一次。
          }


          void run() //設(shè)備自動(dòng)控制程序
          {

          switch(ucRunStep)
          {
          case 0: //機(jī)械手處于左上角原點(diǎn)的位置,待命狀態(tài)。此時(shí)觸發(fā)啟動(dòng)按鍵ucRunStep=1,就觸發(fā)后續(xù)一些列的連續(xù)動(dòng)作。

          break;

          case 1: //機(jī)械手從左邊往右邊移動(dòng)
          left_to_right();
          ucRunStep=2;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          break;

          case 2: //等待機(jī)械手移動(dòng)到最右邊,直到觸發(fā)了最右邊的開關(guān)感應(yīng)器。
          if(ucRightSr==0)//右邊感應(yīng)器被觸發(fā)
          {
          ucRunStep=3;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          }
          break;

          case 3: //機(jī)械手從右上邊往右下邊移動(dòng),從上往下。
          up_to_down();
          ucRunStep=4;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          break;

          case 4: //等待機(jī)械手從右上邊移動(dòng)到右下邊,直到觸發(fā)了右下邊的開關(guān)感應(yīng)器。
          if(ucDownSr==0)//右下邊感應(yīng)器被觸發(fā)
          {
          uiRunTimeCnt=0;//時(shí)間計(jì)數(shù)器清零,為接下來(lái)延時(shí)1秒鐘做準(zhǔn)備
          ucRunStep=5;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          }
          break;

          case 5: //機(jī)械手在右下邊延時(shí)1秒
          if(uiRunTimeCnt>const_1s)//延時(shí)1秒
          {
          ucRunStep=6;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          }
          break;
          case 6: //原路返回,機(jī)械手從右下邊往右上邊移動(dòng)。
          down_to_up();
          ucRunStep=7;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          break;

          case 7: //原路返回,等待機(jī)械手移動(dòng)到最右邊的感應(yīng)開關(guān)
          if(ucRightSr==0)
          {
          ucRunStep=8;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          }
          break;

          case 8: //原路返回,等待機(jī)械手從右邊往左邊移動(dòng)
          right_to_left();
          ucRunStep=9;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量

          break;

          case 9: //原路返回,等待機(jī)械手移動(dòng)到最左邊的感應(yīng)開關(guān),表示返回到了原點(diǎn)
          if(ucLeftSr==0) //返回到左上角的原點(diǎn)位置
          {
          ucRunStep=0;//這就是鴻哥傳說(shuō)中的怎樣靈活控制步驟變量
          }
          break;
          }
          }


          void T0_time() interrupt 1
          {
          TF0=0;//清除中斷標(biāo)志
          TR0=0; //關(guān)中斷


          sensor_scan(); //開關(guān)感應(yīng)器軟件抗干擾處理函數(shù)
          key_scan(); //按鍵掃描函數(shù)

          if(uiRunTimeCnt<0xffff) //不要超過(guò)最大int類型范圍
          {
          uiRunTimeCnt++; //延時(shí)計(jì)數(shù)器
          }
          if(uiVoiceCnt!=0)
          {
          uiVoiceCnt--; //每次進(jìn)入定時(shí)中斷都自減1,直到等于零為止。才停止鳴叫
          beep_dr=0;//蜂鳴器是PNP三極管控制,低電平就開始鳴叫。
          }
          else
          {
          ; //此處多加一個(gè)空指令,想維持跟if括號(hào)語(yǔ)句的數(shù)量對(duì)稱,都是兩條指令。不加也可以。
          beep_dr=1;//蜂鳴器是PNP三極管控制,高電平就停止鳴叫。
          }

          TH0=0xf8; //重裝初始值(65535-2000)=63535=0xf82f
          TL0=0x2f;
          TR0=1;//開中斷
          }

          void delay_short(unsigned int uiDelayShort)
          {
          unsigned int i;
          for(i=0;i {
          ; //一個(gè)分號(hào)相當(dāng)于執(zhí)行一條空語(yǔ)句
          }
          }

          void delay_long(unsigned int uiDelayLong)
          {
          unsigned int i;
          unsigned int j;
          for(i=0;i {
          for(j=0;j<500;j++)//內(nèi)嵌循環(huán)的空指令數(shù)量
          {
          ; //一個(gè)分號(hào)相當(dāng)于執(zhí)行一條空語(yǔ)句
          }
          }
          }


          void initial_myself()//第一區(qū) 初始化單片機(jī)
          {
          /* 注釋二:
          * 矩陣鍵盤也可以做獨(dú)立按鍵,前提是把某一根公共輸出線輸出低電平,
          * 模擬獨(dú)立按鍵的觸發(fā)地,本程序中,把key_gnd_dr輸出低電平。
          * 朱兆祺51學(xué)習(xí)板的S1就是本程序中用到的一個(gè)獨(dú)立按鍵。
          */
          key_gnd_dr=0; //模擬獨(dú)立按鍵的地GND,因此必須一直輸出低電平

          beep_dr=1; //用PNP三極管控制蜂鳴器,輸出高電平時(shí)不叫。

          TMOD=0x01;//設(shè)置定時(shí)器0為工作方式1


          TH0=0xf8; //重裝初始值(65535-2000)=63535=0xf82f
          TL0=0x2f;


          }

          void initial_peripheral() //第二區(qū) 初始化外圍
          {
          EA=1; //開總中斷
          ET0=1; //允許定時(shí)中斷
          TR0=1; //啟動(dòng)定時(shí)中斷

          }

          總結(jié)陳詞:
          前面花了很多節(jié)內(nèi)容在講按鍵和跑馬燈的關(guān)系,但是一直沒(méi)涉及到人機(jī)界面,在大多數(shù)的實(shí)際項(xiàng)目中,人機(jī)界面是必不可少的。人機(jī)界面的程序框架該怎么樣寫?欲知詳情,請(qǐng)聽下回分解-----在主函數(shù)while循環(huán)中驅(qū)動(dòng)數(shù)碼管的動(dòng)態(tài)掃描程序。


          評(píng)論


          技術(shù)專區(qū)

          關(guān)閉