经典案例分享:两种键盘扫描方法比较分析
按键扫描处理个人总结

按键扫描处理总结一、矩阵按键扫描方法1、现在的矩阵扫描主要有两种方法:(1)行列扫描法(2)反转法。
2、行列扫描法(1)行列扫描法的基本思想:行列扫描法是将其中的一行输出为低电平,其他行输出为高电平,列设为输入,然后判断哪一列为低电平,从而确认出是哪一行哪一列有键按下。
(2)行列扫描法举例如图1所示的2*2矩阵键盘,首先:将PB1,PB2作为行,并设置为输出;PA1,PA2作为列,并设置为输入。
其次:PB1设置为低电平输出,PB2设置为高电平输出,查看此时PA1和PA2的输入状态,假设此时S1按下,则此时PB1输出低电平通过S1传到了PA1上,使得PA1输入为低电平,而PA2仍然为高电平。
说明第一行有键按下,并且是第一列有键按下然后:再将PB1设置为高电平输出,PB2设置为低电平输出,此时PA1,PA2输入都为高电平。
说明第二行上没有按键按下。
最后:至此可以判断此时的PA1与PB1上的按键被按下,即第一行第一列的S1被按下。
整个按键扫描过程结束。
3、反转法(1)反转法的基本思想:将行设为输出为低电平,列设为输入,判断此时列的输入状态;然后在将列设为输出位低电平,行设为输入,判断此时行的输入状态。
如果有键按下,则其中的列输入状态必然有其中一列为低,行的输入状态也必然有其中一行为低,记录此时的行列号即可判断出是哪一行哪一列有键按下。
(2)反转法举例:如图1所示的2*2矩阵键盘,首先:将PB1,PB2作为行,并设置为输出;PA1,PA2作为列,并设置为输入。
其次:将PB1,PB2输出为低,查看PA1,PA2输入状态,假设还是S1被按下,则此时PA1输入为低电平,PA2输入为高电平。
说明第一列有键按下。
然后:将PB1,PB2作为行,并设置为输入;PA1,PA2作为列,并设置为输出。
最后:将PA1,PA2输出为低,查看PB1,PB2输入状态,则此时PB1输入为低电平,PB2输入为高电平。
说明第一行有键按下。
实验五 键盘扫描实验 实验报告

