新聞中心

        EEPW首頁 > 嵌入式系統(tǒng) > 設(shè)計(jì)應(yīng)用 > 4*4矩陣鍵盤制作電路+鍵盤掃描法89c52c程序驅(qū)動(dòng)數(shù)碼管

        4*4矩陣鍵盤制作電路+鍵盤掃描法89c52c程序驅(qū)動(dòng)數(shù)碼管

        作者: 時(shí)間:2016-11-26 來源:網(wǎng)絡(luò) 收藏
        這里介紹最常用的4*4矩陣鍵盤,其他的更多鍵在此基礎(chǔ)上拓展。

        一般我們用的電路就如下,此圖我隨手畫下,看懂意思就好了

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

        如果你有興趣可以按照此電路制作,下面附上焊接實(shí)物圖

        矩陣鍵盤的識(shí)別方法一般有掃描法,線反轉(zhuǎn)法

        掃描法:

        矩陣式鍵盤結(jié)構(gòu):輸出行線鎖存器,輸入列線緩沖器。

        工作過程:

        1.CPU先使行線P1.0為低,其余行線為高
        2.CPU讀入輸入緩沖器的狀態(tài),以確定哪條列線為0狀態(tài),若此時(shí)P1.7為0,則"C"鍵按下;若P1.5為0,則"E"鍵按下
        3.若輸入緩沖器(列線)狀態(tài)全部為1,說明P1.0行沒有鍵盤按下,CPU急繼續(xù)使P1.1為0,其余行線為高,再讀入輸入緩沖器的狀態(tài),以確定哪條列線為0,從而判斷是哪個(gè)鍵盤按下
        4.當(dāng)判斷那個(gè)鍵盤按下后,程序轉(zhuǎn)入相應(yīng)的鍵盤處理程序

        把每個(gè)鍵都分成水平和垂直的兩端接入,比如說掃描碼是從垂直的入,那就代表那一行所接收到的掃描碼是同一個(gè)bit,而讀入掃描碼的則是水平,掃描的動(dòng)作是先輸入掃描碼,再去讀取輸入的值,經(jīng)過比對(duì)之后就可知道是哪個(gè)鍵被按下。

        比如說掃描碼送入01111111,前面的0111是代表此時(shí)掃描第一行P1.0列,而后面的1111是讓讀取的4行接腳先設(shè)為VDD,若此時(shí)第一行的第三列按鍵被按下,那讀取的結(jié)果就會(huì)變成01111101(注意1111變成1101),其中LSB的第三個(gè)bit會(huì)由1變成0,這是因?yàn)檫@個(gè)按鍵被按下之后,會(huì)被垂直的掃描碼電位short,而把讀取的LSB的bit電位拉到0,此即為掃描原理。

        線反轉(zhuǎn)法:僅需兩步:(即控制器的接口必須是雙向I/O口)

        Step 1:將列線作為輸出線,行線作為輸入線。置輸出線全部為0,此時(shí)行線中呈低電平0的為按鍵所在行,如果全部都不是0,則沒有按鍵按下。

        Step 2:將第一步反過來,即將行線作為輸出線,列線作為輸入線。置輸出線全部為0,此時(shí)列線呈低電平的為按鍵所在的列。這樣,就可以確定了按鍵的位置(X,Y)。

        當(dāng)然還要注意軟件去抖動(dòng),另外此法需要在行線上上拉電阻,就是焊接電路中的四個(gè)電阻。

        今天這里以掃描法做介紹,不用到上拉電阻。

        此程序是按鍵后,在數(shù)碼管上顯示此鍵的序號(hào)從第一行開始一次是1,2,3,4,5,6,7,8,9,H,F,L,-,后三位為關(guān)數(shù)碼管,當(dāng)然顯示什么呢自己可以隨意的修改,為以后的擴(kuò)展使用。

        我按下第二行第二列的鍵,顯示的是6(1*4+2=6)

        ,明白了程序功能,下來你讀起來就輕松了

        程序中的keyscan()函數(shù)就是掃描法

        這是我花了周末下午的美好時(shí)光編好的程序啊,在板子上的效果圖,經(jīng)檢測(cè)無誤,奉上

        #include
        #include
        #define uchar unsigned char
        #define unit unsigned int
        #definea 0x04//AAAA
        #defineb 0x01// FB
        #definec 0x10// FB
        #defined 0x40//GGGG
        #definee 0x80// ECh
        #definef 0x02// EC
        #define g 0x08//DDDDH
        #defineh 0x20

        unsigned char code LED_table[]={
        a+b+c+d+e+f,//"0"
        b+c,//"1"
        a+b+d+e+g,//"2"
        a+b+c+d+g,//"3"
        b+c+f+g,//"4"
        a+c+d+f+g,//"5"
        a+c+d+e+f+g,//"6"
        a+b+c,//"7"
        a+b+c+d+e+f+g,//"8"
        a+b+c+d+f+g,//"9"
        b+c+e+f+g,//"H"
        a+f+e+g,//"C"
        d+e+f,//"F"
        g,//"-"
        0x00//black
        };

        uchar keyscan(void);

        sbit COM1=P2^3;
        sbit COM3=P2^1;
        sbit COM4=P2^2;
        sbit COM2=P2^0;

        sbit CLK=P2^7;
        void delayms(unit);

        void main()
        {uchar k=0;
        CLK=1;
        P0=0;
        COM1=0;
        COM2=1;
        COM3=1;
        COM4=1;
        while(1)
        {
        while(k==0)
        {
        k=keybscan();
        }
        P0=LED_table[k];
        k=0;
        }
        }
        uchar keyscan(void)
        {
        uchar row,re,m=1,n=0;
        P1=0xf0;//置所有行為低電平,行掃描,列線輸入(此時(shí))
        if((P1&0xf0)!=0xf0)//判斷是否有有鍵按下(讀取列的真實(shí)狀態(tài),若第4列有鍵按下則P1的值會(huì)變成0111 0000),有往下執(zhí)行
        {
        delayms(10);//延時(shí)去抖動(dòng)(10ms)
        if((P1&0xf0)!=0xf0)//再次判斷列中是否是干擾信號(hào),不是則向下執(zhí)行
        {
        row=0xFE;//逐行掃描初值(即先掃描第1行)
        while((row&0x10)!=0) //行掃描完成時(shí)(即4行已經(jīng)全部掃描完成)row為1110 1111停止while
        {
        P1=row;//輸出行掃描碼
        if ((P1&0xf0)!=0xf0)//本行有鍵按下(即P1(真實(shí)的狀態(tài))的高四位不全為1)
        {
        re=((P1&0xf0)>>0x04); //輸出列掃描碼 按位或運(yùn)算
        re=(~re)&0x0f;//列值
        while(re!=1)
        {
        re/=2;
        m++;
        }

        return(n*4+m); //返回行和列
        }
        else

        {
        row=(row<<1)|0x01;//行掃描碼左移一位
        n++;
        }
        }
        }
        else
        {
        return 0;//無鍵按下,返回0
        }

        }
        }

        void delayms(unit i)
        {
        unit j;
        for(;i>0;i--)
        for(j=227;j>0;j--);
        }

        提到擴(kuò)展使用,做這個(gè)鍵盤絕對(duì)不是這么簡(jiǎn)單的應(yīng)用,我有了很多想法,可以和前面一篇文章中的液晶顯示器結(jié)合起來,編寫一個(gè)模擬手機(jī)鍵盤的

        程序,做一個(gè)相互通信的短信發(fā)送器,很有意思的哦,如果加上無線傳輸模塊,就可以短距離相互發(fā)短信,免費(fèi)的哦,很有創(chuàng)意把,將學(xué)校的情侶間推銷一下說不定很有市場(chǎng)前景呢,吼吼~~



        評(píng)論


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

        關(guān)閉
        主站蜘蛛池模板: 永年县| 水城县| 勃利县| 杭锦后旗| 葵青区| 兰考县| 历史| 荆门市| 马龙县| 怀宁县| 景德镇市| 彰化市| 麻阳| 北川| 金秀| 中卫市| 康马县| 江口县| 会同县| 长乐市| 神池县| 礼泉县| 渝北区| 平顺县| 普定县| 调兵山市| 天峻县| 新密市| 西城区| 烟台市| 久治县| 祁门县| 广州市| 巴林右旗| 冷水江市| 凤庆县| 栾城县| 大宁县| 兰溪市| 扶沟县| 平和县|