原發(fā)布者:xujihu1884
9.3.1矩陣鍵盤(pán)的工作原理和掃描確認方式來(lái)源:《AVR單片機嵌入式系統原理與應用實(shí)踐》M16華東師范大學(xué)電子系馬潮當鍵盤(pán)中按鍵數量較多時(shí),為了減少對I/O口的占用,通常將按鍵排列成矩陣形式,也稱(chēng)為行列鍵盤(pán),這是一種常見(jiàn)的連接方式。矩陣式鍵盤(pán)接口見(jiàn)圖9-7所示,它由行線(xiàn)和列線(xiàn)組成,按鍵位于行、列的交叉點(diǎn)上。當鍵被按下時(shí),其交點(diǎn)的行線(xiàn)和列線(xiàn)接通,相應的行線(xiàn)或列線(xiàn)上的電平發(fā)生變化,MCU通過(guò)檢測行或列線(xiàn)上的電平變化可以確定哪個(gè)按鍵被按下。圖9-7為一個(gè)4x3的行列結構,可以構成12個(gè)鍵的鍵盤(pán)。如果使用4x4的行列結構,就能組成一個(gè)16鍵的鍵盤(pán)。很明顯,在按鍵數量多的場(chǎng)合,矩陣鍵盤(pán)與獨立式按鍵鍵盤(pán)相比可以節省很多的I/O口線(xiàn)。矩陣鍵盤(pán)不僅在連接上比單獨式按鍵復雜,它的按鍵識別方法也比單獨式按鍵復雜。在矩陣鍵盤(pán)的軟件接口程序中,常使用的按鍵識別方法有行掃描法和線(xiàn)反轉法。這兩種方法的基本思路是采用循環(huán)查循的方法,反復查詢(xún)按鍵的狀態(tài),因此會(huì )大量占用MCU的時(shí)間,所以較好的方式也是采用狀態(tài)機的方法來(lái)設計,盡量減少鍵盤(pán)查詢(xún)過(guò)程對MCU的占用時(shí)間。下面以圖9-7為例,介紹采用行掃描法對矩陣鍵盤(pán)進(jìn)行判別的思路。圖9-7中,PD0、PD1、PD2為3根列線(xiàn),作為鍵盤(pán)的輸入口(工作于輸入方式)。PD3、PD4、PD5、PD6為4根行線(xiàn),工作于輸出方式,由MCU(掃描)控制其輸出的電平值。行掃描法也稱(chēng)為逐行掃描查詢(xún)法,其按鍵
當鍵盤(pán)中按鍵數量較多時(shí),為了減少對 I/O 口的占用,通常將按鍵排列成矩陣形式,也稱(chēng)為行列鍵盤(pán),這是一種常見(jiàn)的連接方式。矩陣式鍵盤(pán)接口見(jiàn)圖 9-7 所示,它由行線(xiàn)和列線(xiàn)組成,按鍵位于行、列的交叉點(diǎn)上。當鍵被按下時(shí),其交點(diǎn)的行線(xiàn)和列線(xiàn)接通,相應的行線(xiàn)或列線(xiàn)上的電平發(fā)生變化,MCU 通過(guò)檢測行或列線(xiàn)上的電平變化可以確定哪個(gè)按鍵被按下。
圖 9-7 為一個(gè) 4 x 3 的行列結構,可以構成 12 個(gè)鍵的鍵盤(pán)。如果使用 4 x 4 的行列結構,就能組成一個(gè) 16 鍵的鍵盤(pán)。很明顯,在按鍵數量多的場(chǎng)合,矩陣鍵盤(pán)與獨立式按鍵鍵盤(pán)相比可以節省很多的 I/O 口線(xiàn)。
矩陣鍵盤(pán)不僅在連接上比單獨式按鍵復雜,它的按鍵識別方法也比單獨式按鍵復雜。在矩陣鍵盤(pán)的軟件接口程序中,常使用的按鍵識別方法有行掃描法和線(xiàn)反轉法。這兩種方法的基本思路是采用循環(huán)查循的方法,反復查詢(xún)按鍵的狀態(tài),因此會(huì )大量占用 MCU 的時(shí)間,所以較好的方式也是采用狀態(tài)機的方法來(lái)設計,盡量減少鍵盤(pán)查詢(xún)過(guò)程對 MCU 的占用時(shí)間。
我給你一個(gè)我自己寫(xiě)的吧 有注釋假設按下的是S1鍵進(jìn)行如下檢測(4*4鍵盤(pán))先在P3口輸出p3 00001111低四位 行會(huì )有變化cord_h =00001111&00001110 =00001110 if !=00001111延時(shí)0.1uscord_h=00001110&00001111=00001110 if !=00001111P3再輸出11111110P3 =00001110|11110000=11111110輸出高四位cord_l=P3&0xf0 //此時(shí)P3口就是輸入值01111110 而不是上面的11111110cord_l=01111110&11110000=01110000cord_h+cord_l=00001110+01110000=01111110=0x7e //此編碼即為S1的編碼#include //包含頭文件#define uchar unsigned char#define uint unsigned intunsigned char const table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f, 0x77,0x7c,0x39,0x5e,0x79,0x71};//0-Fuchar keyscan(void);void delay(uint i);void main(){ uchar key; P2=0x00;//1數碼管亮 按相應的按鍵,會(huì )顯示按鍵上的字符 while(1){ key=keyscan();//調用鍵盤(pán)掃描, switch(key) { case 0x7e:P0=table[0];break;//0 按下相應的鍵顯示相對應的碼值 case 0x7d:P0=table[1];break;//1 case 0x7b:P0=table[2];break;//2 case 0x77:P0=table[3];break;//3 case 0xbe:P0=table[4];break;//4 case 0xbd:P0=table[5];break;//5 case 0xbb:P0=table[6];break;//6 case 0xb7:P0=table[7];break;//7 case 0xde:P0=table[8];break;//8 case 0xdd:P0=table[9];break;//9 case 0xdb:P0=table[10];break;//a case 0xd7:P0=table[11];break;//b case 0xee:P0=table[12];break;//c case 0xed:P0=table[13];break;//d case 0xeb:P0=table[14];break;//e case 0xe7:P0=table[15];break;//f } }}uchar keyscan(void)//鍵盤(pán)掃描函數,使用行列反轉掃描法{ uchar cord_h,cord_l;//行列值 P3=0x0f; //行線(xiàn)輸出全為0 cord_h=P3&0x0f; //讀入列線(xiàn)值 if(cord_h!=0x0f) //先檢測有無(wú)按鍵按下 { delay(100); //去抖 cord_h=P3&0x0f; //讀入列線(xiàn)值 if(cord_h!=0x0f) { P3=cord_h|0xf0; //輸出當前列線(xiàn)值 cord_l=P3&0xf0; //讀入行線(xiàn)值 return(cord_h+cord_l);//鍵盤(pán)最后組合碼值 } }return(0xff); //返回該值}void delay(uint i)//延時(shí)函數{while(i--);}在P3口做的鍵盤(pán)你的去抖檢測沒(méi)有做好。
unsigned char KeyScan(void) //鍵盤(pán)掃描函數,使用行列逐級掃描法{ unsigned char Val; KeyPort=0xf0;//這句其實(shí)就是整體看看是否有鍵按下,四行全送0,有鍵按下,高四位肯定不為全1 if(KeyPort!=0xf0)//表示有按鍵按下 { DelayMs(10); //去抖 if(KeyPort!=0xf0) { //表示有按鍵按下 KeyPort=0xfe; //檢測第一行 if(KeyPort!=0xfe) { Val=KeyPort&0xf0; Val+=0x0e; //相當于檢測到第一行有鍵按下,鍵值=列(高四位)+行(低四位) while(KeyPort!=0xfe); DelayMs(10); //去抖 while(KeyPort!=0xfe); return Val; }。
unsigned char KeyScan(void) //鍵盤(pán)掃描函數,使用行列逐級掃描法{ unsigned char Val; KeyPort=0xf0;//這句其實(shí)就是整體看看是否有鍵按下,四行全送0,有鍵按下,高四位肯定不為全1 if(KeyPort!=0xf0)//表示有按鍵按下 { DelayMs(10); //去抖 if(KeyPort!=0xf0) { //表示有按鍵按下 KeyPort=0xfe; //檢測第一行 if(KeyPort!=0xfe) { Val=KeyPort&0xf0; Val+=0x0e; //相當于檢測到第一行有鍵按下,鍵值=列(高四位)+行(低四位) while(KeyPort!=0xfe); DelayMs(10); //去抖 while(KeyPort!=0xfe); return Val; }。
聲明:本網(wǎng)站尊重并保護知識產(chǎn)權,根據《信息網(wǎng)絡(luò )傳播權保護條例》,如果我們轉載的作品侵犯了您的權利,請在一個(gè)月內通知我們,我們會(huì )及時(shí)刪除。
蜀ICP備2020033479號-4 Copyright ? 2016 學(xué)習?shū)B(niǎo). 頁(yè)面生成時(shí)間:2.357秒