键盘扫描实验实验报告一、实验目的1. 掌握线反转法键盘扫描原理。
2. 了解单片机的输入和输出过程,理解单片机的数据采集过程。
二、实验内容单片机外接4x4键盘,通过线反转法判断按下的键,并在数码管上显示按键对应的数字。
第一行从左到右分别是开关K0, K1, K2, K3,第二行从左到右分别是K4, K5, K6, K7以此类推。
当按下Kn时,在数码管上显示数字n。
三、实验原理线翻转法:先对行(R0-R3)置0,对列(R4-R7)置1。
当有键被按下时,会把按键所在的列的电位从1变0,记录下位置;然后再将行列翻转,记录下按下键的所在行,两数进行或运算,就可以得到一个唯一表示按下键的数字。
例如:假定R0-R7分别与单片机的P2.0-P2.7相连。
先把R4-R7置1,R0-R3置0(通过指令MOV P2, #0F0H实现)。
当键K5被按下时,R5电位被拉低为低电平。
此时,P2口表示的数为:1101 0000(0xD0);然后再置R4-R7为0,R0-R3为1,此时,R1电位被拉低为低电平,此时,P2口表示的数为:0000 1101(0x0D)。
将两数相与取反,得到:0010 0010。
四、实验过程1. 连接好单片机及其外围设备电路2. 编写汇编程序ORG LJMP KeyLJMP K7: CJNE R2, #82H, K8ORG 0100H MOV P0, #0F8H Init: CLR P1.3 LJMP KeyMOV P0, #0C0H K8: CJNE R2, #14H, K9 Key: MOV P2, #0F0H MOV P0, #080HMOV A, P2 LJMP KeyMOV R1, A K9: CJNE R2, #24H, K10MOV P2, #0FH MOV P0, #090HMOV A, P2 LJMP KeyORL A, R1 K10: CJNE R2, #44H, K11CPL A MOV P0, #088HMOV R2, A LJMP KeyJNZ KeyPro K11: CJNE R2, #84H, K12LJMP Key MOV P0, #083H KeyPro: CJNE R2, #11H, K1 LJMP KeyMOV P0, #0C0H K12: CJNE R2, #18H, K13LJMP Key MOV P0, #0C6H K1: CJNE R2, #21H, K2 LJMP KeyMOV P0, #0F9H K13: CJNE R2, #28H, K14LJMP Key MOV P0, #0A1H K2: CJNE R2, #41H, K3 LJMP KeyMOV P0, #0A4H K14: CJNE R2, #48H, K15LJMP Key MOV P0, #086H K3: CJNE R2, #81H, K4 LJMP KeyMOV P0, #0B0H K15: CJNE R2, #88H, K16LJMP Key MOV P0, #08EH K4: CJNE R2, #12H, K5 LJMP KeyMOV P0, #099H K16: LJMP KeyLJMP Key ENDK5: CJNE R2, #22H, K6MOV P0, #092HLJMP KeyK6: CJNE R2, #42H, K7MOV P0, #082H五、实验结果1. 当按下开关Kn时,数码管能够显示对应的数字。
实验八 键盘扫描实验

实验八键盘扫描实验一、实验目的1. 掌握中断键盘扫描编程方法。
2. 掌握LED动态显示方法。
二、实验原理及实验内容1. 实验原理无论是单片机控制系统还是单片机测量系统,都需要一个人机对话装置,这种人机对话装置通常采用键盘和显示器。
键盘是单片机应用系统中人机对话常用的输入装置,而显示器是单片机应用系统人机对话中的常用输出装置。
键盘是由若干个按键开关组成,键的多少根据单片机应用系统的用途而定。
键盘由许多键组成,而每个键相当于一个机械开关触点,当键按下时,触点闭合,当键松开时,触点断开。
单片机接收到按键的触点信号后作相应的功能处理。
因此对于单片机系统来说键盘接口信号是输入信号。
单片机的键盘接口分为独立式和矩阵式。
独立式键盘的每个按键都有一个信号线与单片机电路相连,所有按键有一个公共地或公共正端,每个键相互独立互不影响。
如图7-7所示,当按下键1时,无论其它键是否按下,键1的信号线就由1变0;当松开键1时,无论其它键是否按下,键1的信号线就由0变1。
矩阵式键盘的按键触点接于由行、列母线构成的矩阵电路的交叉处,每当一个按键按下时通过该键将相应的行、列母线连通。
若在行、列母线中把行母线逐行置0(一种扫描方式),那么列母线就用来作信号输入线。
矩阵式键盘原理图如图7-8所示。
图7-7 独立式按键原理图图7-8 矩阵式按键原理图针对以上两大类键盘工作方式,单片机又有三种键盘扫描方式:查询方式;定时扫描方式和中断扫描方式。
查询方式是指在程序中用一段专门的扫描和读按键程序不停查询有无按键按下,确定键值。
这种方式电路简单,但需要占用单片机的机器时间。
定时扫描方式是指利用单片机内的定时器来产生定时中断,然后在定时中断的服务程序中扫描,检查有无按键按下,确定键值。
这种方式的电路也比较简单,不占用单片机的机器时间,但需要占用一个定时器,同时定时的时间不能过长,否则可能检测不到相应得按键。
中断扫描方式是指当有键按下时由相应的硬件电路产生中断信号,单片机在中断服务程序中扫描,检查有无按键按下,确定键值。
键盘扫描三种方法

第一种------传统法uchar scanf(){P3=0xfe;temp=P3&0xf0;if(temp!=0xf0) //判断是否有键按下{delay(5);//给一个延时temp=P3&0xf0;if(temp!=0xf0) //再次判断是否有键按下{temp=P3;switch(temp){case 0xee:num=1;break;case 0xde:num=2;break;case 0xbe:num=3;break;case 0x7e:num=4;break;}}while(temp!=0xf0)//键起,推出程序{temp=P3&0xf0;}}P3=0xfd;temp=P3&0xf0;if(temp!=0xf0){delay(5);temp=P3&0xf0;if(temp!=0xf0){temp=P3;switch(temp){case 0xed:num=5;break;case 0xdd:num=6;break;case 0xbd:num=7;break;case 0x7d:num=8;break;}}while(temp!=0xf0){temp=P3&0xf0;}}P3=0xfb;temp=P3&0xf0;if(temp!=0xf0){delay(5);temp=P3&0xf0;if(temp!=0xf0){temp=P3;switch(temp){case 0xeb:num=9;break;case 0xdb:num=10;break;case 0xbb:num=11;break;case 0x7b:num=12;break;}}while(temp!=0xf0){temp=P3&0xf0;}}P3=0xf7;temp=P3&0xf0;if(temp!=0xf0){delay(5);temp=P3&0xf0;if(temp!=0xf0){temp=P3;switch(temp){case 0xe7:num=13;break;case 0xd7:num=14;break;case 0xb7:num=15;break;case 0x77:num=16;break;}}while(temp!=0xf0){temp=P3&0xf0;}}Return(num);}第二种——简单法uchar keyscan(void){uchar scancode,tmpcode;P3 = 0xf0; // 发全0行扫描码if ((P3&0xf0)!=0xf0) // 若有键按下{delay(5); // 延时去抖动if ((P3&0xf0)!=0xf0)// 延时后再判断一次,去除抖动影响{scancode = 0xfe;//相当于从第一行开始扫描1111 1110while((scancode&0x10)!=0) // 控制行我的理解while((P3&0xf0)!=0xf0)(原来的程序转了一个大弯)(原程序,首先进入,使其扫描全行,扫描一次退出;我的:按键复原后,才退出程序;我的程序要扫描多次,但前提是一定扫描得到{P3 = scancode; // 输出行扫描码其实P3变为了1101 1110(假设有键按下)其中因为有键按下,写入的1马上又变为0(只有当行和列都对应时,才会继续下面的运算)即:如果开始按的是1101 1011,那么P3显示的就是1111 1110列中就不会出现0if ((P3&0xf0)!=0xf0) // 本行有键按下(确定行){tmpcode = (P3&0xf0)|0x0f; //确定列return((~scancode)+(~tmpcode)); /* 返回特征字节码,为1的位即对应于行和列*/}elsescancode = (scancode<<1)|0x01; // 行扫描码左移一位,换另一行扫面}}}return(0); // 无键按下,返回值为0}第三种———先行扫描,再列扫描uchar keyscan(void){uchar tag1,tag2;tag1=0xff;tag2=0xff;P3 = 0xf0; // 发全0行扫描码if ((P3&0xf0)!=0xf0) // 若有键按下{delay(5); // 延时去抖动if ((P3&0xf0)!=0xf0) // 延时后再判断一次,去除抖动影响{tag1=P3;P3=0x0f;tag2=P3&0x0f;}}return(~(tag1|tag2)); }。
行列式键盘扫描

实验二 行列式键盘扫描一. 实验内容与目的1. 实验内容利用行列式键盘,当按下键盘中的一个键子时会在数码管上显示出相应的键值,要求键盘有去抖功能,数码管显示的键值能进行移位。
2,实验目的学会行列式键盘扫描的原理与方法,进一步强化对MSP430I/O 口使用方法的掌握,加强msp430C 语言编程的能力。
二. 方法与结果键盘扫描:利用P3口进行键盘扫描,如图,令P3.0~P3.3为输出端口,P3.4~P3.7为输入端口,由于P3.4~P3,7接了上拉电阻,所以当没有键子按下时P3.4~P3.7都为‘1’,当有键子按下时P3.4~P3.7就有可能发生变化。
所以键盘扫描式先让P3.0~P3.3都为‘0’,当有键子按下时P3.4~P3.7就会有一个由‘1’变为‘0’,根据哪一个变为‘0’就能判断出相应的列有键子按下,再让P3.0~p3.3逐个变为‘1’判断出哪一行有键子按下进而确定出哪一个键子按下。
11221112221122311224112251122611227112281122911221122#1122*1122A 1122B1122C1122DR2510k R2610kR2710kR2810kP_30P_31P_32P_33P_34P_35P_36P_37P3.0~p3.3为‘0’P3.4~p3.7都为‘1’P3.4~P3.7不都为‘1’ 令P3.0~p3.3逐个为‘1’ 确定列确定行当P3.4~p3.7都为‘1’确定键值数码管显示:数码管位选与段选共用P1.0~P1.3,利用锁存器74HC373分时进行段选和位选,P6.1和P6.2控制74HC373,从而使相应数码管显示相应数。
电路图如下:e 1d 2d p3c 4g 546b 73829f 10a 11112seg4O E 1Q 02D 03D 14Q 15Q 26D 27D 38Q 39G N D 10L E11Q 412D 413D 514Q 515Q 616D 617D 718Q 719V C C 2074HC373_174HC373O E 1Q 02D 03D 14Q 15Q 26D 27D 38Q 39G N D 10L E11Q 412D 413D 514Q 515Q 616D 617D 718Q 719V C C 2074HC373_274HC373R19100R20100R21100R22100R2310k R2410k P_61P_62VCCVCCGND GNDGND GND GNDGNDP_10P_11P_12P_13P_14P_15P_16P_17三. 实验程序#include<msp430.h> void KEYSCAN(); void TUBESCAN();void KEYSLOVE( unsigned int key); unsigned char const table[]={0xff,0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e}; //0~F 码值 unsigned int s1=0,s2=0,s3=0,s4=0; //s1~s4保存相应键值,进行显示 unsigned int key;void delay1(unsigned int i) {while(i--); }void main() {WDTCTL=WDTPW+WDTHOLD; P1DIR=0xff; P1SEL=0x00; P3SEL=0x00; P3DIR=0x0f;P6DIR=BIT1+BIT2; TUBESCAN(); P3OUT=0xf0; while(1)KEYSCAN();TUBESCAN();}}void KEYSCAN(){P3OUT=0xf0;if(P3IN!=0xf0){switch(P3IN){case (0xe0):P3OUT=0x01;if(P3IN==0xf1) {key=16;break;}P3OUT=0x02;if(P3IN==0xf2) {key=12;break;}P3OUT=0x04;if(P3IN==0xf4) {key=8;break;}P3OUT=0x08;if(P3IN==0xf8) {key=4;break;}case (0xd0):P3OUT=0x01;if(P3IN==0xf1) {key=15;break;}P3OUT=0x02;if(P3IN==0xf2) {key=11;break;}P3OUT=0x04;if(P3IN==0xf4) {key=7;break;}P3OUT=0x08;if(P3IN==0xf8) {key=3;break;}case (0xb0):P3OUT=0x01;if(P3IN==0xf1) {key=14;break;}P3OUT=0x02;if(P3IN==0xf2) {key=10;break;}P3OUT=0x04;if(P3IN==0xf4) {key=6;break;}P3OUT=0x08;if(P3IN==0xf8) {key=2;break;}case (0x70):P3OUT=0x01;if(P3IN==0xf1) {key=13;break;}P3OUT=0x02;if(P3IN==0xf2) {key=9;break;}P3OUT=0x04;if(P3IN==0xf4) {key=5;break;}P3OUT=0x08;if(P3IN==0xf8) {key=1;break;}}P3OUT=0xf0;KEYSLOVE(key);} //键盘扫描函数,得到相应的键值key }void KEYSLOVE( unsigned int key){delay1(200);if(P3IN!=0xf0){while(P3IN!=0xf0) TUBESCAN(); //键盘去抖,保证当手松开时读取键值if(s4==0)s4=s3;s3=s2;s2=s1;s1=key;}else{if(key==16){s1=0;s2=0;s3=0;s4=0;key=0;}}}} //将得到的键值进行处理:移位/重置void TUBESCAN(){P6OUT=0x02;P1OUT=table[s4];P6OUT=0x04;P1OUT=0x01;delay1(400);P6OUT=0x02;P1OUT=table[s3];P6OUT=0x04;P1OUT=0x02;delay1(400);P6OUT=0x02;P1OUT=table[s2];P6OUT=0x04;P1OUT=0x04;delay1(400);P6OUT=0x02;P1OUT=table[s1];P6OUT=0x04;P1OUT=0x08;delay1(400);} //数码管扫描,使数码管保持四.行列式键盘实验总结①做行列是键盘重点是键盘扫描确定键值,键盘扫描也有多种方式,要多思考确定最优方式,采用本实验中的键盘扫描方式当没有键子按下时不必执行键盘扫描的其他程序,将更多的时间给了数码管扫描,挺优的,在着手写程序之前一定要筹划如何去写,要寻求简单易行的方法,写程序规划挺重要的。
单片机矩阵键盘扫描的两种方式

单片机矩阵键盘扫描的两种方式单片机矩阵键盘扫描的两种方式矩阵键盘扫描方式:第一种:逐行扫描法,就是一行一行的扫描。
实现代码如下(键盘连接P2口):#define NO_KEY 0XFF#define KEY_LO() P2 &= 0XF0#define KEY_HI() P2 |= 0X0F#define KEY_L(i) P2 &= ~(1<<i)#define KEY_RD() ((P2>>4) & 0x0f)UINT8 OnceKey(void){UINT8 line = 0;UINT8 key = NO_KEY;//key valueKEY_LO();if (KEY_RD() == 0X0F){KEY_HI();return NO_KEY;}for (line=0; line<4; line ++){KEY_HI();KEY_L(line);key = KEY_RD();switch (key){case ROW_FIRST:key = 4*line + 0;break;case ROW_SECOND:key = 4*line + 1;break;case ROW_THIRD:key = 4*line + 2;break;case ROW_FOURTH:key = 4*line +3;break;default :key = 0x0f;break;}if (key < 0x10){return key;}}return NO_KEY;}第二种,线性反转法。
就是行和列分别读出。
实现代码如下:#define CVT(i) ((i)==(~1)&0x0f)? 0: ((i)==(~2)&0x0f)? 1: ((i)==(~4)&0x0f)? 2: ((i)==(~8)&0x0f)? 3: 4;#define KEY0_3HI() P2 |= 0X0F#define KEY0_3LO() P2 &= 0XF0#define KEY4_7HI() P2 |= 0XF0#define KEY4_7LO() P2 &= 0X0F#define KEY0_3RD() (P2 & 0X0F)#define KEY4_7RF() ((P2>>4) & 0X0F)UINT8 OnceKey(void){UINT8 line = NO_KEY;UINT8 row = NO_KEY;UINT8 key;KEY0_3HI();KEY4_7LO();line = KEY0_3RD();//读入行的值if (0x0f == line){key = NO_KEY;}else{KEY0_3LO();KEY4_7HI();row = KEY4_7RD();//读入列的值if (0x0f == row){key = NO_KEY;}else{key = CVT(line)*4 + CVT(row);}}KEY0_3HI();KEY4_7HI();return key; }。
堪称一绝的按键扫描方法

堪称一绝的按键扫描方法堪称一绝的“IO口扫键”法在做项目(工程)的时候,我们经常要用到比较多的按键,而且IO资源紧张,于是我们就想方设法地在别的模块中节省IO口,好不容易挤出一两个IO口,却发 现仍然不够用,实在没办法了就添加一个IC来扫键。
一个IC虽然价格不高,但对于大批量生产而且产品利润低的厂家来说,这是一笔不菲的开支!那,我们能不能想到比较好的扫键方法:用最少的IO口,扫最多的键?可以吗? 举个例:给出5个IO口,能扫多少键?有人说是2*3=6个,如图一:图一对,大部分技术参考书都这么做,我们也经常这样做:用3个IO口作行扫描,2个IO作列检测(为方便描述,我们约定:设置某一IO口输出为 “0”――称其为“扫某IO口”)。
用行线输出扫键码,列线检测是否有按键的查询方法进行扫键。
扫键流程:在行线依次输出011,101,110扫键值, 行线每输出一个扫键值,列线检测一次。
当列线检测到有按键时,结合输出的扫键值可以判断相应的按键。
但是,5个IO真的只能扫6个键吗?有人说可以扫9个,很聪明!利用行IO与地衍生3个键(要注意上拉电阻),如图二:图二扫键流程:先检测3个行IO口,对K1’,K2’,K3’进行扫键,之后如上述2*3扫键流程。
5个IO口能扫9个键,够厉害吧,足足比6个键多了1/2!动动脑,还能不能再多扫几个?就几个?一个也行!好,再想一下,硬是被逼出来了!如图三:图三不多不少,正好10个键!这种扫键方式比较少见吧!漂亮!扫键流程:设IO1输出为“0”,检测IO2…IO5,若判断有相应健按下,则可知有健;若无 键,则继续扫键:设IO2输出为“0”,检测IO3,IO4,IO5,判断有无键按下,如此类推。
这里应注意:当扫某一IO口(输出为“0”)时,不要去 检测已经扫过的IO口。
如:此时设置IO2输出为“0”,依次检测IO3,IO4,IO5,但不要去检测IO1,否则会出错(为什么,请思考)。
感觉怎么样?不错吧!让我们再看看图三,好有成就感!看着,看着……又看到了什么?快!见图四:图四真强!被您看出20个键!多了一个对称的三角形。
键盘扫描方法

键盘扫描方法传统的键盘扫描方法如图1所示,该方法虽然被广泛应用于很多场合,但有一个不足的地方,如果按键一直没有释放,或者按键坏了,一直处于闭合状态,则程序一直处于检测按键是否释放,系统将无法运行。
只要对其稍加改进,就可以避免产生这个问题。
假设键盘接口电路采用独立式键盘接口,所有按键公共端接地,而且没有按键按下时IO口为高电平。
当按键没有按下时,IO口为高电平;当按键按下时,IO口为低电平;当按键释放时,IO口为高电平。
一个完整的按键过程是——按键未按下,按键按下,按键释放,而对应的IO口的电平变化为——高电平,低电平,高电平。
所以,可以通过判断IO口电平变化的变化顺序是否满足高电平→低电平→高电平,来判断是否有按键按下,而对于其它的电平变化顺序都是无效的。
那么该如何实现呢?在键盘扫描过程中,如果IO口为高电平,则需要判断是由于未按键,还是按键按下后释放引起的;如果IO口为低电平,则需要判断是由于未按键还是扫描之前本来就是低电平引起的。
所以我们需要引入一个全局位变量KEY_EN,来标志按键的状态, KEY_EN=0表示按键未按下;KEY_EN=1表示按键按下。
另外,我们还需引入一个全局字节变量KEY_TP来暂存键值,这是因为只有当IO口电平变化满足高电平→低电平→高电平,才表示一个按键有效,而只有在IO口为低电平的时候才能够读取到键值。
具体的键盘扫描流程如图2所示,键盘初始化KEY_EN=0。
图1 传统键盘扫描图2 改进后键盘扫描接下来我们介绍一种代码效率极高的键盘扫描方法。
键盘接口电路同样采用独立式,假设有8个按键,所有按键公共端接地,键盘扫描口为P0.7~P0.0,而且没有按键按下时为高电平,键盘扫描程序如下:unsigned char Trigger;unsigned char Continue;void delayms(unsigned char n){……}void key_scan(){unsigned char ReadData;if (P0!=0xff&&Trigger==0x00) delayms(20);ReadData = P0 ^ 0xff;Trigger = ReadDate & (ReadData ^ Continue);Continue = ReadData;}程序中的Trigger就是键值。
识别按键的两种常用方法

识别按键的两种常用方法
在计算机编程中,识别按键有两种常用的方法:
1. 硬件扫描法:
- 工作原理:通过直接读取键盘的硬件信号来检测按键的按下和释放。
- 优点:响应速度快,适用于对实时性要求较高的应用。
- 缺点:需要了解底层硬件,编程较为复杂,且不同键盘可能需要不同的驱动程序。
2. 软件扫描法:
- 工作原理:通过不断查询键盘状态来检测按键的按下和释放。
- 优点:编程相对简单,不需要了解具体的硬件细节,适用于大多数常见的应用。
- 缺点:可能会消耗一定的CPU 资源,因为需要不断地查询键盘状态。
这两种方法各有优缺点,需要根据具体的应用场景和需求来选择。
在现代编程中,通常使用操作系统提供的键盘事件处理机制,它会自动将按键事件通知给应用程序,从而简化了按键识别的过程。
实验五 键盘扫描实验 实验报告

实验五键盘扫描实验实验报告一、实验目的本次实验的主要目的是深入了解键盘扫描的工作原理,掌握键盘扫描的编程实现方法,以及提高对硬件接口和软件编程的综合应用能力。
二、实验设备1、计算机一台2、实验开发板一套3、下载线一根4、键盘一个三、实验原理键盘扫描的基本原理是通过逐行或逐列扫描键盘矩阵,检测按键的按下和释放状态。
常见的键盘扫描方式有行列式扫描和编码式扫描。
在行列式扫描中,将键盘的行线和列线分别连接到微控制器的输入输出端口。
通过依次将行线设置为低电平,同时读取列线的状态,来判断是否有按键按下。
如果在某一行被设置为低电平时,对应的列线检测到低电平,则表示该行和该列交叉处的按键被按下。
编码式扫描则是利用专门的编码芯片对键盘进行扫描和编码,微控制器只需读取编码芯片输出的按键编码即可确定按键的状态。
四、实验步骤1、硬件连接将实验开发板与计算机通过下载线连接好。
将键盘连接到实验开发板的相应接口。
2、软件编程选择合适的编程语言和开发环境,如 C 语言和 Keil 开发环境。
定义键盘的行线和列线所对应的端口。
编写扫描函数,实现键盘扫描的逻辑。
在主函数中调用扫描函数,并根据返回的按键值进行相应的处理,如显示按键字符或执行特定的操作。
3、编译下载对编写好的程序进行编译,检查是否有语法错误。
将编译生成的可执行文件下载到实验开发板中。
4、实验测试按下键盘上的不同按键,观察实验开发板上的显示或输出结果是否正确。
检查是否能够准确检测到按键的按下和释放,以及是否存在按键抖动等问题。
五、实验结果与分析1、实验结果在实验过程中,成功实现了对键盘的扫描,并能够准确检测到按键的按下。
按下不同的按键时,实验开发板能够正确显示相应的按键字符或执行预定的操作。
2、结果分析对于按键的准确检测,说明编写的扫描函数逻辑正确,能够有效地识别键盘矩阵中的按键状态变化。
在检测到按键按下时,没有出现误判或漏判的情况,表明行线和列线的设置以及读取操作正常。
矩阵键盘的三种扫描方法

矩阵键盘的三种扫描方法矩阵键盘是一种常见的输入设备,它由多个按键组成,并通过矩阵扫描的方式来检测用户的按键输入。
矩阵键盘的扫描方法可以分为三种:行扫描、列扫描和交错扫描。
下面将详细介绍这三种扫描方法。
1.行扫描行扫描是最简单的一种扫描方法。
它的原理是将矩阵键盘的每一行连接到一个IO口,通过轮询检测每一行的电平变化来获取用户的按键输入。
行扫描的工作流程如下:1)将矩阵键盘的每一行连接到一个IO口,并设置为输入模式。
2)逐个地将每一行的IO口设置为高电平,并检测列的电平状态。
3)如果其中一列的电平为低电平,说明该列有按键按下。
此时,记录下这个按键的位置(行号和列号)以及按键的值(键码或字符),然后将这个按键的位置和值传递给上层应用或处理器。
4)将当前行的IO口设置为低电平,然后继续下一行的检测,重复2)~3)步骤,直到所有行都被检测完毕。
行扫描的优点是实现简单,只需要一个IO口来检测按键的状态。
但是它的缺点是扫描速度较慢,因为需要逐个地检测每一行。
2.列扫描列扫描是一种比较常用的扫描方法。
它的原理是将矩阵键盘的每一列连接到一个IO口,通过轮询检测每一列的电平变化来获取用户的按键输入。
列扫描的工作流程如下:1)将矩阵键盘的每一列连接到一个IO口,并设置为输入模式。
2)逐个地将每一列的IO口设置为高电平,并检测行的电平状态。
3)如果其中一行的电平为低电平,说明该行有按键按下。
此时,记录下这个按键的位置(行号和列号)以及按键的值(键码或字符),然后将这个按键的位置和值传递给上层应用或处理器。
4)将当前列的IO口设置为低电平,然后继续下一列的检测,重复2)~3)步骤,直到所有列都被检测完毕。
列扫描的优点是速度较快,因为只需要逐个地检测每一列。
但是它的缺点是需要多个IO口来检测按键的状态。
3.交错扫描交错扫描是一种综合了行扫描和列扫描的扫描方法,它可以有效地减少扫描的时间。
交错扫描的原理是将矩阵键盘的行和列交错地连接到多个IO口,通过并行检测行和列的电平变化来获取用户的按键输入。
键盘扫描及数码管显示

