基于51單片機(jī)的倒計時器設(shè)計
//為了節(jié)約端口8個位接在了74hc138上,由P2.1 P2.0 P2.2控制譯碼器輸出位選.
//本程序完全測試通過.完整代碼下載地址:http://www.51hei.com/f/djsq.rar
/************************************************************************/
/************8位數(shù)碼管倒計時顯示 時間格式24—00—00~~00-00-00**************/
/************************************************************************/
#include
#define uchar unsigned char
#define uint unsigned int
sbit D0=P2^0; //定義數(shù)碼管片選參數(shù)
sbit D1=P2^1;
sbit D2=P2^2;
sbit D3=P1^2; //定義蜂鳴器輸出引腳
#define CLOCK_NUM 4 //動態(tài)定義鬧鐘的個數(shù)
struct SAVE_TIME {
uint save_hour;
uint save_minute;
uint save_second;
};
void key_scan_pro(void);
void Displaypro(void);
void Print_play_pro(void);
struct SAVE_TIME save_time[CLOCK_NUM]={0};
uchar code tab[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f}; //共陰極數(shù)碼管0—9
uchar StrTab[8]; //定義緩沖區(qū)
static uint minute=0,hour=24,second=0; //定義并初始化為 24:00:00
static uchar num=0;
static uchar temp,count1=1;
static uchar time_save_value=0;
void delay(uint z) //按鍵消抖延時函數(shù)
{
uint x,y;
for(x=z; x>0; x--)
for(y=110; y>0; y--);
}
void hour_add_pro(void) //小時加一減一處理函數(shù) KEY0
{
if(24==hour) { hour=24; minute=0; second=0; } //小時為24時,將分鐘和秒置零
else { hour++; }
Displaypro();
}
void hour_sub_pro(void) //KEY1
{
if(0==hour) { hour=0; }
else { hour--; }
Displaypro();
}
void minute_add_pro(void) //分鐘加一減一處理函數(shù) KEY2
{
if(59==minute) { minute=59; }
else
{
if((24==hour)&&(minute==0)){} //分鐘邊界壓力判斷,當(dāng)24:00:00,不允許往上加
else { minute++; }
}
Displaypro();
}
void minute_sub_pro(void) //KEY3
{
if(0==minute) { minute=0; }
else { minute--; }
Displaypro();
}
void second_add_pro(void) //秒加一減一處理函數(shù) KEY4
{
if(60==second) { second=60; }
else //秒邊界壓力判斷 當(dāng)24:00:00,不允許往上加
{
if((24==hour)&&(minute==0)) {}
else { second++; }
}
Displaypro();
}
void second_sub_pro(void) //KEY5
{
if(0==second) { second=0; }
else { second--; }
Displaypro();
}
void begin_suspend_pro(void) //開始/暫停處理函數(shù)
{ TR0 ^=0x1; }
void time_save_pro(void) //定時值保存函數(shù)
{
if(time_save_value
save_time[time_save_value].save_hour = hour;
save_time[time_save_value].save_minute = minute;
save_time[time_save_value].save_second = second;
time_save_value++;
if(CLOCK_NUM==time_save_value) //循環(huán)調(diào)用鬧鐘
{ time_save_value=0; }
}
}
void clock_judge_pro(void) //鬧鐘值判斷函數(shù)
{
uchar i;
for(i=0; i< CLOCK_NUM; i++)
{ if((hour==save_time[i].save_hour)&&(minute==save_time[i].save_minute)&&(second==save_time[i].save_second))
{ TR0=0; TR1=1; } }
}
void time_init_pro(void) //定時器初始化函數(shù)
{
TMOD |=0x01; //定時器0 10ms inM crystal 用于計時
TH0=0xd8; //定時器初值10ms
TL0=0xf0;
ET0=1; //定時器/計數(shù)器T0中斷允許位
TR0=0; //TCON寄存器的TR0位 1:啟動T1/0 0:停止T1/0
TMOD |=0x10; //定時器1用于處理蜂鳴器
TH1=0xd8; //初值20ms
TL1=0xf0;
ET1=1;
TR1=0; //定時器的允許位
EA =1; //開總中斷
}
/********************************主函數(shù)***************************************/
void main(void)
{
time_init_pro(); //調(diào)用定時器初始化函數(shù)
Displaypro(); //調(diào)用顯示函數(shù)
while(1)
{
key_scan_pro(); //不斷掃描按鍵
}
}
/********************************主函數(shù)***************************************/
void key_scan_pro(void) //鍵盤掃描函數(shù)
{
D3=1;
Print_play_pro(); //調(diào)用顯示處理函數(shù)
P1=0xfe; temp=P1; temp&=0xf0;
while(temp!=0xf0) //按鍵消抖
{
delay(6); temp=P1; temp&=0xf0;
while(temp!=0xf0)
{
temp=P1;
switch(temp)
{
case 0xee: num=0;
hour_add_pro(); //按鍵0,1控制小時
break;
case 0xde: num=1;
hour_sub_pro();
break;
case 0xbe: num=2; //按鍵2,3控制分鐘
minute_add_pro();
break;
case 0x7e: num=3;
minute_sub_pro();
break;
default:
break;
}
while(temp!=0xf0)
{ temp=P1; temp&=0xf0; }
delay(6);
while(temp!=0xf0)
{ temp=P1; temp&=0xf0; }
}
}
P1=0xfd; temp=P1; temp&=0xf0;
while(temp!=0xf0)
{
delay(6); temp=P1; temp&=0xf0;
while(temp!=0xf0)
{
temp=P1;
switch(temp)
{
case 0xed: num=4; //按鍵4,5控制秒
second_add_pro();
break;
case 0xdd: num=5;
second_sub_pro();
break;
case 0xbd: num=6; //按鍵6控制開始/暫停處理函數(shù)
begin_suspend_pro();
break;
case 0x7d: num=7; //按鍵7控制定時保存函數(shù)
time_save_pro();
break;
default:
break;
}
while(temp!=0xf0)
{ temp=P1; temp&=0xf0; }
delay(6);
while(temp!=0xf0)
{ temp=P1; temp&=0xf0; }
}
}
}
評論