實驗環(huán)境
軟件: Keil5+Proteus7
元件(主要):
AT89C51 * 1,
BUTTON * 1,
7SEG-MPX2-CA * 1,
LED-GREEN * 8,
LED-RED * 4,
LED-YELLOW * 4
實驗原理
7SEG-MPX2-CA數(shù)碼管
7SEG-MPX2-CA數(shù)碼管是一個兩位數(shù)的陽極數(shù)碼管,有10個針腳,通過標號a-dp八個針腳控制,LED燈的顯示,通過標號為1,2的針腳控制顯示的是個位或是十位的數(shù)碼管。
要通過數(shù)碼管顯示具體數(shù)字,7SEG-MPX2-CA由于是一個陽極的數(shù)碼管,所以需要接收在針腳上接收相應的低電平來顯示,如如果要顯示數(shù)字0,則標號a-dp的針腳需要接收1100 0000也就是0xF9的信號,同時如果不設置針腳1,2信號,便會個,十位都顯示相同的數(shù)字1,于是需要通過對針腳1設置低電平,針腳2設置為高電平實現(xiàn)個位的發(fā)光,相反設置則十位的發(fā)光。
通過人眼的余暉效應,我們可以設置1,2信號變化,來讓兩個單片機顯示自己想要的不同數(shù)字,由于人眼的分辨頻率,遠遠跟不上數(shù)碼管閃爍的頻率,雖然是個十位數(shù)碼管,不同時間進行閃爍,但在人眼看來仿佛是一起亮起來的。
計時器/計數(shù)器
定時/計數(shù)器T0和T1分別是由兩個8位的專用寄存器組成,即定時/計數(shù)器T0由TH0和TL0組成,T1由TH1和TL1組成。此外,其內(nèi)部還有2個8位的特殊功能寄存器TMOD和TCON,TMOD負責控制和確定T0和T1的功能和工作模式,TCON用來控制T0和T1啟動或停止計數(shù),同時包含定時/計數(shù)器的狀態(tài)。
16位的定時器/計數(shù)器實質(zhì)上就是一個加1計數(shù)器,其控制電路受軟件控制、切換。 當定時器/計數(shù)器為定時工作方式時,計數(shù)器的加1信號由振蕩器的12分頻信號產(chǎn)生,即每過一個機器周期,計數(shù)器加1,直至計滿溢出為止。
定時器的定時時間與系統(tǒng)的振蕩頻率有關。因一個機器周期等于12個振蕩周期,所以計數(shù)頻率fcount=1/12osc。
兩個字節(jié)最大數(shù)據(jù)為65536(十進制),或者0FFFFH。
高字節(jié)為TH0=(65536-X)/256,就是除以256后的整數(shù)部分。
低字節(jié)為TL0=(65536-X)%256,減去高字節(jié)后余下的部分。
代碼實現(xiàn)
//名稱: LED模擬交通燈
#include
#define uint unsigned int
#define uchar unsigned char
#define SEG P3
sbit E_RED=P0^0; //東西紅燈
sbit E_YELLOW=P0^1;//東西黃燈
sbit E_GREEN=P0^2;//東西綠燈
sbit N_RED=P0^3;//南北紅燈
sbit N_YELLOW=P0^4;//南北黃燈
sbit N_GREEN=P0^5;//南北綠燈
sbit E_LEFT=P0^6; //南轉(zhuǎn)東向綠燈亮,北轉(zhuǎn)西向綠燈亮
sbit N_LEFT=P0^7;//東轉(zhuǎn)北綠燈亮,西轉(zhuǎn)南的綠燈亮
sbit btn = P1^0; //外部中斷開關
/*sbit P30=P3^0; //測試led燈是否能亮
sbit P31=P3^1;
sbit P32=P3^2;
sbit P33=P3^3;
sbit P34=P3^4;
sbit P35=P3^5;
sbit P36=P3^6;
sbit P37=P3^7;*/
sbit SCON1 = P2^0;//控制數(shù)碼管個位十位顯示
sbit SCON2 = P2^1;
uchar num=10,ge,shi; //定義倒計時初始值
uchar a=0;//定義交通燈種類
uchar count=0; //控制兩位數(shù)碼管
uchar flag;//計時器是否達到1s
//定義表格存放共陽極LED的點陣碼
unsigned char code ledTab[]={
0xC0, // 1100 0000 數(shù)字0
0xF9, // 1111 1001 數(shù)字1
0xA4, // 1010 0100 數(shù)字2
0xB0, // 1011 0000 數(shù)字3
0x99, // 1001 1001 數(shù)字4
0x92, // 1001 0010 數(shù)字5
0x82, // 1000 0010 數(shù)字6
0xF8, // 1111 1000 數(shù)字7
0x80, // 1000 0000 數(shù)字8
0x90 // 1001 0000 數(shù)字9
};
//type = 1;//操作類型變量
//i = 0;//循環(huán)變量
//1毫秒延遲子程序
void Delay_Ms(uint x){
uchar t;
while(x--)
{
for(t=50;t>0;t--);
}
}
int0()interrupt 0
{
TR0=~TR0;
}
//緊急暫停函數(shù)
void stop(){
//當按鈕接受到低電平的時候,停止倒計時,所有路口變成紅燈
if(btn==0){
Delay_Ms(1000);//取消抖動
TR0=~TR0; //停止倒計時
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 0;E_YELLOW = 1;E_GREEN = 1; E_LEFT=1;
}
}
//交通燈切換程序 此程序采用共陽極接法,所以低電平0有效
/*void traffic_light()
{
switch (type)
{
case 1: //南北綠,東西紅
N_RED = 1;N_YELLOW = 1;N_GREEN = 0; N_LEFT=1;
E_RED = 0;E_YELLOW = 1;E_GREEN = 1; E_LEFT=1;
Delay_Ms(5000);
type = 2;
break;
case 2: //南北閃黃燈,東西紅燈
N_RED=1;N_YELLOW = 0; N_GREEN=1; N_LEFT=1;
E_RED=0; E_YELLOW =1; E_GREEN=1; E_LEFT=1;
Delay_Ms(5000);
type = 3;
break;
case 3: //南轉(zhuǎn)東向綠燈亮,北轉(zhuǎn)西向綠燈亮
N_RED = 1; N_YELLOW = 1;N_GREEN = 1; N_LEFT=0;
E_RED = 0; E_YELLOW =1; E_GREEN=1; E_LEFT=1;
Delay_Ms(5000);
type = 4;
break;
case 4: //南北閃黃燈,東西紅燈
N_RED = 1;N_YELLOW = 0;N_GREEN = 1; N_LEFT=1;
E_RED = 0; E_YELLOW =1; E_GREEN=1; E_LEFT=1;
Delay_Ms(5000);
type = 5;
break;
case 5: //南北應該亮紅燈,東西要亮綠燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =1; E_GREEN=0; E_LEFT=1;
Delay_Ms(5000);
type = 6;
break;
case 6: //東西閃黃燈,南北亮紅燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =0; E_GREEN=1; E_LEFT=1;
Delay_Ms(5000);
type = 7;
break;
case 7: //東轉(zhuǎn)北綠燈亮,西轉(zhuǎn)南的綠燈亮
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =1; E_GREEN=1; E_LEFT=0;
Delay_Ms(5000);
type = 8;
break;
case 8: //東西閃黃燈,南北亮紅燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =0; E_GREEN=1; E_LEFT=1;
Delay_Ms(5000);
type = 1;
break;
}
}*/
void T0INTinit() //定時器T0初始化1秒
{
TMOD=0x01;
TH0=(65536-50000)/256;
TL0=(65536-50000)%256;
EA=1;
ET0=1;
TR0=1;
}
void T0INT() interrupt 1
{
TH0=(65536-50000) / 256;
TL0=(65536-50000) % 256;
flag++;
if(flag==20)//當定時到1秒時執(zhí)行花括號里面的語句
{
flag=0;
num--;
if (num == 0 && a%2 == 0) //控制黃燈倒計時
{
num = 5;
a++;
} else if (num == 0 && a%2 == 1){ //控制紅綠燈倒計時
num =10;
a++;
}
switch (a%8)
{
case 0: //南北綠,東西紅
N_RED = 1;N_YELLOW = 1;N_GREEN = 0; N_LEFT=1;
E_RED = 0;E_YELLOW = 1;E_GREEN = 1; E_LEFT=1;
break;
case 1: //南北閃黃燈,東西紅燈
N_RED=1;N_YELLOW = ~N_YELLOW; N_GREEN=1; N_LEFT=1;
E_RED=0; E_YELLOW = 1; E_GREEN=1; E_LEFT=1;
break;
case 2: //南轉(zhuǎn)東向綠燈亮,北轉(zhuǎn)西向綠燈亮
N_RED = 1; N_YELLOW = 1;N_GREEN = 1; N_LEFT=0;
E_RED = 0; E_YELLOW =1; E_GREEN=1; E_LEFT=1;
break;
case 3: //南北閃黃燈,東西紅燈
N_RED = 1;N_YELLOW = ~N_YELLOW;N_GREEN = 1; N_LEFT=1;
E_RED = 0; E_YELLOW =1; E_GREEN=1; E_LEFT=1;
break;
case 4: //南北應該亮紅燈,東西要亮綠燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =1; E_GREEN=0; E_LEFT=1;
break;
case 5: //東西閃黃燈,南北亮紅燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW = ~E_YELLOW; E_GREEN=1; E_LEFT=1;
break;
case 6: //東轉(zhuǎn)北綠燈亮,西轉(zhuǎn)南的綠燈亮
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW =1; E_GREEN=1; E_LEFT=0;
break;
case 7: //東西閃黃燈,南北亮紅燈
N_RED = 0;N_YELLOW = 1;N_GREEN = 1; N_LEFT=1;
E_RED = 1; E_YELLOW = ~E_YELLOW; E_GREEN=1; E_LEFT=1;
break;
}
}
}
//主程序
void main(){
T0INTinit();
while(1){//死循環(huán)
stop();
SEG=0xff; //消影,不然只顯示一位
shi = num / 10;
ge = num % 10;
switch(count){
//通過余暉效應,雖然是不同時間,但人眼感覺是一起亮的
case 0: SCON1=0; SCON2=1; SEG=ledTab[ge]; break;
case 1: SCON1=1; SCON2=0; SEG=ledTab[shi]; break;
}
count++;
if(count>1) count=0;
//traffic_light();//不斷執(zhí)行交通燈切換程序
}
}
成果圖
當?shù)褂嫊r結(jié)束時候,進入黃燈閃爍,后在進入紅燈
當按下緊急暫停按鈕后,所有路口變?yōu)榧t燈,倒計時停止,再次點擊后恢復
原文鏈接:https://blog.csdn.net/qq_47200222/article/details/124027531
更多信息可以來這里獲取==>>電子技術(shù)應用-AET<<