最近在学习单片机的按键检测,开发板附带的源程序是那种很麻烦的条件判断的方法。自己嫌麻烦,所以自己上网查,自己编写搞了一个查表法的键盘检测程序,实现的更能是在矩阵键盘上按下相应数字的的按键时,在数码管上显示器平方。和大家分享一下,下面是源程序:
/*********************************************************
标题:矩阵键盘检测
版本:2.0(Modify by Jack)
Target:89C52
函数描述: char gotkey(void)
从4ⅹ4小键盘输入数据,返回1至16
小键盘的连接方式:(可以修改为自己的连接方式)
1 P3.0(E) -----1-----2----3----4--
十六进制: EE ED EB E7
| | | |
2 P3.1(D) -----5----6----7----8---
十六进制: DE DD DB D7
| | | |
3 P3.2(B) -----9----10---11---12---
十六进制: BE BD BB B7
| | | |
5 P3.3(E) ---------| | | |
| | |
6 P3.4(D) ---------------| | |
| |
7 P3.5(B) -----------------------| |
|
8 P3.6(7) -------------------------------|
**********************************************************/
#include <reg52.h>
typedef unsigned int u16;
typedef unsigned char uChar;
uChar Flag,bai,shi,ge;
u16 temp;
sbit DULA=P2^6;
sbit WELA=P2^7;
/*组合键值码,每个值对应一个键按下*/
uChar code key_code[16]=
{
0xEE,0xDE,0xBE,0x7E,
0xED,0xDD,0xBD,0x7D,
0xEB,0xDB,0xBB,0x7B,
0xE7,0xD7,0xB7,0x77
};
/*P3_3-P3_6扫描码*/
uChar code ksp[4]={0xFE,0xFD,0xFB,0xF7};
//数码管显示数字编码表
uChar code ShuMaGuanDuanXuan[]=
{
0x3f,0x06,0x5b,0x4f,
0x66,0x6d,0x7d,0x07,
0x7f,0x6f,0x77,0x7c,
0x39,0x5e,0x79,0x71
};
//数码管位选编码表
uChar code ShuMaGuanWeiXuan[]=
{
0xfe,0xfd,0xfb,0xf7,
0xef,0xdf
};
unsigned char gotkey();
void Delay (void);
void Display(uChar bai,uChar shi,uChar ge);
void main()
{
EA=1;
ET0=1;
TR0=1;
TMOD=0x01;
TH0=(65536-10000)/256;
TL0=(65536-10000)%256;
while(1)
{
temp=gotkey();
temp=temp*temp;
bai=temp/100;
shi=temp%100/10;
ge=temp%10;
}
}
void Timer0_Interrupt() interrupt 1
{
TH0=(65536-800)/256;
TL0=(65536-800)%256;
Flag++;
if(Flag>=2)
{
Flag=0;
Display(bai,shi,ge);
}
}
void Display(uChar bai,uChar shi,uChar ge)
{
DULA=1;
P0=ShuMaGuanDuanXuan[bai];
DULA=0;
P0=0xff;
WELA=1;
P0=ShuMaGuanWeiXuan[0];
WELA=0;
Delay();
DULA=1;
P0=ShuMaGuanDuanXuan[shi];
DULA=0;
P0=0xff;
WELA=1;
P0=ShuMaGuanWeiXuan[1];
WELA=0;
Delay();
DULA=1;
P0=ShuMaGuanDuanXuan[ge];
DULA=0;
P0=0xff;
WELA=1;
P0=ShuMaGuanWeiXuan[2];
WELA=0;
Delay();
}
/* 时间延迟函数 */
void Delay (void)
{
unsigned char i,j;
for (i=0;i<=1;i++)
for(j=0;j<=150;j++);
}
/**********************************************************
*键盘扫描函数
**********************************************************/
uChar keypad_scan()
{
uChar key,i;
P1=0xF0; //P1赋值00001111
while (P1==0xF0); //如果P1等于0x0F,说明没有按键被按,循环等待按键按下。如果P1不等于00001111,就说明有键按下.
do
{
for(i=0;i<=3;i++) //循环扫描4次
{
P1=ksp[i]; //依次赋值扫描码0xFE,0xFD,0xFB,0xF7
if(P1!=ksp[i]) //P1不等于以上4种状态就说明有键按下
{
Delay(); //延时去抖动
key=P1; //读入P1的状态
if(key!=ksp[i]) //确定键是否真的按下
{
return(key); //返回扫描码
}
}
}
} while(1);
}
/**********************************************************
检查是否有按键按下
**********************************************************/
uChar gotkey()
{
uChar temp,i;
temp=keypad_scan();
for (i=0;i<=11;i++) //与键值码逐一比较直到相等就返回键的ID号
{
if(temp==key_code[i])//不相等就说明没有键按下,返回0.
return(i+1);
}
return(0);
}