P1=0xfd;//1111 1011 temp=P1; temp=temp&0xf0;//1111 0000 if(temp!=0xf0) { delay(10); if(temp!=0xf0) { temp=P1; switch(temp) { case 0xed://1110 1011 key=1; key_flag=1; break; case 0xdd: key=4; key_flag=1; break; case 0xbd: key=7; key_flag=1; break; case 0x7d: down=1; key_flag=1; break; default: break; } while(temp!=0xf0)//·ÀÖ¹³¤°´ { temp=P1; temp=temp&0xf0; } } }
时间: 2023-06-19 18:08:57 浏览: 117
这是一段单片机的代码,根据注释可以看出是在读取键盘输入。首先将P1口的值赋给临时变量temp,然后通过与0xf0按位与运算,将temp的低4位清零,只留下高4位。如果temp不等于0xf0(即有按键被按下),则延时10ms,再次读取P1口的值,如果仍然不等于0xf0,则根据temp的值来判断按下的具体按键,并将对应的键值存储在key变量中,同时设置key_flag标志。如果temp等于0xf0,说明按键已经释放,程序会在while循环中等待键松开,然后返回等待下一次按键输入。
相关问题
修正这个C51代码,使数码管左面第一位显示矩阵按键的键值: #include "reg52.h" #include "intrins.h" #define uchar unsigned char uchar code seg[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};//数码管共阴 uchar code colcode[ 4 ]={ 0xfe, 0xfd, 0xfb, 0xf7}; //列依次为0 void delayms(uchar ms) { uchar i; while(ms--) for(i=0;i<123;i++); } uchar key_scan(void)//P1口连矩阵键盘 { uchar temp, row, column, i; P1=0XF0; //行为1,列为0 temp=P1&0XF0; if(temp!=0xf0) { delayms(10); temp=P1&0XF0; if(temp!=0xf0)//发生变化 { switch(temp) { case 0x70: row=3; break; case 0xb0: row=2; break; case 0xd0: row=1; break; case 0xe0: row=0; break; default: break; } for(i=0; i<4; i++) { P1=colcode[i]; temp=P1&0XF0; temp=~temp; if(temp!=0x0f)column=i; } return row*4+column ; } } else P1=0XFF; return 16; } void main(void) { uchar key_val; while(1) { key_val=keyscan(); P0=seg[key_val];//数码管显示键值 delayms(50); } }
在主函数中调用的函数名和定义的函数名不一致,需要将key_scan函数改为keyscan。同时,在主函数中需要将数码管左侧第一位对应的段码赋值给P0的高四位。修改后的代码如下:
```
#include "reg52.h"
#include "intrins.h"
#define uchar unsigned char
uchar code seg[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71}; //数码管共阴
uchar code colcode[4] = { 0xfe, 0xfd, 0xfb, 0xf7 }; //列依次为0
void delayms(uchar ms)
{
uchar i;
while(ms--)
for(i=0; i<123; i++);
}
uchar keyscan(void)//P1口连矩阵键盘
{
uchar temp, row, column, i;
P1 = 0XF0; //行为1,列为0
temp = P1 & 0XF0;
if(temp != 0xf0)
{
delayms(10);
temp = P1 & 0XF0;
if(temp != 0xf0)//发生变化
{
switch(temp)
{
case 0x70: row = 3; break;
case 0xb0: row = 2; break;
case 0xd0: row = 1; break;
case 0xe0: row = 0; break;
default: break;
}
for(i = 0; i < 4; i++)
{
P1 = colcode[i];
temp = P1 & 0XF0;
temp = ~temp;
if(temp != 0x0f) column = i;
}
return row * 4 + column;
}
}
else P1 = 0XFF;
return 16;
}
void main(void)
{
uchar key_val;
while(1)
{
key_val = keyscan();
if(key_val == 0) P0 = (P0 & 0x0f) | (seg[0] << 4);//数码管显示矩阵按键的键值
else P0 = (P0 & 0x0f) | (seg[key_val] << 4);//数码管显示键值
delayms(50);
}
}
```
#include<reg52.h> #include<intrins.h> #define uchar unsigned char #define uint unsigned int uchar temp,t0,n,t1,qian,bai,shi,ge; //char最大只能装256 uchar code table[]={0xc0,0xf9,0xa4, 0xb0,0x99,0x92,0x82,0xf8,0x80,0x90, 0x88,0x83,0xc6,0xa1,0x86,0x8e,0x8c,0x7f,0xff}; uint shu; void display(uchar qian,uchar bai,uchar shi,uchar ge); void delay(uint z); void init(); void main() { init(); while(1) { } } void init()//初始化函数 { shu=432; temp=0xfe; P1=temp; TMOD=0x11; TH0=(65536-50000)/256; TL0=(65536-50000)%256; TH1=(65536-50000)/256; TL1=(65536-50000)%256; TH1=0xd8; TL1=0xf0; EA=1; ET0=1; ET1=1; TR1=1; TR0=1;//控制流水灯 } void timer0() interrupt 1 { TH0=(65536-50000)/256; TL0=(65536-50000)%256; t0++; if(t0==20) { t0=0; temp=_crol_(temp,1); P1=temp; } } void timer1() interrupt 3 { TH0=(65536-50000)/256; TL0=(65536-50000)%256; t1++; if(t1==20) { t1=0; bai=shu/100; shi=shu%100/10; ge=shu%10; qian=0; display(qian,bai,shi,ge); shu--; if(shu==0) { TR0=0; TR1=0; P1=0xff; } } } void display(uchar qian,uchar bai,uchar shi,uchar ge)//定义三个变量 { P0=0xff; P2=0xf7;// 1111 1011 P0=table[qian]; delay(5); P0=0xff; P2=0xfb;// 1111 1011 P0=table[bai]; delay(5); P0=0xff; P0=table[shi]; P2=0xfd; // 1111 1101 delay(5); P0=0xff; P0=table[ge]; P2=0xfe; // 1111 1110 delay(5); } void delay(uint z)//可以带参数 { uint x,y; for(x=z;x>0;x--) { for(y=113;y>0;y--) { } } } 、
这段代码是一个基于8051单片机的数字倒计时程序。它使用了两个定时器来控制流水灯的显示和倒计时功能。具体的功能如下:
1. 引入头文件reg52.h和intrins.h,定义了一些宏和全局变量。
2. 定义了一个数码管显示的编码表table[],其中存储了0-9和一些特殊字符的编码。
3. 定义了一个显示函数display(),用来控制数码管的显示。
4. 定义了一个延时函数delay(),用来产生一定的延时。
5. 定义了一个初始化函数init(),用来初始化各个寄存器和定时器。
6. 在主函数中,调用了初始化函数,并进入一个无限循环。
在定时器0中断函数timer0()中,通过改变P1口的值来实现流水灯效果。
在定时器1中断函数timer1()中,首先计算出百位、十位和个位数,并调用display()函数进行数码管显示。然后将倒计时数shu减1,如果倒计时数为0,则关闭定时器0和定时器1,并将P1口置为全高电平。
整个程序的功能是实现一个倒计时功能,通过数码管显示倒计时的时间。