|
#include<reg52.h> #define uchar unsigned char #define uint unsigned int uchar a,count,S1num,xqnum; char yue,ri,shi,fen,miao; int nian; sbit lcdrs=P2^0; sbit lcdrw=P2^1; sbit lcden=P2^2; sbit S1=P2^4; //定義鍵——進(jìn)入設(shè)置 sbit S2=P2^5; //定義鍵——增大 sbit S3=P2^6; //定義鍵——減小 sbit S4=P2^7; //定義鍵——退出設(shè)置 uchar code table0[]="2018-10-6 FRI"; uchar code table1[]="00:00:00"; uchar code xingqi[][3]={"MON","TUE","WED","THU","FRI","SAT","SUN"}; void delay(uint z) //延時(shí)1ms的程序 { uint x,y; for(x=z;x>0;x--) for(y=110;y>0;y--); } /************************************************** 1602液晶顯示器模塊 sbit lcdrs=P2^5; sbit lcdrw=P2^4; sbit lcden=P2^3; *************************************************/ void write_com(uchar com) //液晶寫指令 { lcdrw=0; lcdrs=0; P0=com; delay(5); lcden=1; delay(5); lcden=0; } void write_data(uchar dat) //液晶寫數(shù)據(jù) { lcdrw=0; lcdrs=1; P0=dat; delay(5); lcden=1; delay(5); lcden=0; } /******************************************** 年月日寫入1602函數(shù) ********************************************/ void write_sfm(uchar add,uchar dat) //寫時(shí)分秒函數(shù) { uchar shi,ge; shi=dat/10; ge=dat%10; write_com(0x80+0x40+add); write_data(0x30+shi); write_data(0x30+ge); } void write_yr(uchar add,uchar dat) //寫月日函數(shù) { uchar shi,ge; shi=dat/10; ge=dat%10; write_com(0x80+add); write_data(0x30+shi); write_data(0x30+ge); } void write_nian(uchar add,uint dat) //寫年函數(shù) { uint qian,bai,shi,ge; qian=dat/1000; bai=dat%1000/100; shi=dat%100/10; ge=dat%10; write_com(0x80+add); write_data(0x30+qian); write_data(0x30+bai); write_data(0x30+shi); write_data(0x30+ge); } /*************************************************** 初始化 ***************************************************/ void init_lcd() //液晶初始化 { lcden=0; nian=2014; yue=8; ri=13; shi=0; //初始shi、fen、miao fen=0; miao=0; write_com(0x38); //設(shè)置16x2顯示,5x7點(diǎn)陣,8位數(shù)據(jù)口 write_com(0x0c); //設(shè)置開顯示,不顯示光標(biāo) write_com(0x06); //寫一個(gè)字符后地址指針加1 write_com(0x01); //顯示清0,數(shù)據(jù)指針清0 } void init() //初始化函數(shù) { init_lcd(); //液晶初始化 write_com(0x80); //設(shè)置顯示初始坐標(biāo) for(a=0;a<14;a++) //顯示年月日初始值 { write_data(table0[a]); delay(5); } write_com(0x80+0x40); //設(shè)置顯示初始坐標(biāo) for(a=0;a<8;a++) //顯示時(shí)分秒初始值 { write_data(table1[a]); delay(5); } write_nian(0,nian); write_sfm(6,miao); //分別將shi、fen、miao送去液晶顯示 write_sfm(3,fen); write_sfm(0,shi); count=0; xqnum=0; S1num=0; //初始化全局變量count TMOD=0x01; //設(shè)置定時(shí)器0工作模式1 TH0=(65535-50000)/256; //定時(shí)器裝初始值 TL0=(65535-50000)%256; EA=1; //開總中斷 ET0=1; //開定時(shí)器0中斷 TR0=1; //啟動定時(shí)器0 } /************************************************** 獨(dú)立鍵盤 sbit S1=P3^0; //定義鍵——進(jìn)入設(shè)置 sbit S2=P3^1; //定義鍵——增大 sbit S3=P3^2; //定義鍵——減小 sbit S4=P3^3; //定義鍵——退出設(shè)置 獨(dú)立鍵盤已接地 *************************************************/ void keyscan() { if(S1==0) { delay(5); //確認(rèn)定義鍵被按下 if(S1==0) { S1num++; //定義鍵S1按下次數(shù)記錄 while(!S1); //釋放按鍵確認(rèn) if(S1num==1) //S1按下一次時(shí) { TR0=0; //關(guān)閉定時(shí)器 write_com(0xc0+7); //光標(biāo)定位到秒位置 write_com(0x0f); //光標(biāo)閃爍 } if(S1num==2) //S1按下兩次時(shí) { write_com(0xc0+4); //光標(biāo)定位到分位置 } if(S1num==3) //S1按下三次時(shí) { write_com(0xc0+1); //光標(biāo)定位到時(shí)位置 } if(S1num==4) //S1按下四次時(shí) { write_com(0x80+13); //光標(biāo)定位到星期位置 } if(S1num==5) //S1按下五次時(shí) { write_com(0x80+9); //光標(biāo)定位到日位置 } if(S1num==6) //S1按下六次時(shí) { write_com(0x80+6); //光標(biāo)定位到月位置 } if(S1num==7) //S1按下七次時(shí) { write_com(0x80+3); //光標(biāo)定位到年位置 } if(S1num==8) //S1按下八次時(shí) { S1num=0; //S1記錄按鍵次數(shù)清零 TR0=1; //開啟定時(shí)器 write_com(0x0c); //取消光標(biāo)閃爍 } } } if(S1num!=0) //只有定義鍵按下后S2、S3、S4才有效 { if(S2==0) { delay(5); //防抖 if(S2==0) //確認(rèn)按鍵被按下 { while(!S2); //釋放按鍵確認(rèn) if(S1num==1) //S1按下一次時(shí) { miao++; //調(diào)整秒加1 if(miao==60) //滿60清零 miao=0; write_sfm(6,miao); //每調(diào)節(jié)一次送液晶顯示一次 write_com(0x80+0x40+6); //顯示位置重新回到調(diào)節(jié)處 } if(S1num==2) //S1按下兩次時(shí) { fen++; //調(diào)整分加1 if(fen==60) fen=0; write_sfm(3,fen); write_com(0x80+0x40+3); } if(S1num==3) //S1按下三次時(shí) { shi++; //調(diào)整時(shí)加1 if(shi==24) shi=0; write_com(0x80+0x40); write_sfm(0,shi); } if(S1num==4) //星期加調(diào)整 { xqnum++; if(xqnum==7) xqnum=0; write_com(0x80+0x0b); for(a=0;a<3;a++) { write_data(xingqi[xqnum][a]); delay(5); } } if(S1num==5) //日加調(diào)整 { ri++; if(yue==2) { if(nian%4==0&&nian%100!=0||nian%400==0) { if(ri==30) { ri=1; } } if(nian%400!=0) { if(ri==29) { ri=1; } } } else if(yue<=7) { if(yue%2==0&yue!=2) { if(ri==31) { ri=1; } } else if(yue%2!=0&yue!=2) { if(ri==32) { ri=1; } } } else if(yue>=8) { if(yue%2==0) { if(ri==32) { ri=1; } } else if(yue%2!=0) { if(ri==31) { ri=1; } } } write_yr(8,ri); } if(S1num==6) //月加調(diào)整 { yue++; if(yue==13) yue=1; write_yr(5,yue); } if(S1num==7) //年加調(diào)整 { nian++; if(nian==2019) nian=2014; write_nian(0,nian); } } } if(S3==0) { delay(5); if(S3==0) //確認(rèn)按鍵被按下 { while(!S3); if(S1num==1) { miao--; //調(diào)整秒減1 if(miao==-1) //減到00后再減重新設(shè)置為59 miao=59; write_sfm(6,miao); write_com(0x80+0x40+6); } if(S1num==2) { fen--; //調(diào)整分減1 if(fen==-1) fen=59; write_sfm(3,fen); write_com(0x80+0x40+3); } if(S1num==3) { shi--; //調(diào)整時(shí)減1 if(shi==-1) shi=23; write_sfm(0,shi); write_com(0x80+0x40); } if(S1num==4) { xqnum--; //調(diào)整星期減一 if(xqnum==-1) xqnum=6; write_com(0x80+0x0b); for(a=0;a<3;a++) { write_data(xingqi[xqnum][a]); delay(5); } } if(S1num==5) //調(diào)整日 { ri--; if(yue==2) { if(nian%400==0) { if(ri==0) { ri=29; } } if(nian%400!=0) { if(ri==0) { ri=28; } } } else if(yue==4|6|9|11) { if(yue%2==0&yue!=2) { if(ri==0) { ri=30; } } else if(yue%2!=0&yue!=2) { if(ri==0) { ri=31; } } } else if(yue>=8) { if(yue%2==0) { if(ri==0) { ri=31; } } else if(yue%2!=0) { if(ri==0) { ri=30; } } } write_yr(8,ri); } if(S1num==6) //調(diào)整月 { yue--; if(yue==0) yue=12; write_yr(5,yue); } if(S1num==7) //調(diào)整年 { nian--; if(nian==2013) nian=2018; write_nian(0,nian); } } } if(S4==0) //退出設(shè)置、開啟中斷 { delay(5); if(S4==0) { S1num=0; TR0=1; write_com(0x0c); } } } } /************************************************** 定時(shí)器0 *************************************************/ void timer0() interrupt 1 //定時(shí)器0中斷服務(wù)程序 { TH0=(65535-50000)/256; //重裝定時(shí)器初始值 TL0=(65535-50000)%256; count++; //中斷次數(shù)累加 } /************************************************* 主函數(shù) *************************************************/ void main() { init(); while(1) { keyscan(); if(count==20) //20次50毫秒即一秒 { count=0; miao++; if(miao==60) //秒加到60時(shí)分進(jìn)位 { miao=0; fen++; if(fen==60) //分加到60時(shí)時(shí)進(jìn)位 { fen=0; shi++; if(shi==24) //時(shí)加到24時(shí)清0 { shi=0; xqnum++; ri++; if(yue==2) //如果是二月 { if(nian%400==0) //閏年判斷 { if(ri==30) { ri=1; yue++; write_yr(5,yue); } } if(nian%400!=0) //平年判斷 { if(ri==29) { ri=1; yue++; write_yr(5,yue); } } } else if(yue<=7&yue!=2) //一月到七月 { if(yue%2==0) //偶數(shù)月(除二月) { if(ri==31) { ri=1; yue++; } } else if(yue%2!=0) //奇數(shù)月 { if(ri==32) { ri=1; yue++; } } write_yr(5,yue); } else if(yue>=8) //八月到12月 { if(yue%2==0) //偶數(shù)月(除二月) { if(ri==32) { ri=1; yue++; if(yue==13) //如果判斷月份為12月,則加一后重新定義月份為1 { yue=1; nian++; write_nian(0,nian); } write_yr(5,yue); } } else if(yue%2!=0) //奇數(shù)月 { if(ri==31) { ri=1; yue++; write_yr(5,yue); } } } write_yr(8,ri); if(xqnum==7) //星期寫入 xqnum=0; write_com(0x80+0x0b); for(a=0;a<3;a++) { write_data(xingqi[xqnum][a]); delay(5); } } write_sfm(0,shi); //重新寫入數(shù)據(jù) } write_sfm(3,fen); //重新寫入數(shù)據(jù) } write_sfm(6,miao); //重新寫入數(shù)據(jù) } //不停的檢測按鍵是否被按下 } } |
|