单片机按键矩阵识别(含程序、原理图)
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
按键矩阵识别技术实验说明
如图2所示,把P1端口的8条I/O口分成4条列线4条行线交叉但不接触构成4×4键盘阵列,16个按键放置交叉位置,这样在单片机复杂系统需要较多按键时,这种接法可以节省单片机的硬件资源。
1.结合给出的电路原理图试分析4*4键盘矩阵识别原理,及LED动态扫描原理。(6分)
2.根据分析的键盘矩阵识别原理设计程序实现一下功能:当按下某个按键时在2个七段数码管上显示该按键的编号(注意考虑同时按下多个按键时程序处理过程)、按下某个按键使其弹起时对于消抖情况程序的处理。(9分)
2.0相关原理图如下:
3.0实验说明
本试验给了1-8键判断方法。按1-8键中任意键,则数码管显示该键编号。
想想怎样实现1-16个键的判断显示?
参考程序见程序范例。
/************************************************************************ ******************
*描述: 按键距阵识别技术
*编写: 秦立春
*版本信息: V1.0 2008年4月20日
*说明: sp1,sp2,SP3跳线向右;
************************************************************************* *****************/
#include
#define uchar unsigned char
#define uint unsigned int
#define ON 0
#define OFF 1
uchar bdata OUT;
sbit JDQ=OUT^0;
sbit HF =OUT^1;
sbit BZ =OUT^2;
sbit AA =OUT^3;
sbit BB =OUT^4;
sbit CC =OUT^5;
sbit DD =OUT^6;
sbit X0=P2^0;
sbit X1=P2^1;
sbit X2=P2^2;
sbit X3=P2^3;
sbit Y0=P2^4;
sbit Y1=P2^5;
sbit Y2=P2^6;
sbit Y3=P2^7;
sbit RS=P1^7;
sbit RW=P3^4;
sbit E =P3^5;
sbit HC574_LE=P3^3;
//-----------------------------------------------------
void delay(unsigned int t) // 延时函数
{
for(;t!=0;t--) ;
}
//------------------------------------------------------ void HC574(void) // 74HC574控制输出;
{
P0=OUT;
HC574_LE=1;
delay(2);
HC574_LE=0;
}
//================================================== unsigned char Key_Scan(void)
{
uchar a, key;
P2=0xf0;
if(!(Y0&&Y1&&Y2&&Y3))
{
P2=0xf0;
delay(200);
if(!(Y0&&Y1&&Y2&&Y3))
{
P2=0xff;
X0=0;
if(!(Y0&&Y1&&Y2&&Y3)){a=P2;a=(a&0xf0+0x0e);goto pp1;}
P2=0xff;
X1=0;
if(!(Y0&&Y1&&Y2&&Y3)){a=P2;a=(a&0xf0+0x0d);goto pp1;} P2=0xff;
X2=0;
if(!(Y0&&Y1&&Y2&&Y3)){a=P2;a=(a&0xf0+0x0b);goto pp1;} P2=0xff;
X3=0;
if(!(Y0&&Y1&&Y2&&Y3)){a=P2;a=(a&0xf0+0x07);goto pp1;} }
else a=0xff;
}
else a=0xff;
pp1: key=a;
return key;
}
//-----------------------------------------------------------
uchar key(void)
{
uchar k, KEY;
KEY=0xff;
k=Key_Scan();
if(k!=0xff)
{
while(k==Key_Scan());
switch(k) // 键码
{
case 0x7e: KEY=0x04;break; // 4
case 0x7d: KEY=0x08;break; // 8
case 0x7b: KEY=0x0b;break; //
case 0x77: KEY=0x0f;break; //
case 0xbe: KEY=0x03;break; // 3
case 0xbd: KEY=0x07;break; // 7
case 0xbb: KEY=0x0a;break; //
case 0xb7: KEY=0x0e;break; //
case 0xde: KEY=0x02;break; // 2
case 0xdd: KEY=0x06;break; // 6
case 0xdb: KEY=0x00;break; // 0
case 0xd7: KEY=0x0d;break; //
case 0xee: KEY=0x01;break; // 1
case 0xed: KEY=0x05;break; // 5
case 0xeb: KEY=0x09;break; // 9
case 0xe7: KEY=0x0c;break; //
default: KEY=0xff;break; // 无键按下
}
}
return KEY;
}
main()
{
uchar code shu[12]={0xc0,0xf9,0xa4,0xb0,0x99,//0,1,2,3,4,
0x92,0x82,0xf8,0x80,0x90,//5,6,7,8,9,
0x00,0xff}; //灭共阳极数码管显示段码 uchar i,k;
uchar display[2]={0xff,0xff};
RS=0; RW=0; E=0;