利用单片机 AT89C51 的外部中断 0 和中断 1, I/O 口,对 LED 和数码管分别进行控制。以实现按键 K0 时 LED 灯亮灭闪烁,按键 K1 时做 LED 左和右流水运动。无按键操作时偶数位数码管显示 0-F。
使用74LS373可以节省I/O口
74LS373简介:
74LS373是三态输出的八D锁存器,共有54S373和74LS373两种线路。373 的输出端 Q0~Q7 可直接与总线相连。当锁存允许端LE为高电平时,Q 随数据D而变,当LE为低电平时,D 被锁存在已建立的数据电平。
真值表:
电路原理图:
代码如下:有相关的注释
#include <reg51.h>
#include <intrins.h>
#define uchar unsigned char
#define uint unsigned int
sbit a=P2^5; //LED控制
sbit b=P2^6; //数码管赋值控制
sbit c=P2^7; //数码管段选
sbit K0=P3^2;
sbit K1=P3^3;
char d,n;
char t;
//共阴极数码管数字显示表
uchar table[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};
// 对应显示 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
void delay(uint z)
{
uint x,y;
for(x=z;x>0;x--)
{
for(y=110;y>0;y--);
}
}
void int0()interrupt 0 //外部中断0
{
for(d=0;d<5;d++)
{
a=1; //LED赋值控制打开 因为在中断里面操作,所以还需要在打开LED控制,让锁存器赋值
P1=0x00; //赋值
delay(500);
//a=1;
P1=0xFF;
delay(500);
}
}
void int1()interrupt 2 //外部中断1
{
a=1; //开启锁存器控制LED
t=0x7F; //0111 1111
P1=t;
while(1)
{
for(n=0;n<7;n++)
{
P1=t; //初值 //0111 1111
delay(400);
t=_cror_(t,1); //右移
}
for(n=0;n<7;n++)
{
P1=t; //初值 //0111 1111
delay(400);
t=_crol_(t,1); //左移
}
}
}
void main()
{
a=1;
P1=0xff; //数码管关闭
EA=1; //打开总中断开关
EX0=1; //外部中断允许位
EX1=1;//外部中断允许位
PX0=1; //外部中断0高优先级
IT0=0;//外部中断0电平触发方式,低电平有效
IT1=0;//外部中断1电平触发方式,低电平有效
c=1; //打开段选
P0=0x55; //选择数码管 2 4 6 8
c=0; //关闭段选
while(1)
{
for(n=0;n<16;n++)
{
b=1; //开启数码管赋值
P0=table[n]; // 赋值
b=0; //关闭赋值控制
delay(800);
}
}
}
结果展示无按键:
按下K0(外部中断0):
按下K1(外部中断1):
以上电路和代码仅供参考学习。