4乘4矩阵键盘

合集下载

4×4矩阵式键盘的课程设计

4×4矩阵式键盘的课程设计

“电子创新设计与实践”课程期中课题设计报告姓名:张思源,学:20102121026,年级:2010,专业:电信报告内容设计一个4*4矩阵键盘,并编写相关程序摘要1.4×4矩阵式键盘程序识别原理。

2.4×4矩阵式键盘按键的设计方法。

报告正文:一、设计原理(1)如图14.2所示,用单片机的并行口P3连接4×4矩阵键盘,并以单片机的P3.0-P3.3各管脚作输入线,以单片机的P3.4-P3.7各管脚作输出线,在数码管上显示每个按键“0-F”的序号。

(2)键盘中对应按键的序号排列如图14.1所示。

二、参考电路图14.2 4×4矩阵式键盘识别电路原理图图14.1 4×4键盘0-F显示图14.3 4×4矩阵式键盘识别程序流程图三、电路硬件说明(1)在“单片机系统”区域中,把单片机的P3.0-P3.7端口通过8联拨动拨码开关JP3连接到“4×4行列式键盘”区域中的M1-M4,N1-N4端口上。

(2)在“单片机系统”区域中,把单片机的P0.0-P0.7端口连接到“静态数码显示模块”区域中的任何一个a-h端口上;要求:P0.0对应着a,P0.1对应着b,……,P0.7对应着h。

四、程序设计内容(1)4×4矩阵键盘识别处理。

(2)每个按键都有它的行值和列值,行值和列值的组合就是识别这个按键的编码。

矩阵的行线和列线分别通过两并行接口和CPU通信。

键盘的一端(列线)通过电阻接VCC,而接地是通过程序输出数字“0”实现的。

键盘处理程序的任务是:确定有无键按下,判断哪一个键按下,键的功能是什么?还要消除按键在闭合或断开时的抖动。

两个并行口中,一个输出扫描码,使按键逐行动态接地;另一个并行口输入按键状态,由行扫描值和回馈信号共同形成键编码而识别按键,通过软件查表,查出该键的功能。

五、程序流程图(如图14.3所示)六、汇编源程序;;;;;;;;;;定义单元;;;;;;;;;;COUNT EQU 30H;;;;;;;;;;入口地址;;;;;;;;;;ORG 0000HLJMP STARTORG 0003HRETIORG 000BHRETIORG 0013HRETIORG 001BHRETIRETIORG 002BHRETI;;;;;;;;;;主程序入口;;;;;;;;;;ORG 0100HSTART: LCALL CHUSHIHUALCALL PANDUANLCALL XIANSHILJMP START;;;;;;;;;;初始化程序;;;;;;;;;; CHUSHIHUA: MOV COUNT,#00HRET;;;;;;;;;;判断哪个按键按下程序;;;;;;;;;; PANDUAN: MOV P3,#0FFHCLR P3.4MOV A,P3ANL A,#0FHXRL A,#0FHJZ SW1LCALL DELAY10MSJZ SW1ANL A,#0FHCJNE A,#0EH,K1 MOV COUNT,#0LJMP DKK1: CJNE A,#0DH,K2 MOV COUNT,#4LJMP DKK2: CJNE A,#0BH,K3 MOV COUNT,#8LJMP DKK3: CJNE A,#07H,K4 MOV COUNT,#12K4: NOPLJMP DKSW1: MOV P3,#0FFH CLR P3.5MOV A,P3ANL A,#0FHXRL A,#0FHJZ SW2LCALL DELAY10MSMOV A,P3ANL A,#0FHCJNE A,#0EH,K5 MOV COUNT,#1LJMP DKK5: CJNE A,#0DH,K6 MOV COUNT,#5LJMP DKK6: CJNE A,#0BH,K7 MOV COUNT,#9LJMP DKK7: CJNE A,#07H,K8 MOV COUNT,#13K8: NOPLJMP DKSW2: MOV P3,#0FFH CLR P3.6MOV A,P3ANL A,#0FHXRL A,#0FHJZ SW3LCALL DELAY10MSJZ SW3MOV A,P3ANL A,#0FHCJNE A,#0EH,K9 MOV COUNT,#2LJMP DKK9: CJNE A,#0DH,KA MOV COUNT,#6LJMP DKKA: CJNE A,#0BH,KB MOV COUNT,#10 LJMP DKKB: CJNE A,#07H,KC MOV COUNT,#14 KC: NOPLJMP DKSW3: MOV P3,#0FFH CLR P3.7MOV A,P3ANL A,#0FHXRL A,#0FHJZ SW4LCALL DELAY10MSJZ SW4MOV A,P3ANL A,#0FHCJNE A,#0EH,KDMOV COUNT,#3LJMP DKKD: CJNE A,#0DH,KEMOV COUNT,#7LJMP DKKE: CJNE A,#0BH,KFMOV COUNT,#11LJMP DKKF: CJNE A,#07H,KGMOV COUNT,#15KG: NOPLJMP DKSW4: LJMP PANDUANDK: RET;;;;;;;;;;显示程序;;;;;;;;;;XIANSHI: MOV A,COUNTMOV DPTR,#TABLEMOVC A,@A+DPTRMOV P0,ALCALL DELAYSK: MOV A,P3ANL A,#0FHXRL A,#0FHJNZ SKRET;;;;;;;;;;10ms延时程序;;;;;;;;;; DELAY10MS: MOV R6,#20D1: MOV R7,#248DJNZ R7,$DJNZ R6,D1RET;;;;;;;;;;200ms延时程序;;;;;;;;;; DELAY: MOV R5,#20LOOP: LCALL DELAY10MSDJNZ R5,LOOPRET;;;;;;;;;;共阴码表;;;;;;;;;;TABLE: DB 3FH,06H,5BH,4FH,66H,6DH,7DH,07HDB 7FH,6FH,77H,7CH,39H,5EH,79H,71H ;;;;;;;;;;结束标志;;;;;;;;;;END八、C语言源程序#include<AT89X51.H>unsigned char code table[]={0x3f,0x66,0x7f,0x39, 0x06,0x6d,0x6f,0x5e,0x5b,0x7d,0x77,0x79,0x4f,0x07,0x7c,0x71};void main(void){ unsigned char i,j,k,key;while(1){ P3=0xff; //给P3口置1//P3_4=0; //给P3.4这条线送入0//i=P3;i=i&0x0f; //屏蔽低四位//if(i!=0x0f) //看是否有按键按下//{ for(j=50;j>0;j--) //延时//for(k=200;k>0;k--);if(i!=0x0f) //再次判断按键是否按下//{ switch(i) //看是和P3.4相连的四个按键中的哪个//{ case 0x0e:key=0;break;case 0x0d:key=1;break;case 0x0b:key=2;break;case 0x07:key=3;break;}P0=table[key]; //送数到P0口显示//}}P3=0xff;P3_5=0; //读P3.5这条线//i=P3;i=i&0x0f; //屏蔽P3口的低四位//if(i!=0x0f) //读P3.5这条线上看是否有按键按下// { for(j=50;j>0;j--) //延时//for(k=200;k>0;k--);i=P3; //再看是否有按键真的按下//i=i&0x0f;if(i!=0x0f){ switch(i) //如果有,显示相应的按键// { case 0x0e:key=4;break;case 0x0d:key=5;break;case 0x0b:key=6;break;case 0x07:key=7;break;}P0=table[key]; //送入P0口显示//}}P3=0xff;P3_6=0; //读P3.6这条线上是否有按键按下// i=P3;i=i&0x0f;if(i!=0x0f){ for(j=50;j>0;j--)for(k=200;k>0;k--);i=P3;i=i&0x0f;if(i!=0x0f){ switch(i){ case 0x0e:key=8;break;case 0x0d:key=9;break;case 0x0b:key=10;break;case 0x07:key=11;break;}P0=table[key];}}P3=0xff;P3_7=0; //读P3.7这条线上是否有按键按下// i=P3;i=i&0x0f;if(i!=0x0f){ for(j=50;j>0;j--)for(k=200;k>0;k--);i=P3;i=i&0x0f;if(i!=0x0f){ switch(i){ case 0x0e:key=12;break;case 0x0d:key=13;break;case 0x0b:key=14;break;case 0x07:key=15;break;}P0=table[key];}}}}参考文献:百度百科。

51单片机4×4矩阵键盘且在数码管最后一位显示汇编语言

51单片机4×4矩阵键盘且在数码管最后一位显示汇编语言