键盘制作键盘有两类:一个是独立键盘,另一个是矩阵键盘。
从名字上就知道,后者复杂。
那我们先看看前者,这个不复杂的怎么样。
这就是一个独立键盘的电路图其特点是每个按键单独占用一个IO口,每个按键工作不会影响其他的IO口线的状态。
多用于按键不多的场合。
当然,我们说了,这是用到不多的键盘的时候。
如果多的话这个方法不免过于麻烦。
这样,后者就派上用场了。
这就是传说中的矩阵键盘,看起来就比独立键盘复杂的多,矩阵键盘又称行列键盘,它是用四条I/O线作为行线,四条I/O线作为列线组成的键盘。
在行线和列线的每个交叉点上设置一个按键。
这样键盘上按键的个数就为4*4个。
这种行列式键盘结构能有效地提高系统中I/O口的利用率。
矩阵键盘的工作原理最常见的键盘布局如图1所示。
一般由16个按键组成图1这个外观也没什么意思了,大家也经常见到,比如电话键盘、银行的密码盘都是这个样子的。
下面还是让我们看看他的原理。
图2 4*4矩阵键盘当无按键闭合时,P10~P13与P14~P17之间开路。
当有键闭合时,与闭合键相连的两条I/O口线之间短路。
判断有无按键按下的方法是:第一步,置列线P14~P17为输入状态,从行线P10~P13输出低电平,读入列线数据,若某一列线为低电平,则该列线上有键闭合。
第二步,行线轮流输出低电平,从列线P14~P17读入数据,若有某一列为低电平,则对应行线上有键按下。
综合一二两步的结果,可确定按键编号。
但是键闭合一次只能进行一次键功能操作,因此须等到按键释放后,再进行键功能操作,否则按一次键,有可能会连续多次进行同样的键操作。
这个矩阵的工作原理很不好理解,要仔细看,不过也很简单的了。
通常的按键所用开关为机械弹性开关,当机械触点断开、闭合时,电压信号小型如下图。
由于机械触点的弹性作用,一个按键开关在闭合时不会马上稳定地接通,在断开时也不会一下子断开。
因而在闭合及断开的瞬间均伴随有一连串的抖动,如下图。
抖动时间的长短由按键的机械特性决定,一般为5ms~10ms。
键盘扫描分类

