<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ThinkChat2.0新版上線,更智能更精彩,支持會話、畫圖、視頻、閱讀、搜索等,送10W Token,即刻開啟你的AI之旅 廣告
                【98.1 “先加速后勻速”的觸發。】 ![](https://img.kancloud.cn/a2/3d/a23df87ac21f61d2182864f67461b009_359x103.png) 上圖98.1.1 獨立按鍵電路 ![](https://img.kancloud.cn/73/34/7334d9d189f0de190e15939b9fff75d9_214x279.png) 上圖98.1.2 灌入式驅動8個LED ![](https://img.kancloud.cn/89/70/8970513a066fe0726b2997dcb0329ce0_194x190.png) 上圖98.1.3 有源蜂鳴器電路 當“連續加”或者“連續減”的數據范圍很大的時候,就需要按鍵的加速與勻速相結合的觸發方式。“加速”是指按住按鍵不松手,按鍵剛開始觸發是從慢到快的漸進過程,當“加速”到某個特別快的速度的時候,就“不再加速”,而是以該“恒定高速”進行“連續勻速”觸發。這種觸發方式,“加速”和“勻速”是相輔相成缺一不可的,為什么?假如沒有“加速”只有“勻速”,那么剛按下按鍵就直接以最高速的“勻速”進行,就會跑過頭,缺乏微調功能;而假如沒有“勻速”只有“加速”,那么按下按鍵不松手后,速度就會一直不斷飆升,最后失控過沖。 本節例程實現的功能如下: (1) 要更改一個“設置參數”(一個全局變量),參數的范圍是0到800。 (2)8個受“設置參數”控制的跑馬燈在某一時刻只有1個LED亮,每觸發一次K1按鍵,該“設置參數”就自減1,最小值為0;相反,每觸發一次K2按鍵,該“設置參數”就自加1,最大值為800。 (3)LED燈實時顯示“設置參數”的范圍狀態: 只有第0個LED燈亮:0<=“設置參數”<100。 只有第1個LED燈亮:100<=“設置參數”<200。 只有第2個LED燈亮:200<=“設置參數”<300。 只有第3個LED燈亮:300<=“設置參數”<400。 只有第4個LED燈亮:400<=“設置參數”<500。 只有第5個LED燈亮:500<=“設置參數”<600。 只有第6個LED燈亮:600<=“設置參數”<700。 只有第7個LED燈亮:700<=“設置參數”<=800。 (4) 按鍵每“單擊”一次蜂鳴器就鳴叫一次,但是,當按鍵“從單擊進入連擊”后,蜂鳴器就不鳴叫。 \#include "REG52.H" \#define KEY\_VOICE\_TIME 50 \#define KEY\_SHORT\_TIME 25 //按鍵單擊的“濾波”時間 \#define KEY\_ENTER\_CONTINUITY\_TIME 300 //按鍵“從單擊進入連擊”的間隔時間 \#define KEY\_CONTINUITY\_INITIAL\_TIME 80 //按鍵“連擊”起始的預設間隔時間 \#define KEY\_SUB\_DT\_TIME 8 //按鍵在“加速”時每次減小的時間。 \#define KEY\_CONTINUITY\_MIN\_TIME 10 //按鍵時間減小到最后的“勻速”間隔時間。 \#define BUS\_P0 P0 //8個LED燈一一對應單片機的P0口總線 void T0\_time(); void SystemInitial(void) ; void Delay(unsigned long u32DelayTime) ; void PeripheralInitial(void) ; void BeepOpen(void); void BeepClose(void); void VoiceScan(void); void KeyScan(void); void KeyTask(void); void DisplayTask(void); //顯示的任務函數(LED顯示狀態) sbit P3\_4=P3^4; //蜂鳴器 sbit KEY\_INPUT1=P2^2; //K1按鍵識別的輸入口。 sbit KEY\_INPUT2=P2^1; //K2按鍵識別的輸入口。 volatile unsigned char vGu8BeepTimerFlag=0; volatile unsigned int vGu16BeepTimerCnt=0; unsigned int Gu16SetData=0; //“設置參數”。范圍從0到800。LED燈反映該當前值的范圍狀態 unsigned char Gu8DisplayUpdate=1; //顯示的刷新標志 volatile unsigned char vGu8KeySec=0; //按鍵的觸發序號 volatile unsigned char vGu8ShieldVoiceFlag=0; //屏蔽聲音的標志 void main() { SystemInitial(); Delay(10000); PeripheralInitial(); while(1) { KeyTask(); //按鍵的任務函數 DisplayTask(); //顯示的任務函數(LED顯示狀態) } } /\* 注釋一: \* Gu8DisplayUpdate這類“顯示刷新變量”在“顯示框架”里是很常見的,而且屢用屢爽。 \* 目的是,既能及時刷新顯示,又能避免主函數“不斷去執行顯示代碼”而影響程序效率。 \*/ void DisplayTask(void) //顯示的任務函數(LED顯示狀態) { if(1==Gu8DisplayUpdate) //需要刷新一次顯示 { Gu8DisplayUpdate=0; //及時清零,避免主函數“不斷去執行顯示代碼”而影響程序效率 if(Gu16SetData<100) { BUS\_P0=~(1<<0); //第0個燈亮 } else if(Gu16SetData<200) { BUS\_P0=~(1<<1); //第1個燈亮 } else if(Gu16SetData<300) { BUS\_P0=~(1<<2); //第2個燈亮 } else if(Gu16SetData<400) { BUS\_P0=~(1<<3); //第3個燈亮 } else if(Gu16SetData<500) { BUS\_P0=~(1<<4); //第4個燈亮 } else if(Gu16SetData<600) { BUS\_P0=~(1<<5); //第5個燈亮 } else if(Gu16SetData<700) { BUS\_P0=~(1<<6); //第6個燈亮 } else { BUS\_P0=~(1<<7); //第7個燈亮 } } } /\* 注釋二: \* 按鍵“先加速后勻速”的識別過程: \* 第一步:每次按一次就觸發一次“單擊”,如果按下去到松手的時間不超過1秒,則不會進入 \* “連擊”模式。 \* 第二步:如果按下去不松手的時間超過1秒,則進入“連擊”模式。按鍵觸發的節奏 \* 不斷加快,直至到達某個極限值,然后以此極限值間隔勻速觸發。這就是“先加速后勻速”。 \*/ void KeyScan(void) //此函數放在定時中斷里每1ms掃描一次 { static unsigned char Su8KeyLock1; static unsigned int Su16KeyCnt1; static unsigned int Su16KeyContinuityCnt1; //連擊計數器 static unsigned int Su16KeyContinuityTime1=KEY\_CONTINUITY\_INITIAL\_TIME; //動態時間閥值 static unsigned char Su8KeyLock2; static unsigned int Su16KeyCnt2; static unsigned int Su16KeyContinuityCnt2; //連擊計數器 static unsigned int Su16KeyContinuityTime2=KEY\_CONTINUITY\_INITIAL\_TIME; //動態時間閥值 //K1按鍵 if(0!=KEY\_INPUT1)//單個K1按鍵沒有按下,及時清零一些標志。 { Su8KeyLock1=0; //按鍵解鎖 Su16KeyCnt1=0; //去抖動延時計數器清零,此行非常巧妙,是全場的亮點。 Su16KeyContinuityCnt1=0; //連擊計數器 Su16KeyContinuityTime1=KEY\_CONTINUITY\_INITIAL\_TIME; //動態時間閥值。重裝初始值。 } else if(0==Su8KeyLock1)//單個按鍵K1被按下 { Su16KeyCnt1++; //累加定時中斷次數,每一次累加額度是1ms if(Su16KeyCnt1>=KEY\_SHORT\_TIME) //按鍵的“濾波”時間25ms { Su8KeyLock1=1; //“自鎖” vGu8KeySec=1; //觸發一次K1按鍵 Su16KeyCnt1=0; //清零,為了下一步用來累加“從單擊進入連擊的間隔時間300ms” } } else if(Su16KeyCnt1<=KEY\_ENTER\_CONTINUITY\_TIME)//按住不松手累加到300ms { Su16KeyCnt1++; //累加定時中斷次數,每一次累加額度是1ms } else //按住累加到300ms后仍然不放手,這個時候進入有節奏的連續觸發 { Su16KeyContinuityCnt1++; //連擊計數器開始累加,每一次累加額度是1ms if(Su16KeyContinuityCnt1>=Su16KeyContinuityTime1) //按住沒松手,每隔一會就觸發一次 { Su16KeyContinuityCnt1=0; //清零,為了繼續連擊。 vGu8KeySec=1; //觸發一次K1按鍵 vGu8ShieldVoiceFlag=1; //把當前按鍵觸發的聲音屏蔽掉 if(Su16KeyContinuityTime1>=KEY\_SUB\_DT\_TIME) { //此數值不斷被減小,按鍵的觸發速度就不斷變快 Su16KeyContinuityTime1=Su16KeyContinuityTime1-KEY\_SUB\_DT\_TIME;//變快節奏 } if(Su16KeyContinuityTime1<KEY\_CONTINUITY\_MIN\_TIME) //最小間隔時間就是“高速勻速” { Su16KeyContinuityTime1=KEY\_CONTINUITY\_MIN\_TIME; //最后以此最高速進行“勻速” } } } //K2按鍵 if(0!=KEY\_INPUT2) { Su8KeyLock2=0; Su16KeyCnt2=0; Su16KeyContinuityCnt2=0; Su16KeyContinuityTime2=KEY\_CONTINUITY\_INITIAL\_TIME; } else if(0==Su8KeyLock2) { Su16KeyCnt2++; if(Su16KeyCnt2>=KEY\_SHORT\_TIME) { Su8KeyLock2=1; vGu8KeySec=2; //觸發一次K2按鍵 Su16KeyCnt2=0; } } else if(Su16KeyCnt2<=KEY\_ENTER\_CONTINUITY\_TIME) { Su16KeyCnt2++; } else { Su16KeyContinuityCnt2++; if(Su16KeyContinuityCnt2>=Su16KeyContinuityTime2) { Su16KeyContinuityCnt2=0; vGu8KeySec=2; //觸發一次K2按鍵 vGu8ShieldVoiceFlag=1; if(Su16KeyContinuityTime2>=KEY\_SUB\_DT\_TIME) { Su16KeyContinuityTime2=Su16KeyContinuityTime2-KEY\_SUB\_DT\_TIME; } if(Su16KeyContinuityTime2<KEY\_CONTINUITY\_MIN\_TIME) { Su16KeyContinuityTime2=KEY\_CONTINUITY\_MIN\_TIME; } } } } void KeyTask(void) //按鍵任務函數,放在主函數內 { if(0==vGu8KeySec) { return; //按鍵的觸發序號是0意味著無按鍵觸發,直接退出當前函數,不執行此函數下面的代碼 } switch(vGu8KeySec) //根據不同的按鍵觸發序號執行對應的代碼 { case 1: //K1觸發的任務 if(Gu16SetData>0) { Gu16SetData--; //“設置參數” Gu8DisplayUpdate=1; //刷新顯示 } if(0==vGu8ShieldVoiceFlag) //聲音沒有被屏蔽 { vGu8BeepTimerFlag=0; vGu16BeepTimerCnt=KEY\_VOICE\_TIME; //發出“嘀”一聲 vGu8BeepTimerFlag=1; } vGu8ShieldVoiceFlag=0; //及時把屏蔽標志清零,避免平時正常的單擊聲音也被淹沒。 vGu8KeySec=0; //響應按鍵服務處理程序后,按鍵編號必須清零,避免一直觸發 break; case 2: //K2觸發的任務 if(Gu16SetData<800) { Gu16SetData++; //“設置參數” Gu8DisplayUpdate=1; //刷新顯示 } if(0==vGu8ShieldVoiceFlag) //聲音沒有被屏蔽 { vGu8BeepTimerFlag=0; vGu16BeepTimerCnt=KEY\_VOICE\_TIME; //發出“嘀”一聲 vGu8BeepTimerFlag=1; } vGu8ShieldVoiceFlag=0; //及時把屏蔽標志清零,避免平時正常的單擊聲音也被淹沒。 vGu8KeySec=0; //響應按鍵服務處理程序后,按鍵編號必須清零,避免一直觸發 break; } } void T0\_time() interrupt 1 { VoiceScan(); KeyScan(); //按鍵識別的驅動函數 TH0=0xfc; TL0=0x66; } void SystemInitial(void) { TMOD=0x01; TH0=0xfc; TL0=0x66; EA=1; ET0=1; TR0=1; } void Delay(unsigned long u32DelayTime) { for(;u32DelayTime>0;u32DelayTime--); } void PeripheralInitial(void) { } void BeepOpen(void) { P3\_4=0; } void BeepClose(void) { P3\_4=1; } void VoiceScan(void) { static unsigned char Su8Lock=0; if(1==vGu8BeepTimerFlag&&vGu16BeepTimerCnt>0) { if(0==Su8Lock) { Su8Lock=1; BeepOpen(); } else { vGu16BeepTimerCnt--; if(0==vGu16BeepTimerCnt) { Su8Lock=0; BeepClose(); } } } }
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看