51下面是51单片机使用4×4矩阵键盘的汇编程序,并在数码管的最后一位显示一个字符:```ORG 0 ;程序从地址0开始MOV P1,#0FFH ;P1口设置为输入口MOV P0,#0FH ;P0口设置为输出口LOOP:MOV A,P1 ;读取P1口的值CJNE A,#0FFH,KEY_PRESSED ;判断是否有按键按下SJMP LOOP ;如果没有按键按下,继续循环KEY_PRESSED:MOV R0,A ;保存按键的值CLR P0.0 ;选定行0MOV A,P1ANL A,#0F0H ;按位与运算,保留列位的值CJNE A,#0F0H,COL0 ;判断是否有按键按下在第0列MOV A,#'0' ;如果在第0列按下按键,则A的值为0JMP DISP ;跳转到显示程序COL0:CLR P0.1 ;选定行1MOV A,P1ANL A,#0F0HCJNE A,#0E0H,COL1 ;判断是否有按键按下在第1列MOV A,#'1' ;如果在第1列按下按键,则A的值为1JMP DISP ;跳转到显示程序COL1:CLR P0.2 ;选定行2MOV A,P1ANL A,#0F0HCJNE A,#0D0H,COL2 ;判断是否有按键按下在第2列MOV A,#'2' ;如果在第2列按下按键,则A的值为2JMP DISP ;跳转到显示程序COL2:CLR P0.3 ;选定行3MOV A,P1ANL A,#0F0HCJNE A,#0B0H,COL3 ;判断是否有按键按下在第3列MOV A,#'3' ;如果在第3列按下按键,则A的值为3JMP DISP ;跳转到显示程序COL3:CLR P0.4 ;选定行4MOV A,P1ANL A,#0F0H4MOV A,#'4' ;如果在第4列按下按键,则A的值为4 JMP DISP ;跳转到显示程序COL4:CLR P0.5 ;选定行5MOV A,P1ANL A,#0F0HCJNE A,#0B0H,COL5 ;判断是否有按键按下在第5列 MOV A,#'5' ;如果在第5列按下按键,则A的值为5 JMP DISP ;跳转到显示程序COL5:CLR P0.6 ;选定行6MOV A,P1ANL A,#0F0HCJNE A,#0D0H,COL6 ;判断是否有按键按下在第6列 MOV A,#'6' ;如果在第6列按下按键,则A的值为6 JMP DISP ;跳转到显示程序COL6:CLR P0.7 ;选定行7MOV A,P1ANL A,#0F0HCJNE A,#0E0H,COL7 ;判断是否有按键按下在第7列 MOV A,#'7' ;如果在第7列按下按键,则A的值为7 JMP DISP ;跳转到显示程序COL7:MOV A,#00HJMP EXIT ;如果没有按下任何键,退出程序DISP: ;数码管显示程序MOV R1,#100B ;延时计数器初始化MOV P2,A ;把按键值存入P2口MOV A,#07HANL A,P0 ;从P0口读取选定的行值MOV P0,A ;根据选定的行值输出相应的值ACALL DELAY ;调用延时程序MOV P0,#0FH ;关闭所有行DJNZ R1,$ ;当延时计数器不为0时,继续延时MOV A,#0FHMOV P0,A ;清除所有显示JMP LOOP ;跳转回主程序EXIT:MOV P2.7,1 ;在数码管的最后一位显示字符1SJMP EXIT ;无限循环DELAY: ;延时程序MOV R2,#75DMOV R3,#200D DELAY3:DJNZ R3,$DJNZ R2,DELAY2 RET```。

4×4矩阵键盘EDA设计