键盘扫描分类一、概述键盘在单片机应用系统中,实现输入数据、传送命令的功能,是人工干预的主要手段。
键盘分两大类:编码键盘和非编码键盘。
编码键盘:由硬件逻辑电路完成必要的键识别工作与可靠性措施。
每按一次键,键盘自动提供被按键的读数,同时产生一选通脉冲通知微处理器,一般还具有反弹跳和同时按键保护功能。
这种键盘易于使用,但硬件比较复杂,对于主机任务繁重之情况,采用8279可编程键盘管理接口芯片构成编码式键盘系统是很实用的方案。
非编码键盘:只简单地提供键盘的行列与矩阵,其他操作如键的识别,决定按键的读数等仅靠软件完成,故硬件较为简单,但占用CPU较多时间。
有:独立式按键结构、矩阵式按键结构。
二、键盘系统设计首先,确定键盘编码方案:采用编码键盘或非编码键盘。
随后,确定键盘工作方式:采用中断或查询方式输入键操作信息。
然后,设计硬件电路。
非编码键盘系统中,键闭合和键释放的信息的获取,键抖动的消除,键值查找及一些保护措施的实施等任务,均由软件来完成。
(一)非编码键盘的键输入程序应完成的基本任务1.监测有无键按下;键的闭合与否,反映在电压上就是呈现出高电平或低电平,所以通过电平的高低状态的检测,便可确认按键按下与否。
2.判断是哪个键按下。
一.编程扫描方式:当单片机空闲时,才调用键盘扫描子程序,反复的扫描键盘,等待用户从键盘上输入命令或数据,来响应键盘的输入请求。
二.定时扫描工作方式:单片机对键盘的扫描也可用定时扫描方式,即每隔一定的时间对键盘扫描一次。
三.中断工作方式:只有在键盘有键按下时,才执行键盘扫描程序并执行该按键功能程序,如果无键按下,单片机将不理睬键盘3.完成键处理任务。
(二)从电路或软件的角度应解决的问题1.消除抖动影响。
键盘按键所用开关为机械弹性开关,利用了机械触点的合、断作用。
由于机械触点的的弹性作用,一个按键开关在闭合和断开的瞬间均有一连串的抖动、抖动时间的长短由按键的机械特性决定,一般为5~10m s,这是一个很重要的参数。
扫描式按键解读

扫描式按键解读矩阵键盘扫描原理1. 在键盘中按键数量较多时,为了减少I/O口的占用,通常将按键排列成矩阵形式如图1所示。
在矩阵式键盘中,每条水平线和垂直线在交叉处不直接连通,而是通过一个按键加以连接。
这样,一个端口(如P1口)就可以构成4*4=16个按键,比之直接将端口线用于键盘多出了一倍,而且线数越多,区别越明显,比如再多加一条线就可以构成20键的键盘,而直接用端口线则只能多出一键(9键)。
由此可见,在需要的键数比较多时,采用矩阵法来做键盘是合理的。
矩阵式结构的键盘显然比直接法要复杂一些,识别也要复杂一些,上图中,列线通过电阻接正电源,并将行线所接的单片机的I/O口作为输出端,而列线所接的I/O口则作为输入。
这样,当按键没有按下时,所有的输出端都是高电平,代表无键按下。
行线输出是低电平,一旦有键按下,则输入线就会被拉低,这样,通过读入输入线的状态就可得知是否有键按下了。
具体的识别及编程方法如下所述。
2.矩阵式键盘的按键识别方法确定矩阵式键盘上何键被按下介绍一种“行扫描法”。
行扫描法行扫描法又称为逐行(或列)扫描查询法,是一种最常用的按键识别方法,如上图所示键盘,介绍过程如下。
3.判断键盘中有无键按下将全部行线Y0-Y3置低电平,然后检测列线的状态。
只要有一列的电平为低,则表示键盘中有键被按下,而且闭合的键位于低电平线与4根行线相交叉的4个按键之中。
若所有列线均为高电平,则键盘中无键按下。
4.判断闭合键所在的位置在确认有键按下后,即可进入确定具体闭合键的过程。
方法是:依次将行线置为低电平,即在置某根行线为低电平时,其它线为高电平。
在确定某根行线位置为低电平后,再逐行检测各列线的电平状态。
若某列为低,则该列线与置为低电平的行线交叉处的按键就是闭合的按键。
5.下面给出一个具体的例子:8031单片机的P1口用作键盘I/O口,键盘的列线接到P1口的低4位,键盘的行线接到P1口的高4位。
列线P1.0-P1.3分别接有4个上拉电阻到正电源+5V,并把列线P1.0-P1.3设置为输入线,行线P1.4-P.17设置为输出线。
经典的矩阵键盘扫描程序

