新聞中心

        EEPW首頁 > 嵌入式系統 > 設計應用 > 比較好的按鍵處理方法以及實例

        比較好的按鍵處理方法以及實例

        作者: 時間:2016-11-25 來源:網絡 收藏
        按鍵是單片機最常用的輸入設備了。按下接通,松開分斷,本來是 很簡單的事情,由于現在我們使用的單片機實在是一個非常高速的裝置,由于它的高速,使得本來不被人們重視的機械觸點在接通和斷開瞬間的多次快速彈跳問題變 得突出起來。常規的方法就是一旦發現按鍵動作,就人為加上10-20毫秒的延時,等觸點穩定下來以后再進行(例如判斷按鍵碼)。同時為了不至于把 一次按鍵當做多次按鍵,通常就是等待按鍵確實釋放以后再執行鍵碼對應的程序。詳細過程參見版主的“事無巨細,獨立按鍵”文。
        延時法簡單實用,編程也容易,使用非常普遍。
        但是這個辦法有些缺點,1是加上延時后,在延時期間單片機什么也沒干,就在那里兜圈子耗時間,如果這時有其他事情需要處理也只好放一放,降低了運行 效率。2是對一些需要較復雜按鍵功能的情況例如區別長按鍵和短按鍵難于實現。
        那么其他的辦法是有,例如中斷法,不按鍵就不查詢,直到按鍵觸發外部中斷。但是單片機通常外部中斷口很少而按鍵較多,給應用造成不便。
        下面就介紹一個新的按鍵查詢方法:狀態機法。說明如下:
        1,給按鍵設定3種狀態:狀態0:無按鍵,狀態1:已經按下,狀態2:已經釋放。按鍵可以一直處于狀態0,也可以由狀態0轉為狀態1,也可以由狀態1轉為 狀態2,然后恢復到狀態0。如此順序循環。
        2,通過定時(例如定時器中斷)每隔一段時間(例如10毫秒)檢查一下按鍵 狀態,根據上次檢查的狀態和當前的狀態比較,來確定應該做什么。在上述時間間隔內,單片機就可以執行其他任務。一旦確認按鍵成立,就可以立即找出鍵碼并進 行隨后的鍵碼處理程序而無需等待按鍵釋放,加上適當的處置也可以對比較復雜的按鍵進行處理。
        下面以一個具體的程序,詳細解釋怎么實現:讀鍵函數readkey()。無參數,返回鍵碼。4個按鍵連接在PC0...PC3引腳
        ///////////////////////定時器溢出中斷用于定時查鍵 大約10毫秒中斷一次
        keyscan_t=0; //////這個全局變量是個定時器標志,定時中斷置1,外部請0
        ISR(TIMER0_OVF_vect)
        {
        TCNT0=216; ////程序啟動后設TCCR0=0X04;256分頻,每(256-216)*256微秒中斷一次
        keyscan_t=1; ////定時時間到標志置1
        PORTD=dispdata; ////其它刷新顯示功能和理無關
        }

        ////////////////////////////////////
        讀鍵函數
        ////////////////////////////////////
        uchar readkey(void)
        {
        uchar keyval=0;//////keyvai是最終鍵碼,4個按鍵分別對應的鍵碼是0x0e,0x0d,0x0b,0x07
        uchar newkey; ////////newkey是當前鍵碼,需要和上次鍵碼比較
        static uchar keystate=0; ////狀態值,起始為0,注意它是靜態變量賦值后就保持到改寫為止
        uchar keyOK; /////////確認按鍵
        static uchar lastkey; /////lastkey記錄上次檢查時的鍵碼,也是靜態變量
        newkey=PINC&0X0F; /////鍵碼就是PC口低4位取值每次都要讀取
        switch(keystate) //////按照狀態值進行不同的處理,單片機啟動后總是狀態0,
        {
        case 0: /////狀態0
        if(newkey!=0x0f) //////如果有鍵
        {
        keystate=1; //////有鍵記下狀態1
        lastkey=newkey; /////有鍵就用當前鍵碼代替原來鍵碼等待下次檢查
        }
        break; //////如果無鍵直接跳出,有鍵進行上述處理后跳出,注意有鍵狀態值已變
        case 1: ///////如上次有鍵,這次就轉到狀態1
        if(newkey==lastkey) /////這次讀取的鍵值如果和上次記錄的一樣,就是確認按鍵了
        {
        keyOK=1; //////置位按鍵標志
        keyval=newkey; /////取得鍵碼
        keystate=2; //////按鍵狀態下次要轉狀態2
        }
        else //////如果讀鍵和上次不同,不確認按鍵,除了不進行以上處理還要把狀態值情0
        keystate=0;
        break; .///////跳出
        case 2: /////////狀態2
        if(newkey==0x0f) ///////如果10毫秒后仍然無鍵
        keystate=0; //////下次回到狀態0
        break;
        }
        return keyval; ////////返回鍵碼
        }
        ////////////////////////////////

        以上就是在調頻收音機里使用的獲取鍵碼程序。每10余毫秒定時中斷一次就執行一次。

        本文引用地址:http://www.104case.com/article/201611/321129.htm


        關鍵詞: 按鍵處

        評論


        技術專區

        關閉
        主站蜘蛛池模板: 公主岭市| 扶沟县| 彝良县| 新和县| 汕头市| 德令哈市| 根河市| 新野县| 开江县| 松桃| 客服| 富川| 简阳市| 乌兰县| 罗甸县| 高陵县| 博白县| 长岛县| 益阳市| 神池县| 威信县| 清流县| 襄汾县| 桃江县| 新绛县| 商城县| 平安县| 即墨市| 云龙县| 阳城县| 南岸区| 碌曲县| 任丘市| 佳木斯市| 福贡县| 日喀则市| 拜城县| 察雅县| 尼玛县| 蕉岭县| 揭西县|