1. 基於單片機多功能數字鍾
帶萬年歷的LCD顯示多功能數字鍾
程序清單:
;SMC1602介面程序(MCS51模擬口線方式)
;***************************************************************************
;連線圖:*LCM---8031**LCM---8031**LCM------------8031*
;*DB0---P0.0**DB4---P0.4**RS-------------P2.0*
;*DB1---P0.1**DB5---P0.5**RW-------------P2.1*
;*DB2---P0.2**DB6---P0.6**E--------------P2.2*
;*DB3---P0.3**DB7---P0.7**VLCD接10K可調電阻到GND*
;注:8051的晶振頻率為11.0592MHzR0設置數據存放S8為設置鍵S7為加鍵S4為確認鍵
;**************************************************************************
;P0口液晶顯示
;P2.4位選鍵P2.3加一鍵P2.2返回鍵及報時功能鍵鬧鍾設置P2.0控制顯示鍵
;寄存器clrrs0setbrs1R0R4R5在按鍵中用到延時中用到SETBRS0SETBRS1的R0R1R2
;SETBRS0CLRRS1顯示中用到CLRRS0CLRRS1在鬧鍾調整子程序中用到R1
;*********************************************************************
;
;報時功能P2.6和鬧鍾功能P2.5鬧鍾調整時間功能已經可以設置顯示的切換方式變了再關閉的情況下一切正常運行
;*****************************
RSPINBITP1.2
RWPINBITP1.1
EPINBITP1.0
WEIXUANBITP2.4;位選鍵設置鍵
JIAJIANBITP2.3;加一鍵
JIANJIANBITP2.2;減一鍵
FANHUIBITP2.1;返回鍵
NZKGBITP2.0;鬧鍾設置鍵
SECONTLEQU30H;秒
SECONTHEQU31H;秒
MAOHAOLEQU32H;:
MINIUTLEQU33H;分
MINIUTHEQU34H;分
MAOHAOHEQU35H;:
HOURLEQU36H;時
HOURHEQU37H;時
;*****************************日期部分***************************
DAYLEQU40H;日個
DAYHEQU41H;日十
HENLEQU42H;-
MONTHLEQU43H;yue
MONTHHEQU44H;yue
HENHEQU45H;-
YEAROEQU46H;年
YEARTEQU47H
YEARSEQU48H
YEARFEQU49H
TEMPEQU50H;用做存儲單元顯示子程序(DISPLAY)里用到
BIJIAOEQU51H;加一子程序(JIAYI)中用到
ZDRQOEQU55H;中斷加一程序中用到
ZDRQTEQU56H;中斷加一程序中用到
ZDRQSEQU57H;中斷加一程序中用到
ZDRQFEQU58H;中斷加一程序中用到
DIZHIEQU59H;鍵盤(JIANPAN)子程序里用到
NZBZBIT60H;定時標志位在(鬧鍾開關部分)
;38H到3FH沒用到
BSCSBZBIT39H;報時次數轉換標志(BSCS)里用到
BSCSCCEQU3AH;報時次數存儲(BSCS)里用到
ZDBSBZBIT3BH;整點報時標志(SSBS)里用到
ZMBSBZBIT3CH;整秒閃爍標志(SSBS)里用到
BSKGBZBIT3DH;報時開啟標志(BSKG)里用到
XKQHBZBIT3EH;顯示開啟關閉標志(XIANKONG)里用到
ORG0000H
AJMPMAIN
ORG000BH
AJMPZD
ORG0030H
MAIN:MOVSP,#60H;給堆棧指針賦初值
MOV30H,#05H;秒
MOV31H,#05H;秒
MOV32H,#3AH;:
MOV33H,#09H;分
MOV34H,#05H;分
MOV35H,#3AH;:
MOV36H,#03H;時
MOV37H,#01H;時
;*****************************日期部分***************************
MOV40H,#09H;日個
MOV41H,#02H;日十
MOV42H,#2DH;-
MOV43H,#09H;yue
MOV44H,#00H;yue
MOV45H,#2DH;-
MOV46H,#09H;年
MOV47H,#09H
MOV48H,#09H
MOV49H,#02H
CLRP2.5;鬧鍾
CLRP2.6;整點報時
MOV03H,#00H;鬧鍾分個位
MOV04H,#00H;鬧鍾分十位
MOV06H,#04H;鬧鍾時個位
MOV07H,#01H;鬧鍾時十位
;CLRP1.5
;CLRP1.4
MOVB,#20
MOVTMOD,#01H;定時器工作方式1
MOVTH0,#4CH
MOVTL0,#08H
SETBET0;允許T0中斷
SETBEA;總中斷開放
LCALLLCDRESET;初始化LCD
LCALLDISPSTART;調用顯示初始狀態
SETBTR0;開啟定時器
CLRNZBZ;鬧鍾開啟關閉標志
CLRBSKGBZ;報時開啟關閉標志
CLRXKQHBZ;顯示開啟關閉標志
LOOP:LCALLJIANPAN;按鍵子程序
LCALLDISPLAY;顯示子程序
LCALLNZBF;NAOZHONGBUFENG
LCALLNZBJ;NAOZHONGBIJIAO
LCALLBSKG;BAOSHIKAIGUAN
LCALLBSCS;BAOSHICISHU
LCALLSSBS;閃爍報時
SJMPLOOP
;==============================中斷加一程序===================================
ZD:PUSHACC
MOVTH0,#4CH
MOVTL0,#08H
DJNZB,ZDEND
MOVB,#20
INCSECONTL
SETBZMBSBZ
MOVA,SECONTL
CJNEA,#0AH,ZDEND
MOVSECONTL,#00H
INCSECONTH
MOVA,SECONTH
CJNEA,#06H,ZDEND
MOVSECONTH,#00H
INCMINIUTL
MOVA,MINIUTL
CJNEA,#0AH,ZDEND
MOVMINIUTL,#00H
INCMINIUTH
MOVA,MINIUTH
CJNEA,#06H,ZDEND
MOVMINIUTH,#00H
INCHOURL
SETBBSCSBZ
SETBZDBSBZ
MOVA,HOURL;24小時的判斷
CJNEA,#04H,ZDF
MOVA,HOURH
CJNEA,#02H,ZDEND
MOVHOURL,#00H
MOVHOURH,#00H
LCALLZDRQ
SJMPZDEND
ZDF:CJNEA,#0AH,ZDEND
MOVHOURL,#00H
INCHOURH
ZDEND:POPACC
RETI
;日期部分
ZDRQ:PUSHACC
INCDAYL
;判斷天數28,30,31部分
MOVA,MONTHH;用於判斷月份時為31天30天28天
CJNEA,#01H,LL
MOV55H,#0AH;存放月份的十位轉化為個位是0AH
MOVA,MONTHL
ADDA,55H;月分高低相加用於查表
SJMPLL3
LL:MOVA,MONTHL
ADDA,MONTHH
LL3:MOV56H,A;存放相加後的月份數據
MOVDPTR,#TAB5
MOVCA,@A+DPTR;查十位和天數的十位比較
MOV57H,A
MOVA,56H
MOVDPTR,#TAB6;查個位和天數的個位比較
MOVCA,@A+DPTR
MOV58H,A
MOVA,DAYH
CJNEA,57H,LL2
MOVA,DAYL
CJNEA,58H,LL2
MOVDAYH,#00H
MOVDAYL,#01H
SJMPLL4
LL2:MOVA,DAYL
CJNEA,#0AH,ZDRQEND
MOVDAYL,#00H
INCDAYH
MOVA,DAYH;比較天數是否要進位
CJNEA,57H,ZDRQEND
MOVA,DAYL
CJNEA,58H,ZDRQEND
MOVDAYH,#00H
MOVDAYL,#01H
;月份和年份
LL4:INCMONTHL
MOVA,MONTHL
CJNEA,#03H,ZDRQ1;用於判斷月份時為12月時進位
MOVA,MONTHH
CJNEA,#01H,ZDRQ1
MOVMONTHL,#01H;天數符合要求
MOVMONTHH,#00H
SJMPZDRQ2
ZDRQ1:CJNEA,#0AH,ZDRQEND
MOVMONTHL,#00H
INCMONTHH
SJMPZDRQEND
ZDRQ2:INCYEARO;年的加一
MOVA,YEARO
CJNEA,#0AH,ZDRQEND
MOVYEARO,#00H
INCYEART;年的進位
MOVA,YEART
CJNEA,#0AH,ZDRQEND
MOVYEART,#00H
INCYEARS
MOVA,YEARS
CJNEA,#0AH,ZDRQEND
MOVYEARS,#00H
INCYEARF
MOVA,YEARF
CJNEA,#0AH,ZDRQEND
MOVYEARF,#00H
ZDRQEND:
POPACC
RET
;液晶初始化
;========================初始化程序=======================================
LCDRESET:;初始化程序
LCALLDELAY5MS;延時15MS
LCALLDELAY5MS
LCALLDELAY5MS
MOVA,#38H;顯示模式設置(不檢測忙信號)
LCALLLCDWCN;共三次
LCALLDELAY5MS
MOVA,#38H
LCALLLCDWCN
LCALLDELAY5MS
MOVA,#38H
LCALLLCDWCN
MOVA,#38H;顯示模式設置(以後均檢測忙信號)
LCALLLCDWC
MOVA,#08H;顯示關閉
LCALLLCDWC
MOVA,#01H;顯示清屏
LCALLLCDWC
MOVA,#06H;顯示游標移動設置
LCALLLCDWC
MOVA,#0CH;顯示開及游標設置
LCALLLCDWC
RET
;==============================寫指令===================================
LCDWC:;送控制字子程序(檢測忙信號)
LCALLWAITIDLE
;******寫指令*******;送控制字子程序(不檢測忙信號)
LCDWCN:CLRRSPIN;RS=0RW=0E=高脈沖
CLRRWPIN
MOVP0,A
SETBEPIN;(
NOP;給高電平脈沖
CLREPIN;)
RET
;==========================寫數據=======================================
LCDWD:;寫字元子程序
LCALLWAITIDLE
SETBRSPIN;RS=1RW=0E=高脈沖
CLRRWPIN
MOVP0,A
SETBEPIN
NOP
CLREPIN
RET
;===============================等待控制器空閑==================================
WAITIDLE:
PUSHACC;正常讀寫操作之前必須檢測LCD控制器狀態
MOVP0,#0FFH
lcallDELAY5MS;666666666666666666666666
CLRRSPIN;RS=0RW=1E=高電平
SETBRWPIN
SETBEPIN
lcallDELAY5MS;98
WTD_PA:NOP;DB7:0LCD控制器空閑
JBP0.7,WTD_PA;1LCD控制器忙
CLREPIN
POPACC
RET
;***********************初始狀態子程序*******************************
DISPSTART:;顯示初始狀態子程序
PUSHACC
MOVA,#80H
LCALLLCDWC
MOVDPTR,#TAB;顯示字元
DISP1:CLRA
MOVCA,@A+DPTR
JZDISP2
LCALLLCDWD
INCDPTR
SJMPDISP1
DISP2:MOVA,#0C0H
LCALLLCDWC
MOVDPTR,#TAB1
DISP3:CLRA
MOVCA,@A+DPTR
JZDISP_END
LCALLLCDWD
INCDPTR
SJMPDISP3
DISP_END:
POPACC
RET
;==========================顯示子程序=======================================
DISPLAY:PUSHPSW
PUSHACC
SETBRS0
CLRRS1
MOVA,#85H
LCALLLCDWC
MOVR1,#38H;第一行顯示數據存儲單元的啟始地址
MOVTEMP,#30H;第一行顯示數據存儲單元的結束地址
MOVR6,#2
PLAY:DECR1
CJNER1,#32H,PLY;判斷是否為冒號位
MOVA,MAOHAOL;是者送冒號的ACSI碼
SJMPPLAY1
PLY:CJNER1,#35H,PLY1
MOVA,MAOHAOH
SJMPPLAY1
PLY1:CJNER1,#42H,PLY2;判斷是否為橫杠的位置
MOVA,HENL;是者送橫杠的ACSI碼
SJMPPLAY1
PLY2:CJNER1,#45H,PLY3
MOVA,HENH
SJMPPLAY1
PLY3:MOVA,@R1;用查表法送要顯示的數據
MOVDPTR,#TAB2
MOVCA,@A+DPTR
PLAY1:LCALLLCDWD
MOVA,R1
CJNEA,TEMP,PLAY;判斷第一行是否顯示好了
MOVA,#0C5H
LCALLLCDWC
MOVR1,#4AH;第二行顯示數據存儲單元的啟始地址
MOVTEMP,#40H;第二行的結束地址
DJNZR6,PLAY;R6為0時兩行顯示結束
POPACC
POPPSW
RET
;************************按鍵子程序************************
JIANPAN:clrrs0;鍵盤子程序
setbrs1;鍵盤子程序
JBWEIXUAN,JIAN_ZEND;設置鍵的判斷
LCALLDELAY5MS
JBWEIXUAN,JIAN_ZEND
PUSHACC
JNBWEIXUAN,$
;MOVA,#0FH;開啟游標閃爍設置
;LCALLLCDWCN
fah:JNBNZBZ,JPNZSJ;為「1」鬧鍾為「0」時鍾
LCALLJPXS
MOVR4,#86H;鬧鍾設定時間R4存放顯示位地址
MOVR5,#2;鬧鍾設定時間第一行第二行•••••位置改變次數
MOVDIZHI,#8CH;鬧鍾設定時間第一行結束地址
MOVR0,#06H
SJMPGIVED
JPNZSJ:CLRTR0
MOVR4,#86H;R4存放顯示位地址
MOVR5,#2;第一行第二行•••••位置改變次數
MOVDIZHI,#8DH;第一行結束地址
MOVR0,#36H
GIVED:MOVA,#0FH;開啟游標閃爍設置
LCALLLCDWCN
MOVA,R4
LCALLLCDWC
UPONE:JBFANHUI,UPtwo;返回鍵的判斷
LCALLDELAY5MS
JBFANHUI,UPtwo
JNBFANHUI,$
SJMPGOBACK
JIAN_ZEND:SJMPJIAN_END;中繼跳轉
UPtwo:JBJIAJIAN,IAM;加一鍵的判斷
LCALLDELAY5MS
JBJIAJIAN,IAM
JNBJIAJIAN,$
LCALLJIAYI;調用按鍵加一子程序
;MOVA,#0FH;開啟游標閃爍設置
;LCALLLCDWCN
IAM:JBJIANJIAN,IAM22;減一鍵的判斷
LCALLDELAY5MS
JBJIANJIAN,IAM22
JNBJIANJIAN,$
LCALLJIANYI;調用按鍵減一子程序
AJMPGIVED
IAM22:JBWEIXUAN,UPONE;位選鍵的判斷
LCALLDELAY5MS
JBWEIXUAN,UPONE
JNBWEIXUAN,$
DECR0
INCR4
LCALLJIAN;調用位選比較程序
CJNEr4,#88H,JJ11
DECR0
INCR4
SJMPJJ22
JJ11:CJNEr4,#8BH,JJ22
DECR0
INCR4
JJ22:MOVA,R4
CJNEA,DIZHI,GIVED
JBNZBZ,fah;為「1」鬧鍾為「0」時鍾
MOVR4,#0C5H
MOVDIZHI,#0CFH
MOVR0,#49H
DJNZR5,GIVED
LJMPfah
GOBACK:MOVA,#0CH;關閉游標閃爍設置
LCALLLCDWCN
POPACC
JIAN_END:
SETBTR0
RET
;111111
;1111
JPXS:MOVA,#85H
LCALLLCDWC
MOVR1,#08H;第一行顯示數據存儲單元的啟始地址
JPXS_LL:DECR1
CJNER1,#05H,JPXS_LP
MOVA,#3AH
SJMPJPXS_LY
JPXS_LP:MOVA,@R1;用查表法送要顯示的數據
MOVDPTR,#TAB2
MOVCA,@A+DPTR
JPXS_LY:LCALLLCDWD
CJNER1,#03H,JPXS_LL
RET
;
;
;************************位選比較控製程序************************
;在調整時間時這幾位是符號冒號和橫杠的數據
;在這幾位時跳過到下一位
JIAN:CJNER4,#87H,JIAN5
DECR0
INCR4
SJMPJIANEND
JIAN5:CJNER4,#8AH,JIAN1
DECR0
INCR4
SJMPJIANEND
JIAN1:CJNER4,#0C9H,JIAN2
DECR0
INCR4
SJMPJIANEND
JIAN2:CJNER4,#0CCH,JIANEND
DECR0
INCR4
JIANEND:RET
;************************按鍵加一子程序********************
JIAYI:INC@R0
CJNE@R0,#0AH,JIAYI_END
MOV@R0,#0
CJNER4,#86H,JIAYI55
SJMPJIAYI33
JIAYI55:CJNEr4,#89H,JIAYI11
SJMPJIAYI33
JIAYI11:CJNEr4,#8CH,JIAYI22
SJMPJIAYI33
JIAYI22:CJNER0,#30H,JIAYI_END
JIAYI33:INCR0
INC@R0
CJNE@R0,#06H,JIAYI44
MOV@R0,#0
JIAYI44:DECR0
JIAYI_END:MOVA,#0CH;開啟游標閃爍設置
LCALLLCDWCN
JNBNZBZ,JIAYI88;為「1」鬧鍾為「0」時鍾
LCALLJPXS
SJMPJIAYI99
JIAYI88:LCALLDISPLAY;顯示子程序
JIAYI99:RET
;%%%%%%%%%%%%%%%%%%減一%%%%%%%%%%%%%%%%%%%%%%%%
JIANYI:DEC@R0
CJNE@R0,#00H,JIANYI_END
MOV@R0,#9
CJNER4,#86H,JIANYI55
SJMPJIANYI33
JIANYI55:CJNEr4,#89H,JIANYI11
SJMPJIANYI33
JIANYI11:CJNEr4,#8CH,JIANYI22
SJMPJIANYI33
JIANYI22:CJNER0,#30H,JIANYI_END
JIANYI33:INCR0
DEC@R0
CJNE@R0,#0FFH,JIANYI44
MOV@R0,#5
JIANYI44:DECR0
JIANYI_END:MOVA,#0CH;開啟游標閃爍設置
LCALLLCDWCN
JNBNZBZ,JIANYI88;為「1」鬧鍾為「0」時鍾
LCALLJPXS
SJMPJIANYI99
JIANYI88:LCALLDISPLAY;顯示子程序
JIANYI99:RET
;******************************鬧鍾開關部分************************
NZBF:JBNZKG,NZBF_END
LCALLDELAY5MS
JBNZKG,NZBF_END
JNBNZKG,$
CPLNZBZ
JBNZBZ,NZBF_LL
MOVA,#01H;顯示清屏
LCALLLCDWC
CLRP2.5
LCALLDISPSTART;調用顯示初始狀態
LCALLDISPLAY;調用顯示初始狀態
JBBSKGBZ,NZBF_LP;|
SJMPNZBF_END;|
NZBF_LP:MOVA,#8FH;報時標志顯示位置;|
LCALLLCDWC;|保護報時標志在清屏是不被誤清
MOVA,#25H;顯示報時標志;|
LCALLLCDWD;|
SJMPNZBF_END;|
NZBF_LL:MOVA,#8EH;鬧鍾標志顯示位置
LCALLLCDWC
MOVA,#26H;顯示鬧鍾標志
LCALLLCDWD
NZBF_END:RET
;******************************鬧鍾比較部分************************
NZBJ:JBNZBZ,NZBJ_LL
SJMPNZBJ_END
NZBJ_LL:MOVA,07H
CJNEA,37H,NZBJ_END
MOVA,06H
CJNEA,36H,NZBJ_END
MOVA,04H
CJNEA,34H,NZBJ_END
MOVA,03H
CJNEA,33H,NZBJ_END
SETBP2.5
NZBJ_END:RET
;***************報時開關********************
BSKG:JBFANHUI,BSKG_END
LCALLDELAY5MS
JBFANHUI,BSKG_END
JNBFANHUI,$
CPLBSKGBZ
JBBSKGBZ,BSKG_LL
MOVA,#01H;顯示清屏
LCALLLCDWC
CLRP2.6
LCALLDISPSTART;調用顯示初始狀態
LCALLDISPLAY;調用顯示
JBNZBZ,BSKG_LP;|
SJMPBSKG_END;|
BSKG_LP:MOVA,#8EH;|
LCALLLCDWC;|保護鬧鍾標志在清屏是不被誤清
MOVA,#26H;|
LCALLLCDWD;|
SJMPBSKG_END;|
BSKG_LL:MOVA,#8FH;報時標志顯示位置
LCALLLCDWC
MOVA,#25H;顯示報時標志
LCALLLCDWD
BSKG_END:RET
;*********************報時次數********************
BSCS:JNBBSKGBZ,BSCS_END
JNBBSCSBZ,BSCS_END
MOVA,37H
CJNEA,#01H,BSCS_LL
MOVA,#0AH
SJMPBSCS_LP
BSCS_LL:CJNEA,#02H,BSCS_LP
MOVA,#14H
BSCS_LP:ADDA,36H
RLA
MOVBSCSCC,A
CLRBSCSBZ
BSCS_END:RET
;**********************閃爍報時********************************
SSBS:JNBBSKGBZ,SSBS_END
JNBZDBSBZ,SSBS_END
JNBZMBSBZ,SSBS_END
CPLP2.6
CPLP2.7
CLRZMBSBZ
DJNZBSCSCC,SSBS_END
CLRZDBSBZ
CLRP2.6
SSBS_END:RET
;************************延時子程序(5MS)************************
DELAY5MS:
PUSHPSW
SETBRS0
SETBRS1
MOVR1,#25;延時子程序(5MS)
DL5_PA:MOVR2,#100
DJNZR2,$
DJNZR1,DL5_PA
POPPSW
RET
TAB:DB"TIME:",00h
TAB1:DB"DATE:",00h
TAB2:DB"01234567891"
TAB3:DB0AH,06H,00H,0AH,06H,00H,0AH,03H;用於比較調整時間時的比較
TAB4:DB0AH,04H,00H,0AH,02H,00H,0AH,0AH,0AH,0AH;用於調整日期時的比較
TAB5:DB00H,03H,02H,03H,03H,03H,03H,03H,03H,03H,03H,03H,03H;用於天數十位比較
TAB6:DB00H,02H,09H,02H,01H,02H,01H,02H,02H,01H,02H,01H,02H;用於天數個位比較
2. 基於單片機的數字時鍾設計開題報告
//我這里有一個定時的鬧鍾,你把蜂鳴器的中斷改為LED就行了,可以通過P2^0--P2^3實現秒錶的顯示和以及調時調分和調節鬧鍾以及鬧鍾的開關,有問題可以給我留言QQ834589429
#include<reg52.h>//包含頭文件,一般情況不需要改動,頭文件包含特殊功能寄存器的定義
codeunsignedchartab[]=
{0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};
//共陰數碼管0-9
sbitA1=P2^0;
sbitA2=P2^1;
sbitA3=P2^2;
sbitA4=P2^3;
sbitbeep=P1^4;
unsignedcharShiwan;
unsignedcharWanwei;
unsignedcharQianwei;
unsignedcharBaiwei;
unsignedcharShiwei;//定義十位
unsignedcharGewei,Naoling1,Naoling2,Naoling3,Naoling4;//定義個位
staticunsignedcharhour=12,minute=30,second=0,count=0;
staticunsignedcharalarmhour=12,alarmminute=29,i=0,j=0,k;
/******************************************************************/
/*延時函數*/
/******************************************************************/
voiddelay(unsignedintcnt)
{
while(--cnt);
}
voidxianshi(void)
{
Gewei=tab[second%10];//個位顯示處理
Shiwei=tab[second/10];//十位顯示值處理
if(second%2==0)
{
Baiwei=tab[minute%10];
Qianwei=tab[minute/10];//千位
}
else
{
Baiwei=(tab[minute%10]|0x80);//百位顯示處理:加點的字碼
Qianwei=(tab[minute/10]|0x80);
}
if(second%2!=0)
{
Wanwei=tab[hour%10];
Shiwan=tab[hour/10];
}
else
{
Wanwei=(tab[hour%10]|0x80);
Shiwan=(tab[hour/10]|0x80);
}
Naoling1=~tab[alarmhour%10];
Naoling2=~tab[alarmhour/10];
Naoling3=~tab[alarmminute%10];
Naoling4=~tab[alarmminute/10];
}
voidtimer0()interrupt3using1
{
TH1=0x3c;//中斷設置初始化
TL1=0xb0;
if(alarmhour==hour&&alarmminute==minute&&j==1)
{
beep=0;
}
}
/******************************************************************/
/*定時器中斷函數*/
/******************************************************************/
voidtimer1()interrupt1using0
{
TH0=0xd8;//重新賦值
TL0=0xf0;
count++;
xianshi();
if(count==99)//100x10ms=1S,大致延時時間
{
count=0;
second++;//秒加1
if(second==60)
minute++;
{
if(second==60)
second=0;
{
if(minute==60)
hour++;
{
if(minute==60)
minute=0;
{
if(hour==24)
hour=0;
}
}
}
}
}
}
/******************************************************************/
/*主函數*/
/******************************************************************/
voidmain()
{
TMOD|=0x01;//定時器設置10msin12Mcrystal,工作在模式1,16位定時
TH0=0xd8;
TL0=0xf0;
IE=0x82;//打開中斷
TR0=1;//打開定時開關
xianshi();
EA=1;ET0=1;TMOD|=0x21;TR0=1;//開中斷總開關,計數器0允許中斷,設置中斷模式,啟動計數器0
ET1=1;TR1=1;
while(1)
{
{
if(!A3)
{
delay(10000);
if(!A3)
{
i++;if(i==7)i=0;
xianshi();
}
}
}
{
if(!A4)
{
delay(10000);
if(!A4)
{
i--;if(i==255)i=6;
xianshi();
}
}
}
switch(i)
{
case0://正常顯示控制
{
P1=0x1e;//片選個位
P0=~Baiwei;//顯示個位
delay(300);//短暫延時
P1=0x1d;//片選十位
P0=~Qianwei;//顯示十位
delay(300);//短暫延時
P1=0x1b;//片選百位
P0=~Wanwei;//顯示百位
delay(300);//短暫延時
P1=0x17;//片選千位
P0=~Shiwan;//顯示千位
delay(300);//短暫延時
P1=0x1f;
P0=0xff;
delay(300);
};break;
case1://調分控制
{
if(second%2!=0)
{
P1=0x1e;//片選個位
P0=~Baiwei;//顯示個位
delay(300);//短暫延時
P1=0x1d;//片選十位
P0=~Qianwei;//顯示十位
delay(300);//短暫延時
P1=0x1f;
P0=0xff;
delay(300);
}
else
delay(300);
delay(300);
{
if(!A1)
{
delay(10000);//消抖
if(!A1)
{
minute++;if(minute==61)minute=0;
xianshi();
}
}//按鍵處理
}
{
if(!A2)
{
delay(10000);//消抖
if(!A2)
{
minute--;if(minute==255)minute=59;
xianshi();
}
}
}
};break;
case2://調時控制
{
if(second%2==0)
{
P1=0x1b;//片選百位
P0=~Wanwei;//顯示百位
delay(300);//短暫延時
P1=0x17;//片選千位
P0=~Shiwan;//顯示千位
delay(300);//短暫延時
P1=0x1f;
P0=0xff;
delay(300);
}
else
delay(300);
delay(300);
{
if(!A1)
{
delay(10000);//消抖
if(!A1)
{
hour++;if(hour==24)hour=0;
xianshi();
}
}//按鍵處理
}
{
if(!A2)
{
delay(10000);//消抖
if(!A2)
{
hour--;if(hour==255)hour=23;
xianshi();
}
}
}
};break;
case3://秒顯示控制
{
P1=0x1e;//片選個位
P0=~Gewei;//顯示個位
delay(300);//短暫延時
P1=0x1d;//片選十位
P0=~Shiwei;//顯示十位
delay(300);//短暫延時
P1=0x1f;
P0=0xff;
delay(300);
delay(300);
delay(300);
};break;
case4://鬧鍾控制
{
if((!A1)||(!A2))
{
delay(10000);
if((!A1)||(!A2))j++;
if(j==2)
j=0;
}
switch(j)
{
case0:{
P1=0x1e;//片選個位
P0=~0x71;//顯示個位
delay(300);//短暫延時
P1=0x1d;//片選十位
P0=~0x71;//顯示十位
delay(300);//短暫延時
P1=0x1b;//片選百位
P0=~0x3f;//顯示百位
delay(300);//短暫延時
P1=0x17;//片選千位
P0=~0x40;//顯示千位
delay(300);//短暫延時
delay(300);
};break;
case1:{
P1=0x1e;//片選個位
P0=~0x37;//顯示個位
delay(300);//短暫延時
P1=0x1d;//片選十位
P0=~0x3f;//顯示十位
delay(300);//短暫延時
P1=0x1b;//片選百位
P0=0xff;//顯示百位
delay(300);//短暫延時
P1=0x17;//片選千位
P0=~0x40;//顯示千位
delay(300);//短暫延時
delay(300);
}
}
};break;
case5://鬧鈴分鍾調整
{
{
P1=0x1e;
P0=Naoling3;
delay(300);
P1=0x1d;
P0=Naoling4;
delay(300);
P1=0x1f;
P0=0xff;
delay(300);
delay(300);
delay(300);
}
{
if(!A1)
{
delay(10000);//消抖
if(!A1)
{
alarmminute++;if(alarmminute==61)alarmminute=0;
}
}//按鍵處理
}
{
if(!A2)
{
delay(10000);//消抖
if(!A2)
{
alarmminute--;if(alarmminute==255)alarmminute=59;
}
}
}
};break;
case6://鬧鈴小時調整
{
{
P1=0x1b;
P0=Naoling1;
delay(300);
P1=0x17;
P0=Naoling2;
delay(300);
P1=0x1f;
P0=0xff;
delay(300);
delay(300);
delay(300);
}
{
if(!A1)
{
delay(10000);//消抖
if(!A1)
{
alarmhour++;if(alarmhour==24)alarmhour=0;
}
}//按鍵處理
}
{
if(!A2)
{
delay(10000);//消抖
if(!A2)
{
alarmhour--;if(alarmhour==255)alarmhour=23;
}
}
};break;
default:break;
}
}
}
}
3. 單片機數字時鍾設計
ORG 0X00
LJMP START
ORG 0X30
#30H ; 設置堆棧
MOV P1, #0XFE ; 設置在數碼管的第0位顯示
MOV A, #0X01 ; A置初值為0000 0001
LOOP: MOV P0, A ; 在數碼管上顯示寄存器A中的二進制數
MOV R3, #0X5C ; 延時1S
ACALL EXTDELAY ; 延時觀察和記錄對應的顯示結果
RL A ; 將A寄存器的值循環左移一位
SJMP LOOP ; 循環顯示
DELAY: MOV R1, #0XC8 ; 延時20MS
DL2: MOV R2, #0X18
DL1: NOP
NOP
DJNZ R2, DL1
DJNZ R1, DL2
RET
EXTDELAY:ACALL DELAY
DJNZ R3,EXTDELAY
RET
END
ORG 0X00
SJMP START
ORG 0X30
START: MOV SP, #30H ; 設置堆棧
MOV P1, #0XFE ; 位選信號,選中第0個數碼管
MOV P0, #0X6F ; 在數碼管上顯示"9"
LOOP: SJMP LOOP ; 循環執行程序
END
ORG 0X00
LJMP START
ORG 0X30
START: MOV SP, #30H ; 設置堆棧
MOV P1, #0XFE ; 設置在數碼管的第0位顯示
MOV DPTR, #TABLE ; 送TABLE地址到DPTR指針
MOV R7, #0X00 ; 標志變數,限制指針在TABLE區
LOOP: CLR A
MOVC A, @A+DPTR ; 取TABLE區的字形碼
MOV P0, A ; 在數碼管上顯示寄存器A中的二進制數
INC R7 ; 指針控制加一
MOV R3, #0X5C ; 延時
ACALL EXTDELAY ; 延時觀察和記錄對應的顯示結果
CJNE R7, #0X10, NEXT ; 如果TABLE中數未取到最後一個,繼續取下一個
MOV R7, #0X00 ; 如果已經取過所有數,則重新開始去第一個數
MOV DPTR, #TABLE
SJMP LOOP
NEXT: INC DPTR ; 指針寄存器加1
SJMP LOOP ; 循環顯示
DELAY: MOV R1, #0XC8 ; 延時20MS
DL2: MOV R2, #0X18
DL1: NOP
NOP
DJNZ R2, DL1
DJNZ R1, DL2
RET
EXTDELAY: ACALL DELAY
DJNZ R3 ,EXTDELAY
RET
TABLE: ; 相對地址
DB 0X3F,0X06,0X5B,0X4F,0X66,0X6D,0X7D,0X07,0X7F,0X6F ;十六進制字形數據
0 1 2 3 4 5 6 7 8 9 (十六進制數)
DB 0X77,0X7C,0X39,0X5E,0X79,0X71 ; 十六進制字形數據
A B C D E F (十六進制數)
END
ORG 0X00
LJMP START
ORG 0X30
START: MOV SP, #30H
MOV A, #0XFE ; 置A寄存器為0XFE
MOV DPTR, #TABLE
MOV R7, #0X00
LOOP: MOV P1, A ; 在數碼管的第0位顯示
MOV R4,A ; 保存A寄存器的制
CLR A
MOVC A, @A+DPTR
MOV P0, A
MOV A, R4 ; 還原A寄存器的值
CJNE A, #0XBF, SKIP ; 如果已在第五位顯示,那麼下一次
MOV A, #0XFE ; 從第0位開始顯示
SJMP LOOP ; 跳回執行下一次顯示
SKIP: RL A ; A左移一位,下一次在數碼管的下一位顯示數字
INC R7
MOV R3, #0X5C
ACALL EXTDELAY
CJNE R7, #0X10, NEXT ; 如果TABLE中數未取到最後一個,繼續取下一個
MOV R7, #0X00 ; 如果已經取過所有數,則重新開始去第一個數
MOV DPTR, #TABLE
SJMP LOOP
NEXT: INC DPTR ; 指針寄存器加1
SJMP LOOP ; 循環顯示
DELAY: MOV R1, #0XC8 ; 延時20MS
DL2: MOV R2, #0X18
DL1: NOP
NOP
DJNZ R2, DL1
DJNZ R1, DL2
RET
EXTDELAY: ACALL DELAY
DJNZ R3, EXTDELAY
RET
TABLE: ; 相對地址
DB 0X3F,0X06,0X5B,0X4F,0X66,0X6D,0X7D,0X07,0X7F,0X6F ;十六進制字形數據
0 1 2 3 4 5 6 7 8 9 (十六進制數)
DB 0X77,0X7C,0X39,0X5E,0X79,0X71 ; 十六進制字形數據
A B C D E F (十六進制數)
END