键盘是单片机常用输入设备,在按键数量较多时,为了节省I/O口等单片机资源,一般采取扫描的方式来识别到底是哪一个键被按下。
即通过确定被按下的键处在哪一行哪一列来确定该键的位置,获取键值以启动相应的功能程序。
4*4矩阵键盘的结构如图1(实物参考见万用板矩阵键盘制作技巧)。
在本例中,矩阵键盘的四列依次接到单片机的P1.0~P1.3,四行依次接到单片机的P1.4~P1.7;同时,将列线上拉,通过10K电阻接电源。
查找哪个按键被按下的方法为:一个一个地查找。
先第一行输出0,检查列线是否非全高;否则第二行输出0,检查列线是否非全高;否则第三行输出0,检查列线是否非全高;如果某行输出0时,查到列线非全高,则该行有按键按下;根据第几行线输出0与第几列线读入为0,即可判断在具体什么位置的按键按下。
下面是具体程序:1 / 2void Check_Key(void){unsigned char row,col,tmp1,tmp2;tmp1 = 0x10; //tmp1用来设置P1口的输出,取反后使P1.4~P1.7中有一个为0for(row=0;row<4;row++) // 行检测{P1 = 0x0f; // 先将p1.4~P1.7置高P1 =~tmp1; // 使P1.4~p1.7中有一个为0tmp1*=2; // tmp1左移一位if ((P1 & 0x0f) < 0x0f) // 检测P1.0~P1.3中是否有一位为0,只要有,则说明此行有键按下,进入列检测{tmp2 = 0x01; // tmp2用于检测出哪一列为0for(col =0;col<4;col++) // 列检测{if((P1 & tmp2)==0x00) // 该列如果为低电平则可以判定为该列{key_val =key_Map[ row*4 +col ]; // 获取键值,识别按键;key_Map为按键的定义表return; // 退出循环}tmp2*=2; // tmp2左移一位}}}} //结束这是一种比较经典的矩阵键盘识别方法,实现起来较为简单,程序短小精炼。
键盘扫描显示实验原理及分析报告

键盘扫描显示实验原理及分析报告学 院 计算机工程学院专 业 计算机科学与技术年级班别 09计算机科学与技术1班学 号 2009404010131学生姓名 李雅旖指导教师 李 永2012年01月JINGCHU UNIVERSITY OF TECHNOLOGY目录一、内容提要二、实验目的三、实验要求四、实验器材五、实验电路六、实验说明七、实验框图八、实验程序九、实验分析十、实验心得十一、参考文献一、内容提要单片机技术日趋成熟的今天,其灵活的硬件电路的设计和软件的设计,让单片机得到了广泛的应用,几乎是从小的电子产品,到大的工业控制,单片机都起到了举足轻重的作用。
单片机在人们的生活中得到广泛的应用。
本文介绍了基于单片机的键盘扫描显示实验,详细讨论了它从软件上实现的过程,以及硬件接口的原理及其实现,根据输出的列码和读取的行码来判断按下的是什在么键,即有按键时向列扫描码地址(0e101H)逐列输出低电平,然后从行码地址(0e103H)读回,理解读取键盘按键的原理,和最简单的单片机接口原理二、实验目的:1、掌握键盘和显示器的接口方法和编程方法。
2、掌握键盘扫描和LED八段数码管显示器的工作原理。
二、实验要求:在上一个实验的基础上,利用实验仪提供的键盘扫描电路和显示电路,做一个扫描键盘和数码显示实验,把按键输入的键码在六位数码管上显示出来。
实验程序可分成三个模块:1、键输入模块:扫描键盘、读取一次键盘并将键值存入键值缓冲单元。
2、显示模块:将显示单元的内容在显示器上动态显示。
3、主程序:调用键输入模块和显示模块。
三、实验器材:1、超想-3000TC综合实验仪 1 台2、KEIL仿真器 1 台3、计算机 1 台四、实验电路:这里只是键盘草图,详细原理参见“8155键显模块”。
五、实验说明:本实验仪提供了一个6×4的小键盘,向列扫描码地址(0e101H)逐列输出低电平,然后从行码地址(0e103H)读回,如果有键按下,则相应行的值应为低,如果无键按下,由于上拉的作用,行码为高.这样就可以通过输出的列码和读取的行码来判断按下的是什么键。
键盘扫描原理

笔记本键盘的总类:美式、英式、日本各个键盘的区别:键盘的扫描方式:逐行扫描法与线反转法现在的笔记本键盘一般都是16+8的方式,即16个pin输出,对应列;8个输入pin脚,对应行。
键盘输入与输出的结构如下:在Idel状态下,EC把16条输出线全部拉低,使能键盘扫描中断,这样当任意一个按键按下时,就会触发中断(ICU的INT11h),然后EC就开始逐列扫面,比如OUT(0,1,……,15)输出(1,1,……,1,0),(1,1,……,0,1)……(0,1,……,1,1),当数一个列扫描码,得到的行如输入信号为有一个为0的时候,这是得到的列扫描码与行扫描码就是这个键的扫面码。
比如上图按下S6的时候,列与行扫描码就分别为1101,1011。
然后通过扫描码在Scan table里面找对应的键码,传给OS,确定是哪个键。
在上面的图中,我们看到,在输入信号每个上面都有上拉电阻,这个电阻必须有除非EC的输入pin脚上面的有足够的上拉能力,否则扫描就会出现错误。
下图中,是一个正常的键盘矩阵图。
键盘上面的数字就与下面矩阵里面相同的数字对应。
普通键盘结构及工作原理键盘一般有独立式和行列式(矩阵式)两种。
当然还有其它的结构,比如交互式结构等等,不过其它的结构比较少用,在这里就不介绍了。
在中颖的单片机中,有些单片机的LCD 驱动引脚的SEGMENT 口可以共享按键扫描口,当选择为按键扫描口时,可以使用这些口来扫描按键,所以在外部电路可以连接LCD 和按键矩阵,采用分时扫描进行处理,下面也将介绍这个特殊应用的方法和注意的地方。
1、独立式键盘结构独立式键盘是指各个按键相互独立地连接到各自的单片机的I/O 口,I/O口只需要做输入口就能读到所有的按键。
独立式键盘可以使用上拉电阻也可以使用下拉电阻,基本原理是一样的。
使用上拉电阻的独立式键盘结构如图1-3 所示。
(上面这个图是有问题的,应该是行列式的键盘)图1-3 所示的是利用PB 口和PC 口共8 个I/O 口独自连接8 个按键,使用外部上拉电阻构成的独立式键盘。
按键扫描讨论

我也觉得现在在网上的资料要么是供初学者用的, 要么是功能很强, 但是只是演示性质 (晒) , 或者是卖广告的。 幸亏我们这个论坛的高手们都不吝赐教啊!代表所有初学者向你们致敬! 再说说楼主所提到的释放 CPU、按键处理,我简单地说说我的看法(仅供参考) 。 释放 CPU:在你所建立的工程不是很复杂并且实时性要求不高的时候,你不懂这个概念 的话貌似问题不大,但是倘若你所设计的系统实时性要求较强时,你没有考虑过释放 CPU,
那你做出来的系统将是问题多多的。 举个例子:做一个简单的门禁系统(真的是很简单的,高手们看到不能偷笑哦) ,有上位 机、下位机,下位机需要串口与上位机进行通讯,两者的通讯协议是多字节的帧结构;下位 机需要扫描按键,检查是否有按键按下,按键是由数字键和几个功能键组成;还要 LCD 显 示。 对于这个系统,按键扫描可采用“零耗时扫描”以及查表法来选择返回键码值的方式,这样 设计的话,按键消抖处理的延时就可以用定时器来完成,不用 CPU 去软件延时;键盘扫描 利用查表法的话, 可以使得程序结构简单, 不用太多的重复, 也不用一大堆 switch{case:……} 结构,整个键盘扫描程序就一个循环查表搞定。 与上位机通信这个模块,可以声明两个缓冲区,一个缓冲区(buffer1)是放置当前在接收 中的帧,另外一个(buffer2)是放置已经接收完的帧。帧接收工作最好放在串口中断中完成, 当接收完成即将 buffer1 的内容转到 buffer2 当中去,并将接收完成标志置 1,让主程序去处 理帧。 如此一来,主程序就没有延时语句,就是循环判断各个标志位,若标志有效才去工作。 按键处理:对于 4X4 键盘,可能很多像我一样的初学者都用或者用过类似下面程序的方 法去扫描。下面说说基于查表法的键盘扫描方法 unsigned char key_check(void) { unsigned char code table[]={0x01,0x02,0x03,0x0a, 0x04,0x05,0x06,0x0b, 0x07,0x08,0x09,0x0c, 0x0f,0x00,0x0e,0x0d}; unsigned char temp; unsigned char key; unsigned char i,j; unsigned char key_number=0xff; unsigned int kk=0; while(kk<=2) { kk=kk+1; P2=0xff; P2_4=0; temp=P2; temp=temp&0x0f; if (temp!=0x0f) { for(i=100;i>0;i--) for(j=200;j>0;j--); temp=P2; temp=temp & 0x0f; if (temp!=0x43;; if(num_check==10)//连续 10 次(10ms)低电平有效,则认为按键有效 { key_flag=1;//使能按键有效标识 temp_code=temp;//保存按键值 } } else//松手时判断 { num_check=0; if(key_flag==1)//按键有效 { key_flag=0; switch(temp_code)//读取按键号 { case 0xE0: num_key=1; break; case 0xD0: num_key=2; break; case 0xB0: num_key=3; break; case 0x70: num_key=4; break; } } } return(num_key); }
打破思维定式--两种键盘扫描方法比较分析剖析

打破思维定式--两种键盘扫描方法比较分析说到键盘扫描,相信大多数人第一反应就是行列矩阵扫描,这样我们可以用相对有限的IO口得到尽可能多的按键。
键盘扫描是单片机技术的一种基本处理方法,学校的单片机课程都会有相应章节进行阐述,只要按照课本上讲述的方法,一般都能设计出比较可靠的键盘扫描电路与程序。
课本上的键盘扫描方法(见下图接法二)不能说是尽善尽美,从易懂性、成本、程序难易程度等方面综合看应该是不错的方法,给人感觉是已经没有太多的改善空间,至少说到键盘扫描,相信大多数人第一反应就是行列矩阵扫描,这样我们可以用相对有限的IO口得到尽可能多的按键。
键盘扫描是单片机技术的一种基本处理方法,学校的单片机课程都会有相应章节进行阐述,只要按照课本上讲述的方法,一般都能设计出比较可靠的键盘扫描电路与程序。
课本上的键盘扫描方法(见下图接法二)不能说是尽善尽美,从易懂性、成本、程序难易程度等方面综合看应该是不错的方法,给人感觉是已经没有太多的改善空间,至少我是这么认为的。
然而前段时间一位台湾朋友画给我的键盘扫描矩阵电路(见下图接法二),让我又一次看到到自己的思维还有许多地方被自己的所谓“经验”束缚着。
单纯的从硬件接法看,两种接法并没有明显区别,接法一甚至要复杂一些,但如果结合到键盘扫描的程序来看,就会发现接法一确实更好。
两种接法我都没有把上拉电阻包含进来,来让我们看一下两种接法到底有什么不同:接法二:我们熟悉的传统扫键处理电路,假定键盘行列IO口标号分别为H1/H2/H3和V1/V2/V3,扫键流程通常如下。
2.1. H1设置为输出,H2/H3和V1/V2/V3设置为输入2.2. H1分别输出1和0,读V1/V2/V3状态,如果Vy状态与H1一致,则认为H1与Vy交叉位置的键按下2.3. H2设置为输出,H1/H3和V1/V2/V3设置为输入2.4. H2分别输出1和0,读V1/V2/V3状态,如果Vy状态与H2一致,则认为H2与Vy交叉位置的键按下2.5. H3设置为输出,H1/H2和V1/V2/V3设置为输入2.6. H3分别输出1和0,读V1/V2/V3状态,如果Vy状态与H3一致,则认为H3与Vy交叉位置的键按下接法一:新扫键处理电路,假定键盘行列IO口标号分别为H1/H2/H3和V1/V2/V3,扫键流程通常如下。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
经典案例分享:两种键盘扫描方法比较分析
说到键盘扫描,相信大多数人第一反应就是行列矩阵扫描,这样我们可以用相对有限的IO口得到尽可能多的按键。
键盘扫描是单片机技术的一种基本处理方法,学校的单片机课程都会有相应章节进行阐述,只要按照课本上讲述的方法,一般都能设计出比较可靠的键盘扫描电路与程序。
课本上的键盘扫描方法(见下图接法二)不能说是尽善尽美,从易懂性、成本、程序难易程度等方面综合看应该是不错的方法,给人感觉是已经没有太多的改善空间,至少我是这幺认为的。
然而前段时间一位台湾朋友画给我的键盘扫描矩阵电路(见下图接法二),让我又一次看到到自己的思维还有许多地方被自己的所谓经验束缚着。
单纯的从硬件接法看,两种接法并没有明显区别,接法一甚至要复杂一些,但如果结合到键盘扫描的程序来看,就会发现接法一确实更好。