4×4矩阵键盘EDA设计
else if(ClkEN) ClkCount <= 0;
else ClkCount <= ClkCount + 1'b1;
end assign ClkEN = (ClkCount == CmpCnt); //Clock=50MHz时,ClkEN=2ms
2021/7/23
14
软件设计
/*产生键盘时钟使能信号*/
always @(posedge Clock)
begin
if(~nRST)
Cnt4 <= 2'd0;
else if(ClkEN)
begin
if(Clk4EN)
Cnt4 <= 2'd0;
else
Cnt4 <= Cnt4 + 1'b1;
end
end
assign Clk4EN = (Cnt4 == 2'b11) && ClkEN;
软件设计
/*产生消抖时钟使能信号*/
parameter CmpCnt = 100000;//消抖时钟分频系数=0.002*系统时钟频率
always @(posedge Clock)//系统时钟分频,将系统时钟时间用CLKEN 分出2ms begin
if(~nRST)(同步复位信号取反) ClkCount <= 0;
KeyVal <= 8'h09;
else if(nFlag[9])
KeyVal <= 8'h06;
19
2021/7/23
软件设计
else if(nFlag[10]) KeyVal <= 8'h03;
else if(nFlag[11])KeyVal <= 8'h0b;

4乘4矩阵键盘总结

4乘4矩阵键盘总结

|
39 //
|
40 //
|
41 // P X.0 ----------|------|-----|-----|
42 //
43 //************************************************************
44 // 扫描方法二: 06.8.15 添加 4X4 矩阵键盘线翻转识别法函数
0xe7,0xeb,0xed,0xee
58 //
|
|||
59 //
|
|||
60 // P X.3 ----------|
|||
61 //
|||
62 //
|||
63 // P X.2 ----------|------|
|
|
64 //
||
65 //
||
66 // P X.1 ----------|------|-----|
//计算识别码的算法,灵活性很大。
142
return ((~uc_Temp_1)+(~uc_Temp_2)); //返回识别码,识
143 一个按键,一共有 16 个识别码。
144
}
145
else
//否则依次将第二,第三,第四行拉低
146
{
147
uc_Temp_1>>=1;
01111111 00111111
|
67 //
|
68 //
|
69 // P X.0 ----------|------|-----|-----|
70 //
71
72 //*****************************************************************

4X4矩阵式键盘输入程序

4X4矩阵式键盘输入程序

4*4键盘程序readkeyboard:begin: acall key_onjnz delayajmp readkeyboard delay:acall delay10msacall key_onjnz key_numajmp beginkey_num:acall key_panl a,#0FFhjz beginacall key_ccodepush akey_off:acall key_onjnz key_offpop aretkey_on: mov a,#00horl a,#0fhmov p1,amov a,p1orl a,#0f0hcpl aretkey_p: mov r7,#0efhl_loop:mov a,r7mov p1,amov a,p1orl a,#0f0hmov r6,acpl ajz nextajmp key_cnext: mov a,r7jnb acc.7,errorrl amov r7,aajmp l_looperror:mov a,#00hretkey_c:mov r2,#00hmov r3,#00hmov a,r6mov r5,#04hagain1:jnb acc.0,out1rr ainc r2djnz r5, again1out1: inc r2mov a,r7mov r5,#04hagain2:jnb acc.4,out2rr ainc r3djnz r5,again2out2: inc r3mov a, r2swap aadd a,r3retkey_ccode:push aswap aanl a,#0fhdec arl a ;行号乘4rl amov r7,apop aanl a,#0fhdec aadd a,r7retdelay10ms:anl tmod,#0f0horl tmod,#01hmov th0,#0d8hmov tl0,#0f0hsetb tr0wait:jbc tf0,overajmp waitclr tr0over:ret单片机键盘设计(二)从电路或软件的角度应解决的问题软件消抖:如果按键较多,硬件消抖将无法胜任,常采用软件消抖。

单片机4×4矩阵键盘设计方案

单片机4×4矩阵键盘设计方案

1、设计原理(1)如图14.2所示,用单片机的并行口P3连接4×4矩阵键盘,并以单片机的P3.0-P3.3各管脚作输入线,以单片机的P3.4-P3.7各管脚作输出线,在数码管上显示每个按键“0-F”的序号。

(2)键盘中对应按键的序号排列如图14.1所示。

2、参考电路图14.2 4×4矩阵式键盘识别电路原理图3、电路硬件说明(1)在“单片机系统”区域中,把单片机的P3.0-P3.7端口通过8联拨动拨码开关JP3连接到“4×4行列式键盘”区域中的M1-M4,N1-N4端口上。

(2)在“单片机系统”区域中,把单片机的P0.0-P0.7端口连接到“静态数码显示模块”区域中的任何一个a-h端口上;要求:P0.0对应着a,P0.1对应着b,……,P0.7对应着h。

4、程序设计内容(1)4×4矩阵键盘识别处理。

(2)每个按键都有它的行值和列值,行值和列值的组合就是识别这个按键的编码。

矩阵的行线和列线分别通过两并行接口和CPU通信。

键盘的一端(列线)通过电阻接VCC,而接地是通过程序输出数字“0”实现的。

键盘处理程序的任务是:确定有无键按下,判断哪一个键按下,键的功能是什么?还要消除按键在闭合或断开时的抖动。

两个并行口中,一个输出扫描码,使按键逐行动态接地;另一个并行口输入按键状态,由行扫描值和回馈信号共同形成键编码而识别按键,通过软件查表,查出该键的功能。

5、程序流程图(如图14.3所示)6、汇编源程序;;;;;;;;;;定义单元;;;;;;;;;;COUNT EQU 30H;;;;;;;;;;入口地址;;;;;;;;;;ORG 0000HLJMP STARTORG 0003HRETIORG 000BHRETIORG 0013HRETIORG 001BHRETIORG 0023HRETIORG 002BHRETI;;;;;;;;;;主程序入口;;;;;;;;;;ORG 0100HSTART: LCALL CHUSHIHUALCALL PANDUANLCALL XIANSHILJMP START;;;;;;;;;;初始化程序;;;;;;;;;;CHUSHIHUA: MOV COUNT,#00HRET;;;;;;;;;;判断哪个按键按下程序;;;;;;;;;;PANDUAN: MOV P3,#0FFHCLR P3.4MOV A,P3ANL A,#0FHJZ SW1LCALL DELAY10MS JZ SW1MOV A,P3ANL A,#0FHCJNE A,#0EH,K1 MOV COUNT,#0 LJMP DKK1: CJNE A,#0DH,K2 MOV COUNT,#4 LJMP DKK2: CJNE A,#0BH,K3 MOV COUNT,#8 LJMP DKK3: CJNE A,#07H,K4 MOV COUNT,#12K4: NOPLJMP DKSW1: MOV P3,#0FFH CLR P3.5MOV A,P3ANL A,#0FHJZ SW2LCALL DELAY10MS JZ SW2MOV A,P3ANL A,#0FHCJNE A,#0EH,K5 MOV COUNT,#1 LJMP DKK5: CJNE A,#0DH,K6 MOV COUNT,#5 LJMP DKK6: CJNE A,#0BH,K7 MOV COUNT,#9 LJMP DKK7: CJNE A,#07H,K8 MOV COUNT,#13K8: NOPLJMP DKSW2: MOV P3,#0FFH CLR P3.6MOV A,P3ANL A,#0FHJZ SW3LCALL DELAY10MS JZ SW3MOV A,P3ANL A,#0FHCJNE A,#0EH,K9 MOV COUNT,#2 LJMP DKK9: CJNE A,#0DH,KA MOV COUNT,#6 LJMP DKKA: CJNE A,#0BH,KB MOV COUNT,#10 LJMP DKKB: CJNE A,#07H,KC MOV COUNT,#14 KC: NOPLJMP DKSW3: MOV P3,#0FFH CLR P3.7MOV A,P3ANL A,#0FHJZ SW4LCALL DELAY10MSJZ SW4MOV A,P3ANL A,#0FHCJNE A,#0EH,KDMOV COUNT,#3LJMP DKKD: CJNE A,#0DH,KE MOV COUNT,#7LJMP DKKE: CJNE A,#0BH,KF MOV COUNT,#11 LJMP DKKF: CJNE A,#07H,KG MOV COUNT,#15KG: NOPLJMP DKSW4: LJMP PANDUAN DK: RET ;;;;;;;;;;显示程序;;;;;;;;;; XIANSHI: MOV A,COUNTMOV DPTR,#TABLEMOVC A,@A+DPTRMOV P0,ALCALL DELAYSK: MOV A,P3ANL A,#0FHXRL A,#0FHJNZ SKRET;;;;;;;;;;10ms延时程序;;;;;;;;;;DELAY10MS: MOV R6,#20D1: MOV R7,#248DJNZ R7,$DJNZ R6,D1RET;;;;;;;;;;200ms延时程序;;;;;;;;;;DELAY: MOV R5,#20LOOP: LCALL DELAY10MSDJNZ R5,LOOPRET;;;;;;;;;;共阴码表;;;;;;;;;;TABLE: DB 3FH,06H,5BH,4FH,66H,6DH,7DH,07H DB 7FH,6FH,77H,7CH,39H,5EH,79H,71H;;;;;;;;;;结束标志;;;;;;;;;;END7、C语言源程序#includeunsigned char code table[]={0x3f,0x66,0x7f,0x39,0x06,0x6d,0x6f,0x5e,0x5b,0x7d,0x77,0x79,0x4f,0x07,0x7c,0x71};void main(void){ unsigned char i,j,k,key;while(1){ P3=0xff; //给P3口置1//P3_4=0; //给P3.4这条线送入0//i=P3;i=i&0x0f; //屏蔽低四位//if(i!=0x0f) //看是否有按键按下//{ for(j=50;j>0;j--) //延时//for(k=200;k>0;k--);if(i!=0x0f) //再次判断按键是否按下//{ switch(i) //看是和P3.4相连的四个按键中的哪个// { case 0x0e:key=0;break;case 0x0d:key=1;break;case 0x0b:key=2;break;case 0x07:key=3;break;}P0=table[key]; //送数到P0口显示//}}P3=0xff;P3_5=0; //读P3.5这条线//i=P3;i=i&0x0f; //屏蔽P3口的低四位//if(i!=0x0f) //读P3.5这条线上看是否有按键按下// { for(j=50;j>0;j--) //延时//for(k=200;k>0;k--);i=P3; //再看是否有按键真的按下//i=i&0x0f;if(i!=0x0f){ switch(i) //如果有,显示相应的按键//{ case 0x0e:key=4;break;case 0x0d:key=5;break;case 0x0b:key=6;break;case 0x07:key=7;break;}P0=table[key]; //送入P0口显示//}}P3=0xff;P3_6=0; //读P3.6这条线上是否有按键按下// i=P3;i=i&0x0f;if(i!=0x0f){ for(j=50;j>0;j--)for(k=200;k>0;k--);i=P3;i=i&0x0f;if(i!=0x0f){ switch(i){ case 0x0e:key=8;break;case 0x0d:key=9;break;case 0x0b:key=10;break;case 0x07:key=11;break;}P0=table[key];}}P3=0xff;P3_7=0; //读P3.7这条线上是否有按键按下//i=P3;i=i&0x0f;if(i!=0x0f){ for(j=50;j>0;j--) for(k=200;k>0;k--); i=P3;i=i&0x0f;if(i!=0x0f){ switch(i){ case 0x0e:key=12;break;case 0x0d:key=13;break;case 0x0b:key=14;break;case 0x07:key=15;break;}P0=table[key];}}}}8、注意事项在硬件电路中,要把8联拨动拨码开关JP2拨下,把8联拨动拨码开关JP3拨上去。

机电单片机课程设计--4乘4矩阵键盘-汇编语言

机电单片机课程设计--4乘4矩阵键盘-汇编语言

目录1 引言 (2)2 4×4矩阵键盘控制LED工作原理及软硬件设计、仿真调试 (2)2.1 4×4矩阵式键盘识别显示系统概述 (2)2.2 4×4矩阵式键盘原理 (3)2.3 4×4矩阵式键盘控制LED显示方法 (3)2.4 电路设计及电路图 (3)2.5 4×4矩阵式键盘软件编程 (6)2.6 4×4矩阵式键盘软件仿真调试分析 (9)3 结论 (10)4参考文献 (10)1 引言随着现代科技日新月异的发展,作为新兴产业,单片机的应用越来越广。

单片机以其体积小、重量轻、功能强大、功耗低等特点而备受青睐。

键盘作为一种最为普遍的输入工具在单片机项目应用上显得尤为重要。

用MCS51系列的单片机并行口P1接4×4矩阵键盘,以P1.0-P1.3 作输入线,以P1.4-P1.7作输出线;在数码管上显示每个按键的0-F序号。

2 4×4矩阵键盘控制LED工作原理及软硬件设计、仿真调试2.1 4×4矩阵式键盘识别显示系统概述矩阵式键盘模式以4个端口连接控制4*4个按键,实时在LED数码管上显示按键信息。

显示按键信息,省下了很多的I/O端口为他用,相反,独立式按键虽编程简单,但占用I/O口资源较多,不适合在按键较多的场合应用。

矩阵式键盘简介:矩阵式键盘又称行列键盘,它是用4条I/O线作为行线,4条I/O线作为列线组成的键盘。

在行线和列线的每个交叉点上设置一个按键。

这样键盘上按键的个数就为4*4个。

这种行列式键盘结构能有效地提高单片机系统中I/O口的利用率。

最常见的键盘布局如图1所示。

一般由16个按键组成,在单片机中正好可以用一个P 口实现16个按键功能,这也是在单片机系统中最常用的形式,本设计就采用这个键盘模式。

2.2 4×4矩阵式键盘原理在占用相同的I/O端口的情况下,行列式键盘的接法会比独立式接法允许的按键数量多。

数码管显示4×4键盘矩阵按键实验

数码管显示4×4键盘矩阵按键实验

5、4×4键盘矩阵按键实验一、实验目的及要求键盘实质上是一组按键开关的集合。

通常,键盘开关利用了机械触点的合、断作用。

键的闭合与否,反映在行线输出电压上就是呈高电平或低电平,如果高电平表示键断开,低电平则表示键闭合,反之也可。

通过对行线电平高低状态的检测,便可确认按键按下与否。

为了确保CPU对一次按键动作只确认一次按键有效,还必须消除抖动。

当按键较多时会占用更多的控制器端口,为减少对端口的占用,可以使用行列式键盘接口,本实验中采用的4×4键盘矩阵可以大大减少对单片机的端口占用,但识别按键的代码比独立按键的代码要复杂一些。

在识别按键时使用了不同的扫描程序代码,程序运行时LED灯组会显示相应按键的键值0~15的二进制数。

本实验中P2端口低4位连接是列线,高4位连接的是行线。

二、实验原理(图)三、实验设备(环境):1、电脑一台2、STC-ISP(V6.85I)烧写应用程序3、Keil应用程序四、实验内容(算法、程序、步骤和方法):#include<STC15F2K60S2.h> //此文件中定义了STC15系列的一些特殊功能寄存器#include"intrins.h"#define uint unsigned int#define uchar unsigned charuchar code dsy_code[]={0x01,0x02,0x03,0x04,0x05,0x06,0x07,0x08,0x09,0x0A,0x0B,0x0C,0x0D,0x0E,0x0 F,0xff};uchar Pre_keyno=16,keyno=16;void delayMS(char x){uchar i;while(x--)for(i=0;i<120;i++) ;}void keys_scan(){uchar tmp;P2=0x0f;delayMS(5);tmp=P2^0x0f;switch(tmp){case 1:keyno=0;break;case 2:keyno=1;break;case 4:keyno=2;break;case 8:keyno=3;break;default:keyno=16;}P2=0xf0;delayMS(5);tmp=P2>>4^0x0f;switch(tmp){case 1:keyno+=0;break;case 2:keyno+=4;break;case 4:keyno+=8;break;case 8:keyno+=12;break;}}main(){P0=0x00;while(1){P2=0xf0;if(P2!=0xf0)keys_scan();if(Pre_keyno!=keyno){P0=~dsy_code[keyno];Pre_keyno=keyno;}delayMS(50);}}五、实验结论(结果):本实验实现了XXX功能,核心算法采用了XXX的方式,达到了预期目的。

4×4矩阵键盘识别技术

4×4矩阵键盘识别技术

实验课题:4×4矩阵键盘识别技术一实验目的1.熟悉和掌握AT89S51单片机相关的功能2.了解矩阵式键盘的内部结构,掌握至少一种常用的按键识别的方法3.利用AT89S51单片机和设计一个4×4矩阵键盘控制。

4.掌握子程序结构和子程序实际的基本知识。

二实验原理1. 4×4矩阵键盘的序列排列如图1-1,图1-12.如图1-2所示,用AT89S51的并行口P1接4×4矩阵键盘,以P1.0―P1.3作输入线,以p1.4-P1.7作输出线,在数码管上显示每个按键的“0-F”序号.每个按键有它的行值和列值,行值和列值的组合就是识别这个按键的编码。

矩阵的行线和列线分别通过两并行接口和CPU通信。

每个按键的状态同样需变成数字量“0”和“1”,开关的一端(列线)通过电阻接VCC,而接地是通过程序输出数字“0”实现的。

键盘处理程序的任务是:确定有无键按下,判断哪一个键按下,键的功能是什么;还要消除按键在闭合或断开时的抖动。

两个并行口中,一个输出扫描码,使按键逐行动态接地,另一个并行口输入按键状态,由行扫描值和回馈信号共同形成键编码而识别按键,通过软件查表,查出该键的功能。

3.程序框图三实验原理图四实验代码#include<AT89X51.H> unsignedcharcodetable[]={0x3f,0x06,0x5b,0x4f, 0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71}; unsignedchartemp;unsignedcharkey;unsignedchari,j;voidmain(void){while(1){P3=0xff;P3_4=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp&0x0f;if(temp!=0x0f) {temp=P3;temp=temp&0x0f;switch(temp){case0x0e:key=7;break;case0x0d:key=8;break;case0x0b:key=9;break;case0x07:key=10;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp&0x0f;while(temp!=0x0f){temp=P3;temp=temp&0x0f;}}}P3=0xff;P3_5=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3; temp=temp&0x0f; switch(temp){case0x0e:key=4;break;case0x0d:key=5;break;case0x0b:key=6;break;case0x07:key=11;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp&0x0f;while(temp!=0x0f){temp=P3;temp=temp&0x0f;}}}P3=0xff;P3_6=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--) for(j=200;j>0;j--); temp=P3;temp=temp&0x0f; if(temp!=0x0f) {temp=P3;temp=temp&0x0f; switch(temp){ case0x0e:key=1;break;case0x0d:key=2;break;case0x0b:key=3;break;case0x07:key=12;break;}temp=P3;P1_0=~P1_0;P0=table[key]; temp=temp&0x0f; while(temp!=0x0f) {temp=P3;temp=temp&0x0f; }}}P3=0xff;P3_7=0;temp=P3;temp=temp&0x0f; if(temp!=0x0f) {for(i=50;i>0;i--) for(j=200;j>0;j--); temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3;temp=temp&0x0f;switch(temp){case0x0e:key=0;break; case0x0d:key=13;break;case0x0b:key=14;break;case0x07:key=15;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp&0x0f;while(temp!=0x0f){temp=P3;temp=temp&0x0f;}}}}}五实验小结1.通过本次试验熟练的掌握了AT89S51单片机相关的功能。

4×4矩阵键盘在单片机中的应用(Proteus)

4×4矩阵键盘在单片机中的应用(Proteus)

4×4矩阵键盘原理及其在单片机中的简单应用基于Proteus仿真1、4×4矩阵键盘的工作原理如下图所示,4×4矩阵键盘由4条行线和4条列线组成,行线接P3.0-P3.3,列线接P3.4-P3.7,按键位于每条行线和列线的交叉点上。

按键的识别可采用行扫描法和线反转法,这里采用简单的线反转法,只需三步。

第一步,执行程序使X0~X3均为低电平,此时读取各列线Y0~Y3的状态即可知道是否有键按下。

当无键按下时,各行线与各列线相互断开,各列线仍保持为高电平;当有键按下时,则相应的行线与列线通过该按键相连,该列线就变为低电平,此时读取Y0Y1Y2Y3的状态,得到列码。

第二步,执行程序使Y0~Y3均为低电平,当有键按下时,X0~X3中有一条行线为低电平,其余行线为高电平,读取X0X1X2X3的状态,得到行码。

第三步,将第一步得到的列码和第二步得到的行码拼合成被按键的位置码,即Y0Y1Y2Y3X0X1X2X3(因为行线和列线各有一条为低电平,其余为高电平,所以位置码低四位和高四位分别只有一位低电平,其余为高电平)。

当0键按下时,行线X0和列线Y0为低电平,其余行列线为高电平,于是可以得到0键的位置码Y0Y1Y2Y3X0X1X2X3为0111 0111,即0X77。

当5键按下时,行线X1和列线Y1为低电平,其余行列线为高电平,于是可得到5键的位置码Y0Y1Y2Y3X0X1X2X3为1011 1011,即0XBB。

全部矩阵键盘的位置码如下:2、4×4矩阵键盘在单片机的简单应用举例(一)如下图所示,运行程序时,按下任一按键,数码管会显示它在矩阵键盘上的序号0~F,并且蜂鸣器发出声音,模拟按键的声音。

此处采用线反转法识别按键。

C程序如下:#include<reg51.h>#define uchar unsigned char#define uint unsigned intsbit buzzer=P1^0;uchar code dis[]= //0~9,A~F的共阳显示代码{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0X88,0X83,0XC6,0XA1,0X86,0X8E};uchar code tab[]= //矩阵键盘按键位置码{0x77,0xb7,0xd7,0xe7,0x7b,0xbb,0xdb,0xeb,0x7d,0xbd,0xdd,0xed,0x7e,0xbe,0xde,0xee};void delay(uint x) //延时函数{uchar i;while(x--)for(i=0;i<120;i++);}uchar scan() //矩阵键盘扫描函数,得到按键号,采用线反转法{uchar a,b,c,i;P3=0XF0; //P3口输出11110000a=P3; //读取列码delay(10); //防抖延时10msP3=0X0F; //P3口输出00001111b=P3; //读取行码c=a+b; //得到位置码for(i=0;i<16;i++)if(c==tab[i])return i; //查表得到按键序号并返回return -1; //无按键,则返回-1}void beep() //蜂鸣器发出声音,模拟按键的声音{ uchar i;for(i=0;i<100;i++){buzzer=~buzzer;delay(1);}buzzer=0;}void main(){uchar key;buzzer=0; //关闭蜂鸣器while(1){key=scan(); //得到按键号if(key!=-1) //有按键则显示,并且蜂鸣器发出声音{P0=dis[key];beep();delay(100);}}}Proteus仿真运行结果如下:3、4×4矩阵键盘在单片机的简单应用举例(二)如下图所示,运行程序时,按下的按键键值越大,点亮的LED灯越多,例如,按下1号键时,点亮一只LED灯,按下2号键时,点亮两只LED灯,按下16号键时,点亮全部LED 灯。

4x4矩阵键盘(仅供参考)

4x4矩阵键盘(仅供参考)
if(rPDATF&(1<<6)==0);
{
if(rPDATG&(1<<4)==0) keyvalue=2;
else if(rPDATG&(1<<5)==0) keyvalue=6;
else if(rPDATG&(1<<5)==0) keyvalue=7;
else if(rPDATG&(1<<6)==0) keyvalue=11;
else if(rPDATG&(1<<6)==0) keyvalue=15;
}
else if(rPDATF&(1<<8)==0);
longdelay(3);
if(rPDATF&(1<<8)==0);
{ if(rPDATG&(1<<4)==0) keyvalue=4;
rPUPG=rpupG&0x0f; //使能GPG4~GPG7内部上拉电阻
while(1)
{ (rPDATG&0x00)|(0x0e<<4);delay(1);
(rPDATG&0x00)|(0x0d<<4);delay(1);
if(rPDATF&(1<<5)==0); //如果GPF5为低
longdelay(3); //延时
if(rPDATF&(1<<5)==0); //如果GPF5为低
{if(rPDATG&(1<<4)==0) keyvalue=1; //判断GPG4,若为低,则按键为1号键

4乘4矩阵键盘检测

4乘4矩阵键盘检测
#include <reg51.h>//包含头文件
#define uchar unsigned char
#define uint unsigned int
sbit p2_7 = P2^7 ;
unsigned char const table[]={
0x06,0x5b,0x3f,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,
{
uchar cord_h,cord_l;//行列值
P1=0x0f; //行线输出全为0
cord_h=P1&0x0f; //读入列线值
if(cord_h!=0x0f) //先检测有无按键按下
{
delay(100); //去抖
if(cord_h!=0x0f)
{
cord_h=P1&0x0f; //读入列线值
temp=table[13];
break;//d
case 0xeb:
temp=table[14];
break;//e
case 0xe7:
temp=table[15];
break;//f
}
if (p2_7==0)//确认键
{
P0 = temp;
}
}
}
uchar keyscan(void)//键盘扫描函数
0x77,0x7c,0x39,0x5e,0x79,0x71};//0-F
uchar temp;
uchar keyscan(void);
void delay(uint i);
void main()
{
uchar key;
P0=0x049;//1数码管亮按相应的按键,会显示按键上的字符

4 4矩阵键盘(未消抖)verilog

4 4矩阵键盘(未消抖)verilog

4*4矩阵键盘(未消抖):module Matrix_keyboard(clk,in_s,out_s,num);//定义模块端口信息input clk;input [3:0] in_s;output [3:0] out_s;output [4:0] num;//定义输出信号类型及局部变量reg [4:0] num;reg [1:0] cnt = 0;reg [1:0] tmp = 0;reg [3:0] o_ut_st = 0;wire [7:0] dsample;//将扫描输出和输入信号级联,得到矩阵扫描结果assign dsample = {o_ut_st, in_s};assign out_s = o_ut_st;//产生按钮矩阵的列扫描信号always @(posedge clk)begincnt <= cnt + 1'b1;case (cnt)2'b00: o_ut_st <= 4'b1000;2'b01: o_ut_st <= 4'b0100;2'b10: o_ut_st <= 4'b0010;2'b11: o_ut_st <= 4'b0001;endcaseend//根据按钮的列扫描信号和行输入信号判断按钮是否被按下always @(posedge clk)begin//如果无按钮按下,定义num=16为无效状态if (in_s == 4'b0000)beginif (tmp == 3)beginnum <= 16; //无按键输入,输出16tmp <= 0;endelsebeginnum <= num;tmp <= tmp + 1'b1; //扫描周期,3个时钟周期endendelsebegintmp <= 0;case (dsample)//第1列扫描结果8'b1000_0001: num <= 0;8'b1000_0010: num <= 1;8'b1000_0100: num <= 2;8'b1000_1000: num <= 3;//第2列扫描结果8'b0100_0001: num <= 4;8'b0100_0010: num <= 5;8'b0100_0100: num <= 6;8'b0100_1000: num <= 7;//第3列扫描结果8'b0010_0001: num <= 8;8'b0010_0010: num <= 9;8'b0010_0100: num <= 10;8'b0010_1000: num <= 11;//第4列扫描结果8'b0001_0001: num <= 12;8'b0001_0010: num <= 13;8'b0001_0100: num <= 14;8'b0001_1000: num <= 15;endcaseendendendmodule独立按键消抖程序:module Btn_without_shake(Clk_50MHz,PB_UP,PB_Out,count_sel); //定义模块端口信息input Clk_50MHz; //模块时钟50MHzinput PB_UP; //按钮输入output PB_Out; //去抖后按钮输出output [1:0] count_sel; //计数器输出//定义输出信号类型及局部变量reg [19:0] count_high = 0; //按钮输入高电平计数器reg [19:0] count_low = 0; //按钮输入低电平计数器reg PB_reg = 0;reg [1:0] count_sel_reg = 0;//输出赋值assign PB_Out = PB_reg;assign count_sel = count_sel_reg;//对输入进行采样,计数always @(posedge Clk_50MHz)if(PB_UP == 1'b0)count_low <= count_low + 1'b1;elsecount_low <= 20'h0_0000;always @(posedge Clk_50MHz)if(PB_UP == 1'b1)count_high <= count_high + 1'b1;elsecount_high <= 20'h0_0000;//防抖输出always @(posedge Clk_50MHz)if(count_high == 20'h7_FFFF) //判断高电平信号是否符合输出条件10msPB_reg <= 1'b1; //如果符合条件,则防抖输出高电平elseif(count_low == 20'h7_FFFF) //判断低电平信号是否符合输出条件10msPB_reg <= 1'b0; //如果符合条件,则防抖输出低电平elsePB_reg <= PB_reg;//使用去抖输出PB_reg控制count_sel计数always @(posedge PB_reg)count_sel_reg <= count_sel_reg + 1'b1;endmodule初学,参考书上的《Verilog HDL程序设计与实践》,准备用状态机做一下矩阵键盘,恩,坛子里也有,不过还是自己尝试一下,坛里老牛很多呀!。

4x4矩阵键盘扫描原理

4x4矩阵键盘扫描原理

4x4矩阵键盘扫描原理
4x4矩阵键盘扫描原理是一种常用的键盘扫描方法,也称为矩阵键盘扫描。

它可以将多个按键连接在一起并使用较少的引脚来检测按键的状态。

4x4矩阵键盘由4行和4列组成,共有16个按键。

通常使用单片机或电路来进行扫描,以下是简要的原理:
1. 行扫描:首先,将行引脚设置为输出,同时将列引脚设置为输入,并将其上拉或下拉。

所有行引脚中只有一个为低电平,其余为高电平。

然后逐行检测按键状态。

2. 列检测:对于每一行,将对应的行引脚置为低电平后,检测列引脚的电平状态。

如果有按键按下,则相应的列引脚会变为低电平。

通过读取列引脚的状态,可以确定按键的位置。

3. 组合键:由于只能一次检测一行,因此当同时按下多个按键时,可能会导致误检。

为了解决这个问题,可以在检测到按键按下时,延迟一段时间,并再次检测按键的状态。

如果在第二次检测时仍然检测到按键按下,则确认按键有效。

4. 反向扫描:为了检测按键的释放状态,可以将行引脚设置为输入,列引脚设置为输出,并将其置为低电平。

然后逐列检测行引脚的电平状态,如果有按键释放,则相应的行引脚会变为高电平。

通过不断地循环扫描所有的行和列,可以实时检测按键的状态,并根据需要进行相应的处理。

44矩阵键盘课程设计

44矩阵键盘课程设计

4 4矩阵键盘课程设计一、课程目标知识目标:1. 学生能够理解4x4矩阵键盘的基本原理,掌握其电路连接方式和扫描原理。

2. 学生能够运用所学知识,设计并搭建一个简单的4x4矩阵键盘电路。

3. 学生了解矩阵键盘在嵌入式系统中的应用和重要性。

技能目标:1. 学生能够运用编程软件(如Arduino)编写程序,实现对4x4矩阵键盘的扫描和按键识别。

2. 学生能够运用调试工具,对矩阵键盘电路进行故障排查和优化。

3. 学生具备团队协作能力,共同完成矩阵键盘电路设计和程序编写。

情感态度价值观目标:1. 学生通过动手实践,培养对电子技术和编程的兴趣,增强学习动力。

2. 学生在团队合作中,学会沟通、协作、分享,培养团队精神和责任感。

3. 学生认识到科技发展对社会进步的重要性,激发为我国科技事业贡献力量的志向。

本课程针对高中年级学生,结合电子技术和编程知识,以实用性为导向,旨在培养学生的动手实践能力和创新精神。

课程内容紧密联系课本知识,通过设计4x4矩阵键盘电路,使学生在实践中掌握相关原理和方法。

课程目标具体、可衡量,为后续教学设计和评估提供明确方向。

二、教学内容1. 矩阵键盘基础知识:介绍矩阵键盘的原理、电路连接方式及其在嵌入式系统中的应用。

- 相关章节:课本第三章第二节“矩阵键盘及其应用”2. 4x4矩阵键盘电路设计:讲解如何搭建4x4矩阵键盘电路,包括硬件连接、电路图绘制等。

- 相关章节:课本第三章第三节“矩阵键盘电路设计”3. 矩阵键盘编程:介绍如何使用Arduino编程软件编写程序,实现对4x4矩阵键盘的扫描和按键识别。

- 相关章节:课本第四章第一节“Arduino编程基础”及第四节“矩阵键盘编程实例”4. 矩阵键盘电路调试与优化:教授学生如何运用调试工具进行故障排查,以及如何对电路和程序进行优化。

- 相关章节:课本第五章“电路调试与优化”5. 团队合作与展示:学生分组进行项目实践,共同完成矩阵键盘电路设计与程序编写,并进行成果展示。

数码管显示4×4矩阵键盘

数码管显示4×4矩阵键盘

2013年1月1.课程设计目的1.1巩固和加深对单片机原理和接口技术知识的理解;1.2培养根据课题需要选学参考书籍、查阅手册和文献资料的能力;1.3学会方案论证的比较方法,拓宽知识,初步掌握工程设计的基本方法;1.4掌握常用仪器、仪表的正确使用方法,学会软、硬件的设计和调试方法;1.5能按课程设计的要求编写课程设计报告,能正确反映设计和实验成果,能用计算机绘制电路图和流程图。

2.课程设计要求单片机的P1口的P1.0~P1.7连接4×4矩阵键盘,P0口控制一只数码管,当4×4矩阵键盘中的某一按键按下时,数码管上显示对应的键号。

例如,1号键按下时,数码管显示“1”, 14号键按下时,数码管显示“E”等等。

3.硬件设计3.1 设计思想分析本任务的要求,使设计能够完成当4*4矩阵键盘中的某一按键按下时,数码管上显示对应的键盘号。

则本系统主要由以下几大模块构成:显示模块,共阴极LED数码管;输入模块,4*4矩阵键盘;3.2主要元器件介绍矩阵键盘又称为行列式键盘,它是用4条I/O线作为行线,4条I/O线作为列线组成的键盘。

在行线和列线的每一个交叉点上,设置一个按键。

这样键盘中按键的个数是4×4个。

这种行列式键盘结构能够有效地提高单片机系统中I/O 口的利用率。

数码管不同位显示的时间间隔可以通过调整延时程序的延时长短来完成。

数码管显示的时间间隔也能够确定数码管显示时的亮度,若显示的时间间隔长,显示时数码管的亮度将亮些,若显示的时间间隔短,显示时数码管的亮度将暗些。

若显示的时间间隔过长的话,数码管显示时将产生闪烁现象。

所以,在调整显示的时间间隔时,即要考虑到显示时数码管的亮度,又要数码管显示时不产生闪烁现象。

4.1 设计思想按键采用线反转法先把列线置成低电平,行线置成输入状态,读行线;再把行线置成低电平,列线输入状态,读列线。

当有键按下时,由两次所读状态即可确定所按键的位置,不需扫描,键盘响应速度大大加快。

4×4矩阵式键盘识别技术

4×4矩阵式键盘识别技术

14.4×4矩阵式键盘识别技术1.实验任务如图4.14.2所示,用AT89S51的并行口P1接4×4矩阵键盘,以P1.0-P1.3作输入线,以P1.4-P1.7作输出线;在数码管上显示每个按键的“0-F”序号。

对应的按键的序号排列如图4.14.1所示错误!48C159D26AE37BF图4.14.12.硬件电路原理图图4.14.23.系统板上硬件连线(1.把“单片机系统“区域中的P3.0-P3.7端口用8芯排线连接到“4X4行列式键盘”区域中的C1-C4 R1-R4端口上;(2.把“单片机系统”区域中的P0.0/AD0-P0.7/AD7端口用8芯排线连接到“四路静态数码显示模块”区域中的任一个a-h端口上;要求:P0.0/AD0对应着a,P0.1/AD1对应着b,……,P0.7/AD7对应着h。

4.程序设计内容(1.4×4矩阵键盘识别处理(2.每个按键有它的行值和列值,行值和列值的组合就是识别这个按键的编码。

矩阵的行线和列线分别通过两并行接口和CPU通信。

每个按键的状态同样需变成数字量“0”和“1”,,而接地是通过程序输出数开关的一端(列线)通过电阻接VCC字“0”实现的。

键盘处理程序的任务是:确定有无键按下,判断哪一个键按下,键的功能是什么;还要消除按键在闭合或断开时的抖动。

两个并行口中,一个输出扫描码,使按键逐行动态接地,另一个并行口输入按键状态,由行扫描值和回馈信号共同形成键编码而识别按键,通过软件查表,查出该键的功能。

5.程序框图错误!P3=FFH,P3.0=0有键按下吗?延时10ms真得有键按下吗?根据当前状态识别按键P3=FFH,P3.1=0有键按下吗?延时10ms真得有键按下吗?根据当前状态识别按键P3=FFH,P3.2=0有键按下吗?延时10ms真得有键按下吗?根据当前状态识别按键P3=FFH,P3.3=0有键按下吗?延时10ms真得有键按下吗?根据当前状态识别按键图4.14.3 6.汇编源程序KEYBUF EQU 30HORG 00HSTART: MOV KEYBUF,#2WAIT:MOV P3,#0FFHCLR P3.4MOV A,P3ANL A,#0FHXRL A,#0FHLCALL DELY10MS MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY1MOV A,P3ANL A,#0FHCJNE A,#0EH,NK1 MOV KEYBUF,#0 LJMP DK1NK1: CJNE A,#0DH,NK2 MOV KEYBUF,#1 LJMP DK1NK2: CJNE A,#0BH,NK3 MOV KEYBUF,#2 LJMP DK1NK3: CJNE A,#07H,NK4 MOV KEYBUF,#3 LJMP DK1NK4: NOPDK1:MOV A,KEYBUFMOV DPTR,#TABLE MOVC A,@A+DPTR MOV P0,ADK1A: MOV A,P3ANL A,#0FHJNZ DK1A NOKEY1:MOV P3,#0FFHCLR P3.5MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY2LCALL DELY10MS MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY2MOV A,P3ANL A,#0FHCJNE A,#0EH,NK5 MOV KEYBUF,#4 LJMP DK2NK5: CJNE A,#0DH,NK6 MOV KEYBUF,#5 LJMP DK2NK6: CJNE A,#0BH,NK7 MOV KEYBUF,#6 LJMP DK2NK7: CJNE A,#07H,NK8 MOV KEYBUF,#7 LJMP DK2NK8: NOPDK2:MOV A,KEYBUFMOV DPTR,#TABLE MOVC A,@A+DPTR MOV P0,ADK2A: MOV A,P3ANL A,#0FHXRL A,#0FHJNZ DK2ANOKEY2:MOV P3,#0FFHCLR P3.6MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY3LCALL DELY10MS MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY3MOV A,P3ANL A,#0FHCJNE A,#0EH,NK9 MOV KEYBUF,#8LJMP DK3NK9: CJNE A,#0DH,NK10 MOV KEYBUF,#9LJMP DK3NK10: CJNE A,#0BH,NK11 MOV KEYBUF,#10 LJMP DK3NK11: CJNE A,#07H,NK12 MOV KEYBUF,#11 LJMP DK3NK12: NOPDK3:MOV A,KEYBUFMOV DPTR,#TABLE MOVC A,@A+DPTR MOV P0,ADK3A: MOV A,P3ANL A,#0FHXRL A,#0FHJNZ DK3ANOKEY3:MOV P3,#0FFHCLR P3.7MOV A,P3ANL A,#0FHXRL A,#0FHJZ NOKEY4LCALL DELY10MS MOV A,P3ANL A,#0FHXRL A,#0FHMOV A,P3ANL A,#0FHCJNE A,#0EH,NK13 MOV KEYBUF,#12 LJMP DK4NK13: CJNE A,#0DH,NK14 MOV KEYBUF,#13 LJMP DK4NK14: CJNE A,#0BH,NK15 MOV KEYBUF,#14 LJMP DK4NK15: CJNE A,#07H,NK16 MOV KEYBUF,#15 LJMP DK4NK16: NOPDK4:MOV A,KEYBUFMOV DPTR,#TABLE MOVC A,@A+DPTR MOV P0,ADK4A: MOV A,P3ANL A,#0FHXRL A,#0FHJNZ DK4ANOKEY4:LJMP WAITDELY10MS:D1: MOV R7,#248DJNZ R7,$DJNZ R6,D1RETTABLE: DB 3FH,06H,5BH,4FH,66H,6DH,7DH,07HDB 7FH,6FH,77H,7CH,39H,5EH,79H,71HEND7.C语言源程序#include <AT89X51.H>unsigned char code table[]={0x3f,0x06,0x5b,0x4f, 0x66,0x6d,0x7d,0x07, 0x7f,0x6f,0x77,0x7c, 0x39,0x5e,0x79,0x71}; unsigned char temp;unsigned char key;unsigned char i,j;void main(void){while(1){P3=0xff;P3_4=0;temp=P3;temp=temp & 0x0f;if (temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp & 0x0f;if (temp!=0x0f){temp=P3;temp=temp & 0x0f; switch(temp){case 0x0e:key=7;break;case 0x0d:key=8;break;case 0x0b:key=9;break;case 0x07:key=10;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp & 0x0f;while(temp!=0x0f){temp=P3;temp=temp & 0x0f; }}}P3=0xff;P3_5=0;temp=P3;temp=temp & 0x0f;if (temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp & 0x0f;if (temp!=0x0f){temp=P3;temp=temp & 0x0f;switch(temp){case 0x0e:key=4;break;case 0x0d:key=5;break;case 0x0b:key=6;break;case 0x07:key=11;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp & 0x0f;while(temp!=0x0f){temp=P3;temp=temp & 0x0f; }}}P3=0xff;P3_6=0;temp=P3;temp=temp & 0x0f;if (temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp & 0x0f;if (temp!=0x0f){temp=P3;temp=temp & 0x0f; switch(temp){case 0x0e:key=1;break;case 0x0d:key=2;break;case 0x0b:key=3;break;case 0x07:key=12;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp & 0x0f; while(temp!=0x0f){temp=temp & 0x0f; }}}P3=0xff;P3_7=0;temp=P3;temp=temp & 0x0f;if (temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp & 0x0f;if (temp!=0x0f){temp=P3;temp=temp & 0x0f;switch(temp){case 0x0e:key=0;break;case 0x0d:key=13;break;key=14;break;case 0x07:key=15;break;}temp=P3;P1_0=~P1_0;P0=table[key];temp=temp & 0x0f;while(temp!=0x0f){temp=P3;temp=temp & 0x0f; }}}}}。

013、4×4矩阵式键盘识别技术

013、4×4矩阵式键盘识别技术

13.4×4矩阵式键盘识别技术1.实验任务如图4.13.2所示,用AT89S51的并行口P1接4×4矩阵键盘,以P1.0-P1.3作输入线,以P1.4-P1.7作输出线;在数码管上显示每个按键的“0-F”序号。

对应的按键的序号排列如图4.13.1所示图4.13.12.硬件电路原理图图4.13.23.系统板上硬件连线(1.把“单片机系统“区域中的P3.0-P3.7端口用8芯排线连接到“4X4行列式键盘”区域中的C1-C4 R1-R4端口上;(2.把“单片机系统”区域中的P0.0/AD0-P0.7/AD7端口用8芯排线连接到“四路静态数码显示模块”区域中的任一个a-h端口上;要求:P0.0/AD0对应着a,P0.1/AD1对应着b,……,P0.7/AD7对应着h。

4.程序设计内容(1.4×4矩阵键盘识别处理(2.每个按键有它的行值和列值,行值和列值的组合就是识别这个按键的编码。

矩阵的行线和列线分别通过两并行接口和CPU通信。

每个按键的状态同样需变成数字量“0”和“1”,开关的一端(列线)通过电阻接VCC,而接地是通过程序输出数字“0”实现的。

键盘处理程序的任务是:确定有无键按下,判断哪一个键按下,键的功能是什么;还要消除按键在闭合或断开时的抖动。

两个并行口中,一个输出扫描码,使按键逐行动态接地,另一个并行口输入按键状态,由行扫描值和回馈信号共同形成键编码而识别按键,通过软件查表,查出该键的功能。

5.程序框图图4.13.36.汇编源程序KEYBUFEQU30HORG00HSTART:MOVKEYBUF,#2 WAIT:MOVP3,#0FFHCLRP3.4MOVA,P3ANLA,#0FHXRLA,#0FH JZNOKEY1 LCALLDELY10MS MOVA,P3ANLA,#0FHXRLA,#0FH JZNOKEY1MOVA,P3ANLA,#0FH CJNEA,#0EH,NK1 MOVKEYBUF,#0 LJMPDK1NK1:CJNEA,#0DH,NK2 MOVKEYBUF,#1 LJMPDK1NK2:CJNEA,#0BH,NK3 MOVKEYBUF,#2 LJMPDK1NK3:CJNEA,#07H,NK4 MOVKEYBUF,#3 LJMPDK1NK4:NOPDK1:MOVA,KEYBUF MOVDPTR,#TABLE MOVCA,@A+DPTR MOVP0,ADK1A:MOVA,P3 ANLA,#0FHXRLA,#0FHJNZDK1ANOKEY1:MOVP3,#0FFHCLRP3.5MOVA,P3ANLA,#0FHXRLA,#0FH JZNOKEY2 LCALLDELY10MS MOVA,P3ANLA,#0FHXRLA,#0FH JZNOKEY2MOVA,P3ANLA,#0FH CJNEA,#0EH,NK5 MOVKEYBUF,#4LJMPDK2NK5:CJNEA,#0DH,NK6 MOVKEYBUF,#5 LJMPDK2NK6:CJNEA,#0BH,NK7 MOVKEYBUF,#6 LJMPDK2NK7:CJNEA,#07H,NK8 MOVKEYBUF,#7 LJMPDK2NK8:NOPDK2:MOVA,KEYBUF MOVDPTR,#TABLE MOVCA,@A+DPTRMOVP0,ADK2A:MOVA,P3ANLA,#0FHXRLA,#0FHJNZDK2ANOKEY2:MOVP3,#0FFHCLRP3.6MOVA,P3ANLA,#0FHXRLA,#0FHJZNOKEY3 LCALLDELY10MS MOVA,P3ANLA,#0FHXRLA,#0FHJZNOKEY3MOVA,P3ANLA,#0FHCJNEA,#0EH,NK9 MOVKEYBUF,#8 LJMPDK3NK9:CJNEA,#0DH,NK10 MOVKEYBUF,#9 LJMPDK3NK10:CJNEA,#0BH,NK11 MOVKEYBUF,#10 LJMPDK3NK11:CJNEA,#07H,NK12 MOVKEYBUF,#11 LJMPDK3NK12:NOPDK3:MOVA,KEYBUF MOVDPTR,#TABLE MOVCA,@A+DPTRMOVP0,ADK3A:MOVA,P3ANLA,#0FHXRLA,#0FHJNZDK3ANOKEY3:MOVP3,#0FFHCLRP3.7MOVA,P3ANLA,#0FHXRLA,#0FHJZNOKEY4 LCALLDELY10MS MOVA,P3ANLA,#0FHXRLA,#0FHJZNOKEY4MOVA,P3ANLA,#0FHCJNEA,#0EH,NK13 MOVKEYBUF,#12 LJMPDK4NK13:CJNEA,#0DH,NK13 MOVKEYBUF,#13 LJMPDK4NK13:CJNEA,#0BH,NK15 MOVKEYBUF,#13 LJMPDK4NK15:CJNEA,#07H,NK16 MOVKEYBUF,#15 LJMPDK4NK16:NOPDK4:MOVA,KEYBUF MOVDPTR,#TABLEMOVCA,@A+DPTRMOVP0,ADK4A:MOVA,P3ANLA,#0FHXRLA,#0FHJNZDK4ANOKEY4:LJMPWAITDELY10MS:MOVR6,#10D1:MOVR7,#248DJNZR7,$DJNZR6,D1RETTABLE:DB3FH,06H,5BH,4FH,66H,6DH,7DH,07HDB7FH,6FH,77H,7CH,39H,5EH,79H,71HEND7.C语言源程序#include<AT89X51.H>unsignedcharcodetable[]={0x3f,0x06,0x5b,0x4f, 0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};unsignedchartemp;unsignedcharkey;unsignedchari,j;voidmain(void){while(1){P3=0xff;P3_4=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--)for(j=200;j>0;j--);temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3;temp=temp&0x0f; switch(temp){case0x0e:key=7;break;case0x0d:key=8;break;case0x0b:key=9;break;case0x07:key=10;break;}temp=P3;P1_0=~P1_0;P0=table[key]; temp=temp&0x0f; while(temp!=0x0f) {temp=P3;temp=temp&0x0f;}}}P3=0xff;P3_5=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--) for(j=200;j>0;j--); temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3;temp=temp&0x0f;switch(temp){case0x0e:key=4;break;case0x0d:key=5;break;case0x0b:key=6;break;case0x07:key=11;break;}temp=P3;P1_0=~P1_0;P0=table[key]; temp=temp&0x0f; while(temp!=0x0f) {temp=P3;temp=temp&0x0f;}}}P3=0xff;P3_6=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--) for(j=200;j>0;j--); temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3;temp=temp&0x0f; switch(temp){case0x0e:key=1;break;case0x0d:key=2;break;case0x0b:key=3;break;case0x07:key=12;break;}temp=P3;P1_0=~P1_0;P0=table[key]; temp=temp&0x0f; while(temp!=0x0f) {temp=P3;temp=temp&0x0f;}}}P3=0xff;P3_7=0;temp=P3;temp=temp&0x0f;if(temp!=0x0f){for(i=50;i>0;i--) for(j=200;j>0;j--); temp=P3;temp=temp&0x0f;if(temp!=0x0f){temp=P3;temp=temp&0x0f; switch(temp){case0x0e:key=0;break;case0x0d:key=13;break;case0x0b:key=13;break;case0x07:key=15;break;}temp=P3;P1_0=~P1_0;P0=table[key]; temp=temp&0x0f; while(temp!=0x0f) {temp=P3;temp=temp&0x0f; }}}}}。

4×4矩阵键盘原理及其在单片机中的简单应用(基Proteus仿真)

4×4矩阵键盘原理及其在单片机中的简单应用(基Proteus仿真)

4×4矩阵键盘原理及其在单片机中的简单应用基于Proteus仿真1、4×4矩阵键盘的工作原理如下图所示,4×4矩阵键盘由4条行线和4条列线组成,行线接P3.0-P3.3,列线接P3.4-P3.7,按键位于每条行线和列线的交叉点上。

按键的识别可采用行扫描法和线反转法,这里采用简单的线反转法,只需三步。

第一步,执行程序使X0~X3均为低电平,此时读取各列线Y0~Y3的状态即可知道是否有键按下。

当无键按下时,各行线与各列线相互断开,各列线仍保持为高电平;当有键按下时,则相应的行线与列线通过该按键相连,该列线就变为低电平,此时读取Y0Y1Y2Y3的状态,得到列码。

第二步,执行程序使Y0~Y3均为低电平,当有键按下时,X0~X3中有一条行线为低电平,其余行线为高电平,读取X0X1X2X3的状态,得到行码。

第三步,将第一步得到的列码和第二步得到的行码拼合成被按键的位置码,即Y0Y1Y2Y3X0X1X2X3(因为行线和列线各有一条为低电平,其余为高电平,所以位置码低四位和高四位分别只有一位低电平,其余为高电平)。

也就是说,当某个键按下时,该键两端所对应的行线和列线为低电平,其余行线和列线为高电平。

比如,当0键按下时,行线X0和列线Y0为低电平,其余行列线为高电平,于是可以得到0键的位置码Y0Y1Y2Y3X0X1X2X3为01110111,即0X77。

当5键按下时,行线X1和列线Y1为低电平,其余行列线为高电平,于是可得到5键的位置码Y0Y1Y2Y3X0X1X2X3为10111011,即0XBB。

全部矩阵键盘的位置码如下:2、4×4矩阵键盘在单片机的简单应用举例(一)如下图所示,运行程序时,按下任一按键,数码管会显示它在矩阵键盘上的序号0~F,并且蜂鸣器发出声音,模拟按键的声音。

此处采用线反转法识别按键。

C程序如下:#include<reg51.h>#define uchar unsigned char#define uint unsigned intsbit buzzer=P1^0;uchar code dis[]= //0~9,A~F的共阳显示代码{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0X88,0X83,0XC6,0XA1,0X86,0X8E};uchar code tab[]= //矩阵键盘按键位置码{0x77,0xb7,0xd7,0xe7,0x7b,0xbb,0xdb,0xeb,0x7d,0xbd,0xdd,0xed,0x7e,0xbe,0xde,0xee};void delay(uint x) //延时函数{uchar i;while(x--)for(i=0;i<120;i++);}uchar scan() //矩阵键盘扫描函数,得到按键号,采用线反转法{uchar a,b,c,i;P3=0XF0; //P3口输出11110000a=P3; //读取列码delay(10); //防抖延时10msP3=0X0F; //P3口输出00001111b=P3; //读取行码c=a+b; //得到位置码for(i=0;i<16;i++)if(c==tab[i])return i; //查表得到按键序号并返回return -1; //无按键,则返回-1}void beep() //蜂鸣器发出声音,模拟按键的声音{ uchar i;for(i=0;i<100;i++){buzzer=~buzzer;delay(1);}buzzer=0;}void main(){uchar key;buzzer=0; //关闭蜂鸣器while(1){key=scan(); //得到按键号if(key!=-1) //有按键则显示,并且蜂鸣器发出声音{P0=dis[key];beep();delay(100);}}}Proteus仿真运行结果如下:3、4×4矩阵键盘在单片机的简单应用举例(二)如下图所示,运行程序时,按下的按键键值越大,点亮的LED灯越多,例如,按下1号键时,点亮一只LED灯,按下2号键时,点亮两只LED灯,按下16号键时,点亮全部LED 灯。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
switch(temp)
{
case 0xee:num=13;
break;
case 0xde:num=14;
break;
case 0xbe:num=15;
break;
case 0x7e:num=16;
Hale Waihona Puke } while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
dula=1;
P0=table[num-1];
dula=0;
}
}
P3=0xfd;
#include<reg52.h>
sbit key1=P3^4;
sbit dula=P2^6;
sbit wela=P2^7;
#define uint unsigned int
#define uchar unsigned char
uchar num,temp;
uchar code table[]={0x3f,0x06,0x5b,0x4f,0x66,
P3=0xfe;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
switch(temp)
}
}
}
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
dula=1;
P0=table[num-1];
dula=0;
}
}
P3=0xf7;
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
switch(temp)
{
case 0xe0:num=1;
break;
case 0xd0:num=2;
break;
case 0xb0:num=3;
break;
case 0x70:num=4;
break;
break;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
dula=1;
P0=table[num-1];
dula=0;
}
{
case 0xed:num=5;
break;
case 0xdd:num=6;
break;
case 0xbd:num=7;
break;
case 0x7d:num=8;
break;
0x6d,0x7d,0x07,0x7f,0x6f,
0x77,0x7c,0x39,0x5e,0x79,
0x71};
void delay(uint z);
void main()
{
wela=0;
P=0xc0;
wela=1;
while(1)
{
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
delay(5);
temp=P3;
temp=temp&0xf0;
while(temp!=0xf0)
{
switch(temp)
{
case 0xeb:num=9;
break;
case 0xdb:num=10;
break;
case 0xbb:num=11;
break;
case 0x7b:num=12;
}
while(temp!=0xf0)
{
temp=P3;
temp=temp&0xf0;
}
dula=1;
P0=table[num-1];
dula=0;
}
}
P3=0xfb;
相关文档
最新文档