51单片机100例实例之16例
//项目名称:4*4矩阵键盘控制条形LED
//项目再创作者:科技小宅神
//完成时间:2021/01/21

#include <reg52.h>//c51头文件
#include <intrins.h>//c51内部移位函数
#define uchar unsigned char
#define uint unsigned int
//定义键盘状态数组 k1,k2,k3,k4,k5,k6,k7,k8,k9,k10,k11,k12,k13,k14,k15,k16,1k7,18
uchar code KeyCodeTable[]={0x11,0x12,0x14,0x18,0x21,0x22,0x24,0x28,0x41,0x42,0x44,0x48,0x81,0x82,0x84,0x88};
//延时程序
void Delay(uint x)
{
uchar i;
while(x--)
for(i=0;i<200;i++);
}
//键盘查询子程序
uchar Keys_Scan()
{
uchar hang,lie,i,k;//定义4个局部变量hang,lie,i,k
P1 = 0xf0; //为P1口赋初值1111 0000,即低四位置0,放入4行
if((P1&0xf0)!=0xf0)//(若高4位出现0,则有按键按下)判断是否有按键按下
{
Delay(2);//延时函数进行防抖
if((P1&0xf0)!=0xf0)//(若高4位出现0,则有按键按下)判断是否有按键按下
{
hang = 0xfe;//行扫描初值
for(k=0;k<4;k++)//对4行分别进行扫描
{
P1 = hang;//P1口为1111 0000,此处4个0刚好对应P1.0-P.3等4行
if((P1&0xf0)!=0xf0)//(若高4位出现0,则有按键按下)判断是否有按键按下
{
lie= ~P1;//lie为0000 1111,此处4个0刚好对应P1.4-P.7等4列
for(i=0;i<16;i++)//查表得到按键序号并返回
if(lie == KeyCodeTable[i])//比较按键状态,判断那个按键号
return(i);//返回按键号
}
else
hang = _crol_(hang,1);//比较不成功,循环到下一行
}
}
}
return(-1);//没有按键按下返回-1(-1,一改全改成一样的)
}
//主程序
void main()
{
uchar KeyNO =-1;//按键号 (-1,一改全改成一样的) /*注意程序中-1,是个任意值,可以改成其他的,但是如果改就要全部都改成一样的,否则功能实现不了*/
uchar i,P2_LED,P3_LED;
while(1)//死循环
{
KeyNO = Keys_Scan();//扫描键盘获取按键序号KeyNO
if(KeyNO !=-1)//等于-1代表有按键按下,不等于则代表没有(-1,一改全改成一样的)
{
P2_LED = 0xff;//赋初值使P2口灯全灭
P3_LED = 0xff;//赋初值使P3口灯全灭
for(i=0;i<=KeyNO;i++)//按键号值越大,点亮的LED灯越多
{
if(i<8) P3_LED>>=1;//按键号值小于8,P3_LED右移1位,实际在原理中就是向下移1位
else P2_LED>>=1;//如果不是小于8,P2_LED向右移1位,实际在原理中就是向下移1位
}
//这里安排是给按键号值等于16时,整个条形LED灯可以全部点亮
P3 = P3_LED;
P2 = P2_LED;
}
}
}