📄 kyxp.c
字号:
//******************个位显示列号码,十位显示行号码,百位显示键值****************************************//
#include "reg51.h"
#define displaycan P0 //定义P0口为显示的位选输出口,由于P0口用S8550做放大,数码管是共阳极,所以P0口是低电平有效//
#define displaydata P2 //定义P2口为显示的段码输出口,数码管为共阳极,所以P2低电平有效//
sbit row1=P1^4;
sbit row2=P1^5;
sbit row3=P1^6;
sbit row4=P1^7; //定义了行号,将可读性不强的P1^*,映射成可读性很好的row*,便于理解//****row 行***//
sbit line1=P1^0;
sbit line2=P1^1;
sbit line3=P1^2;
sbit line4=P1^3; //定义了列号,将可读性不强的P1^*,映射成可读性很好的line*,便于理解//***line 列***//
unsigned int m=0; //同一数据类型相加,避免不同数据类型。
unsigned char code displaydatabase[18]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71,0xff,0xbf};
//共阴LED段码表 "0" "1" "2" "3" "4" "5" "6" "7" "8" "9" "a" "b" "c" "d" "e""f" "不亮" "-" //
unsigned char code displaycanbase[7]={0xFE,0xFD,0xFB,0xF7,0xef,0xdf,0xff};
//列扫描控制字 "个位" "十位" "百位" "千位" "全部关闭"//
unsigned data shuju[7]={0x3f,0x3f,0x3f,0x3f,0x3f,0x3f,0x3f};
unsigned data shuju1[3]={0x3f,0x3f,0x3f};
//数据暂时存放,可以叫做数据缓存,存放由矩阵键盘识别来的数据//
unsigned char key,i,j;
unsigned char flog=0;
unsigned char flog1=0;
unsigned char gg=0;
//*****************11us延时函数*************************//
void delay(unsigned int t)
{
for (;t>0;t--);
}
//******************显示扫描函数***************************/
void scan()
{
unsigned int k;
for(k=0;k<6;k++)
{
displaydata=shuju[k];//段码数据查询并将信号输出//
displaycan=displaycanbase[k]; //位选数据查询并将信号输出//
delay(30) ; //延时
displaycan=displaycanbase[6]; //位选信号输出. 及时关闭位选信号,如果去掉这条语句,会发现数码管上出现了“鬼影”//
}
}
//******************键盘扫描程序********************//
unsigned char keycan(void)
{
unsigned char rnum,lnum;//用于记录行号和列号//
P1=0xf0;
if(P1!=0xF0)
{ delay(40); //延时去抖动// //初始状态下,列线为高电平,行线为低电平,以此拉高行线,确定行号//
if(P1!=0xF0)
{
//**********下面分别查找行号和列号********************//
line1=1;
if((P1&0xF0)==0XF0)
{lnum=1;} //一行检测//
line1=0;
line2=1;
if((P1&0xF0)==0XF0)
{lnum=2;} //二行检测//
line2=0;
line3=1;
if((P1&0xF0)==0XF0)
{lnum=3;} //三行检测//
line3=0;
line4=1;
if((P1&0xF0)==0XF0)
{lnum=4;} //四行检测//
//**********对行号的检测到此处结束,下面对列进行检测*************//
P1=0x0F; //切换电平状态,便于检测//
row1=1;
if((P1&0x0F)==0x0F)
{rnum=12;} //一列检测//
row1=0;
row2=1;
if((P1&0x0F)==0x0F)
{rnum=8;} //二列检测//
row2=0;
row3=1;
if((P1&0x0F)==0x0F)
{rnum=4;} //三列检测//
row3=0;
row4=1;
if((P1&0x0F)==0x0F)
{rnum=0;} //四列检测//
}
row4=0;
P1=0x0f;
do{scan();}while((P1&0x0F) != 0x0F); //等待键释放
gg=1;
return ( rnum+ lnum ); // 返回键编码
}
}
void angorfre()
{
if(key==11)
flog=1;
if(key==12)
flog=2;
if(key==13)
flog=3;
//if(key==14);
// flog1=4;
}
/****************主程序*******************/
main()
{
unsigned char key;
while(1)
{ //******在这里如果不加while()语句,单片机会循环运行,并且每次都将 ************************//
key=keycan(); //******各个存储器中的值还原为处置,也就是我们在前面的“有反应的初级键盘”和“显示********//
//******行列号的键盘”中所看到的,按键数据会变化,但是松开手,数据又返回了零*************//
//############################################//
if(key==10)
key=0;
//angorfre(); ///调用此函数时键盘输入输出没反映
if(key==11)
{
j=0;
flog=1;
for(i=3;i<6;i++)
{
shuju1[i-3]=shuju[i];
shuju[i]=0x00;
}
}
if(key==12)
{
j=0;
flog=2;
for(i=0;i<3;i++)
{
shuju1[i]=shuju[i];
shuju[i]=0x00;
}
}
if(key==13)
flog1=1;
if((gg==1)&&(flog==1))
{
if(flog1==1)
{
flog=0;
flog1=0;
if(j==0)
{
for(i=3;i<6;i++)
shuju[i]=shuju1[i-3];
}
}
if(key<10)
{
//shuju[7]=shuju[3];
if(j<3)
{
shuju[j+3]=displaydatabase[key];
j++;
}
else
j=3;
}
gg=0;
}
if((gg==1)&&(flog==2))
{
if(flog1==1)
{
flog=0;
flog1=0;
if(j==0)
{
for(i=0;i<3;i++)
shuju[i]=shuju1[i];
}
}
if(key<10)
{
//shuju[7]=shuju[0];
if(j<3)
{
shuju[j]=displaydatabase[key];
j++;
}
else
j=3;
} //每一次按键,只做一次位转移//
gg=0;
}
//############################################//
scan();
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -