📄 电子钟程序4.asm
字号:
;使用说明:
;QIUHUAN键即为时钟和闹钟的切换
;按TIAOSHI键时钟加1
;按TIAOFEN键分钟加1
;TIAONAO在显示时间的状态下按下则停止闹铃,在闹铃调节状态下为开关闹铃的切换
;对于各个引脚的定义如下,可以根据硬件的不同来相应的修改
;只要修改以下框中的定义就可以!!!!!
;有疑问可以QQ联系:313735321 哈哈。。。。。。
;*********************************************************************
DUANMA EQU P1 ;送段码的口
MIAO_GE BIT P0.0 ;秒钟个位
MIAO_SHI BIT P0.1 ;秒钟十位
FEN_GE BIT P0.2 ;分钟个位
FEN_SHI BIT P0.3 ;分钟十位
SHI_GE BIT P0.4 ;时钟个位
SHI_SHI BIT P0.5 ;时钟十位
LINGSHENG BIT P0.6 ;送铃声
QIEHUAN BIT P2.0 ;切换按键
TIAOSHI BIT P2.1 ;调时钟按键
TIAOFEN BIT P2.2 ;调分钟按键
TIAONAO BIT P2.3 ;调闹钟按键
N EQU 30 ;定义响多少秒,最多可以定义59S,多了没用,但是也不会有什么事。
GAO EQU 50 ;调此值可改变响一声的长度(就是响铃脉冲高电平的长度)
DI EQU 30 ;调此值可改变声声间的间隔时间(就是响铃脉冲低电平的长度)
;******************************************************************
MIAO EQU 30H ;秒寄存器
FEN EQU 31H ;分寄存器
SHI EQU 32H ;時寄存器
N_FEN EQU 33H ;闹铃分寄存器
N_SHI EQU 34H ;闹铃时寄存器
ORG 00H
LJMP START
ORG 0BH ;定時中斷入口
LJMP TIMER
ORG 30H
;***************初始化部分******************************************
START:
MOV MIAO,#0
MOV FEN,#0
MOV SHI,#0
MOV N_FEN,#0 ;闹铃的初值为7:00
MOV N_SHI,#07
MOV 20H, #10 ;0.5秒鐘中斷次數,0.5s=500ms=50msx10
MOV 21H, #2 ;2個0.5秒即為1秒
MOV SP, #40H ;堆棧指針設置
MOV IE, #82H ;開定時器0中斷及總中斷
MOV TMOD, #01H ;定時器0模式1
MOV TH0, #03CH ;50ms初值
MOV TL0, #0B0H
CLR LINGSHENG
MOV DUANMA,#00H ;*************清DUANMA口
MOV R5, #250
MOV R1, #0
SETB TR0 ;啟動定時器0
MOV DPTR, #TAB ;表地址送數據指針
SETB 24H.0
CLR 23H.0
CLR 22H.0
;******时间主导程序****************************************
LOOP0:
ACALL DISP ;调用显示
JNB TIAONAO, TING ;一旦按下响铃就去处理使响铃停
JNB TIAOFEN, MT ;查詢分調整鍵
JNB TIAOSHI, HT ;查詢時調整鍵
JNB QIEHUAN, QIEHUAN1 ;切换
MOV A,FEN ;这里到T—3为止都是响铃的判断程序
CJNE A,N_FEN,L_2 ;当分不等时,跳开,不响
MOV A,SHI
CJNE A,N_SHI,T_3 ;时不相等跳开,不响
MOV A,MIAO
CJNE A,#N,L_1 ;CJNE和JC结合来判断秒是否大于N(可改,即改其响铃的时间长短),
L_1:
ANL C,24H.0 ;只有24H.0和C都为1的时候才响铃
JC XIANGLING ;大于N,C的值受影响变为0,小于为1,所以可用来判断是否要响铃
AJMP T_3
L_2:
SETB 24H.0 ;分钟不等的时候再把1还给它
T_3:
CJNE R1,#1,LOOP0 ;查询整点到了没有,到了就往下走去报时
;(在中断里整点到的时候已给R1赋1)
;******整点报时*************************************
SETB LINGSHENG ;整点报时
BAOSHI:
ACALL DISP
DJNZ R5,BAOSHI
CLR LINGSHENG
MOV R1,#0
MOV R5,#250
AJMP LOOP0
;**********闹铃响铃程序******************************
XIANGLING:
JNB 23H.0,LOOP0 ;响铃总允许,=0就跳过不响
CPL LINGSHENG
MOV R2,#GAO ;调此值可改变响一声的长度
T_5:
ACALL DISP
ACALL DISP
DJNZ R2,T_5
CPL LINGSHENG
MOV R2,#DI ;调此值可改变声声间的间隔时间
T_6:
ACALL DISP
ACALL DISP
DJNZ R2,T_6
AJMP LOOP0
;*******切换到闹铃显示的按键程序********************************
QIEHUAN1:
ACALL DISP
DJNZ R5,QIEHUAN1
MOV R5,#250
JB QIEHUAN,LOOP0
AJMP LOOP3
;******调时程序*****************************************
MT: ;分調整
ACALL DISP
ACALL DISP
JNB TIAOFEN, MT ;鍵消抖
INC FEN ;分加1
MOV A, FEN
CJNE A, #60, LOOP0 ;沒到60分返回,到60分清0
MOV FEN, #0
AJMP LOOP0
HT: ;時調整
ACALL DISP
ACALL DISP
JNB TIAOSHI, HT
INC SHI
MOV A,SHI
CJNE A,#24,LOOP0
MOV SHI,#0
AJMP LOOP0
;********** 闹铃停止响程序***************************
TING:
ACALL N_DISP
JNB TIAONAO,TING
CLR LINGSHENG
CLR 24H.0 ;把它清0,不让铃声响
AJMP LOOP0
; *******时间显示子程序******************************************
DISP: ;显示子程序
;秒显示*******
MOV A, MIAO
MOV B, #10
DIV AB
MOVC A, @A+DPTR
MOV DUANMA, A
SETB MIAO_SHI
ACALL D1MS
CLR MIAO_SHI
MOV A, B
MOVC A, @A+DPTR
MOV DUANMA, A
SETB MIAO_GE
ACALL D1MS
CLR MIAO_GE
;分显示*******
MOV A, FEN ;分送A
MOV B, #10
DIV AB ;十進制調整
MOVC A, @A+DPTR ;查表
MOV DUANMA, A ;分十位送DUANMA口顯示
SETB FEN_SHI ;開分十位顯示
ACALL D1MS ;延時1ms
CLR FEN_SHI ;關顯示
MOV A, B ;分個位DUANMA口顯示
ADD A, R0
MOVC A, @A+DPTR
MOV DUANMA, A
SETB FEN_GE
ACALL D1MS
CLR FEN_GE
;时显示*******
MOV A, SHI
MOV B, #10
DIV AB
MOVC A, @A+DPTR
MOV DUANMA, A
SETB SHI_SHI ;顯示時十位
ACALL D1MS
CLR SHI_SHI
MOV A, B
ADD A, R0
MOVC A, @A+DPTR
MOV DUANMA, A
SETB SHI_GE ;顯示時個位
ACALL D1MS
CLR SHI_GE
RET ;返回
;*********闹铃主导程序******************************
LOOP3:
ACALL N_DISP
JNB QIEHUAN,QIEHUAN2 ;查询按键,决定是否该跳回时间显示
JNB TIAOSHI,N_SHIT ;查询按键,决定是否给闹铃时钟加1
JNB TIAOFEN,N_FENT ;查询按键,决定是否给闹铃分钟加1
JNB TIAONAO,N_K ;查询按键,决定是否调节闹钟开关
AJMP LOOP3
;**********闹铃调时程序******************************
N_FENT:
ACALL N_DISP
ACALL N_DISP
JNB TIAOFEN,N_FENT
INC N_FEN
MOV A,N_FEN
CJNE A,#60,LOOP3
MOV N_FEN,#0
AJMP LOOP3
N_SHIT:
ACALL N_DISP
ACALL N_DISP
JNB TIAOSHI,N_SHIT
INC N_SHI
MOV A,N_SHI
CJNE A,#24,LOOP3
MOV N_SHI,#0
AJMP LOOP3
N_K:
ACALL N_DISP
ACALL N_DISP
JNB TIAONAO,N_K
CPL 22H.0 ;为1就显示闹铃开
CPL 23H.0 ;为1就标志开闹铃
AJMP LOOP3
;**********切换回去显示时间的按键程序****************
QIEHUAN2:
ACALL N_DISP
ACALL N_DISP
DJNZ R5,QIEHUAN2
MOV R5,#250
JB QIEHUAN,LOOP3
AJMP LOOP0
;**********闹铃显示程序********************************
N_DISP:
;分显示*******
MOV A,N_FEN ;把闹铃时间分给A
MOV B,#10
DIV AB
MOVC A,@A+DPTR
MOV DUANMA,A ;显示闹铃分十位
SETB FEN_SHI
ACALL D1MS
CLR FEN_SHI
MOV A,B
ADD A,R0
MOVC A,@A+DPTR
MOV DUANMA,A ;显示闹铃分个位
SETB FEN_GE
ACALL D1MS
CLR FEN_GE
;时显示*******
MOV A,N_SHI
MOV B,#10
DIV AB
MOVC A,@A+DPTR
MOV DUANMA,A ;显示闹铃时十位
SETB SHI_SHI
ACALL D1MS
CLR SHI_SHI
MOV A,B
ADD A, R0
MOVC A,@A+DPTR
MOV DUANMA,A ;显示闹铃时个位
SETB SHI_GE
ACALL D1MS
CLR SHI_GE
JNB 22H.0,SET_1 ;=0,就跳
;闹铃开标志显示**** ;这段是可选择的,如果开闹铃(22H.0=1)就往下走显示;否则无显示
MOV DUANMA,#40H
SETB MIAO_SHI
ACALL D1MS
CLR MIAO_SHI
MOV DUANMA,#40H
SETB MIAO_GE
ACALL D1MS
CLR MIAO_GE
SET_1:
RET
;**********中断服务程序******************************
TIMER: ;定時中斷程序
PUSH ACC ;數據保護
PUSH PSW
MOV TL0, #0B2H ;重置50ms定時值(本来是B0的,现在校正了一点用B2就准点了)
MOV TH0, #03CH
DJNZ 20H, RETI_1 ;到0.5秒了嗎?(-1/=0,就跳,到了就往下)
MOV 20H, #10
CPL 25H ;取反秒秒閃爍標志位
JNB 25H, T_1 ;标志位为0转T-1(就是为0就显示秒点)--.
MOV R0, #0 ;查表偏移量寄存器置0(不顯示秒点) !
AJMP T_2 ; !
; !
; !
T_1: ; !
; V
MOV R0, #10 ;查表偏移量寄存器置10(顯示秒点,秒点每秒閃爍1次)
T_2:
DJNZ 21H, RETI_1 ;到1秒了嗎?(-1/=0,就跳)
MOV 21H, #2
INC MIAO ;秒加1
MOV A, MIAO
CJNE A, #60, RETI_1 ;到60秒了嗎?
MOV MIAO, #0 ;到60秒清0
INC FEN ;分加1
MOV A, FEN
CJNE A, #60, RETI_1 ;到60分了嗎?
MOV FEN, #0
MOV R1, #1 ;一个小时到,开始报时
INC SHI ;時加1
MOV A, SHI
CJNE A, #24, RETI_1 ;到24小時了嗎?
MOV SHI, #0
RETI_1:
POP PSW
POP ACC
RETI
;*******延时子程序*************************************
D1MS: ;1毫秒延時
MOV R7, #2
D_1:
MOV R6, #250
DJNZ R6, $
DJNZ R7, D_1
RET
;*******显示列表***************************************
TAB:
DB 3FH,06H,5BH,4FH,66H,6DH,7DH,07H,7FH,6FH ;不带小数点
DB 0BFH,86H,0DBH,0CFH,0E6H,0EDH,0FDH,87H,0FFH,0EFH ;带小数点
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -