Download as txt, pdf, or txt
Download as txt, pdf, or txt
You are on page 1of 6

P4 EQU 0E8h

DispBuf0 EQU 40h


DispBuf1 EQU 41h
DispBuf2 EQU 42h
DispBuf3 EQU 43h
Keybuf_P2 EQU 44h
Keybuf_P3 EQU 45h
Key_pre EQU 46h
Key_now EQU 47h
Hex_clk0 EQU 48h
Hex_clk1 EQU 49h
Clk0_up_down BIT 90h
Clk1_up_down BIT 97h
Stable_Key EQU 4Ch
D0 EQU 4Dh ;較高的兩位數 ;****************
D1 EQU 4Eh ;****************
;------------------------------------------
ORG 0000h
SJMP Initial
ORG 000Bh
LJMP Timer0_ISR

Initial: ********************clK1 的都不要


SETB ET0 ; (IE) 可使用 timer0 中斷
SETB EA ; (IE) 斷總開關
MOV TMOD, #11h ; timer0 ,timer1, mode1
MOV TH0, #0F8h ; 設定 timer0 水杯
MOV TL0, #2Fh ; 設定 timer0 水杯
MOV R1, #100 ; for counting timer0
MOV Hex_clk0,#0 ; 碼表 0
CLR Clk0_up_down; 碼表 0 預設向上數

MOV P4, #07Fh


MOV DPTR, #Seven_table
MOV R0, #DispBuf0 ; pointer for DispBuf0~1
MOV DispBuf0, #0
MOV DispBuf1, #0
MOV DispBuf2, #0
MOV DispBuf3, #0
MOV P2, #0FFh ; initiate P2 for input
MOV P3, #0FFh ; initiate P3 for input
MOV Keybuf_P2,#0FFh ; initial : no key pressed
MOV Keybuf_P3,#0FFh ; initial : no key pressed
MOV Key_pre, #0FFh ; for key debouncing
MOV Key_now, #0FFh ; for key debouncing
MOV R3, #50 ; for key debouncing

MOV Stable_Key, #0FFh


CLR TF0 ; timer0 flag 清除為 0

SETB TR0 ;timer0 開始計數

MOV D0,#0 ;****************


MOV D1,#0 ;****************
Loop:
ACALL GetKey
ACALL Delay_KeyDebounce
ACALL Disp_7seg
SJMP Loop
;-------------------------------------------
************ACC 值會不一
樣,用數的
************ANL 加在 MOV
P0 前一行

Disp_7seg:
PUSH 0E0h
MOV A, P4
RL A
JB Acc.4, Out_P4
MOV A, #0FEh
Out_P4:
Dot_1:
JB Acc.0,Dot_2 ;當跑到左邊第二顆顯示器時,特別處理 ;****************
MOV P4, A
MOV A, @R0
MOVC A, @A+DPTR
ANL A,#01111111B ;把原本 DPTR 抓到的值加上點(和 01111111B 做 ANL)
MOV P0, A
SJMP Cont1
Dot_2:
JB Acc.2,Cont ;當跑到左邊第二顆顯示器時,特別處理 ;****************
MOV P4, A
MOV A, @R0
MOVC A, @A+DPTR
ANL A,#01111111B ;把原本 DPTR 抓到的值加上點(和 01111111B 做 ANL)
MOV P0, A
SJMP Cont1 ;處理完成直接跳到 Cont1
Cont: ************原本講義上的
MOV P4, A
MOV A, @R0
MOVC A, @A+DPTR
MOV P0, A
Cont1: 跟講義也一樣
INC R0
MOV A, R0
ANL A, #01000011B
MOV R0, A
POP 0E0h
RET
;-------------------------------------
GetKey:
PUSH 0E0h ; 不能用 PUSH A !!!
MOV Keybuf_P2, P2 ; save to keyBuffer_P2
MOV Keybuf_P3, P3 ; save to keyBuffer_P3
MOV A, Keybuf_P2 ; read out keyBuffer_P2
CJNE A, #0FFh, Get_P2
MOV A,Keybuf_P3 ; read out keyBuffer_P3
CJNE A, #0FFh, Get_P3
SJMP Exit_Getkey
Get_P2:
MOV R4, #0
Check_P2:
JB Acc.0, Check_next_P2
MOV Key_now,R4 ;****************
SJMP Exit_Getkey
Check_next_P2:
RR A
INC R4
CJNE R4, #8, Check_P2
SJMP Exit_Getkey
Get_P3:
MOV R4,#8
Check_P3:
JB Acc.0, Check_next_P3
MOV Key_now,R4 ;****************
SJMP Exit_Getkey
Check_next_P3:
RR A
INC R4
CJNE R4, #16, Check_P3
Exit_Getkey:
POP 0E0h ; 不能用 POP A !!!
RET
;-----------------------------------------
Delay_KeyDebounce:
PUSH 0E0h
ACALL Delay
DJNZ R3, Exit_KeyDebounce
MOV R3, #100 ; reset delay count
MOV A, Key_now
CJNE A, #0FFh, Check_debounce
SJMP Clear_KeyCheck
Check_debounce:
CJNE A, Key_pre, Update_Keypre
Update_Stable_Key:
MOV Stable_Key,Key_now ;****************
ACALL Key_function ;****************
Clear_KeyCheck:
MOV Key_now, #0FFh
MOV Key_pre, #0FFh
SJMP Exit_KeyDebounce
Update_Keypre:
MOV Key_pre, A ; (key_pre) (key_now)
SJMP Exit_KeyDebounce
Exit_KeyDebounce:
POP 0E0h
RET
;--------------------------------------
Key_function:
PUSH 0E0h
MOV A,Stable_Key
Check8:
CJNE A,#8,Check9
CLR Clk0_up_down ;把 Clk0_up_down 設定為 0(代表正數)
MOV A,P1 ;把現在的 P1 值給 A
ANL A,#11111110B ;A 加上最左邊亮燈
MOV P1,A
SJMP Exit_Key_function
Check9:
CJNE A,#9,CheckA
SETB Clk0_up_down ;把 Clk0_up_down 設定為 1(代表倒數)
MOV A,P1
ANL A,#11111111B ;A 加上最左邊不亮燈
MOV P1,A
SJMP Exit_Key_function
CheckA:
CJNE A,#0Ah,CheckB
MOV Hex_clk0,#0 ;把碼表設為 0
MOV D0,#0
MOV D1,#0
MOV DispBuf0,#0
MOV DispBuf1,#0
MOV DispBuf2,#0
MOV DispBuf3,#0
SJMP Exit_Key_function
CheckB:
CJNE A,#0Bh,Exit_Key_function
CPL TR0 ;取 TR0 的互補,暫停或啟動碼錶

Exit_Key_function:
POP 0E0h
RET
;------------------------------------
Timer0_ISR:
PUSH 0E0h
CLR TR0 ;停止 timer0 計數
MOV TH0, #0F8h ;設定 timer0 水杯
MOV TL0, #2Fh ;設定 timer0 水杯
SETB TR0 ;開始 timer0 計數
DJNZ R1, Exit_Timer0 ;是否 0.5s 了
MOV R1, #100 ;reset R1
MOV C,Clk0_up_down ;把 Clk0_up_down copy 到 C
************************
JC Down ;如果 Clk0_up_down 為 1(倒數),則跳到 Down_0
************************
Up:
;最低位元
INC Hex_clk0 ;Hex_clk0++
MOV A,Hex_clk0
CJNE A,#10,Hex_to_Dec ;判斷 Hex_clk0 有沒有超過 10
*********************判斷
MOV Hex_clk0,#0 ;如果有超過 10 就對 D0++,同時把 Hex_clk0 設為 0
INC D0
;中間兩位元
MOV A,D0
CJNE A,#60,Hex_to_Dec
MOV D0,#0
INC D1
;最高位元
MOV A,D1
CJNE A,#10,Hex_to_Dec
MOV D1,#0
SJMP Hex_to_Dec ;跳到最低兩位數的顯示 subroutine
Down:
;最低位元
DEC Hex_clk0 ;Hex_clk0--
MOV A,Hex_clk0 ;判斷 Hex_clk0 有沒有小於 0
CJNE A,#0FFh,Hex_to_Dec ;如果有就 reset 為 99
MOV Hex_clk0,#9
DEC D0
;中間兩位元
MOV A,D0
CJNE A,#0FFh,Hex_to_Dec
MOV D0,#60
DEC D1
;最高位元
MOV A,D1
CJNE A,#0FFh,Hex_to_Dec
MOV D1,#9
SJMP Hex_to_Dec ;跳到最低兩位數的顯示 subroutine

Hex_to_Dec:
;最低位元
MOV DispBuf3,Hex_clk0
;中間兩位元
MOV A,D0
MOV B,#10
DIV AB
MOV DispBuf1,A
MOV DispBuf2,B
;最高位元
MOV DispBuf0,D1
Exit_Timer0:
POP 0E0h
RETI
;---------------------------------------

;------------------------------------
Delay:
MOV R5, #30
delay1: MOV R6, #10
delay2: MOV R7, #100
delay0: DJNZ R7, delay0
DJNZ R6, delay2
DJNZ R5, delay1
RET
;----------------------------
Seven_table:
DB 11000000B ; number 0
DB 11001111B ; number 1
DB 10100100B ; number 2
DB 10110000B ; number 3
DB 10011001B ; number 4
DB 10010010B ; number 5
DB 10000010B ; number 6
DB 11111000B ; number 7
DB 10000000B ; number 8
DB 10010000B ; number 9
DB 10001000B ; number A
DB 10000011B ; number b
DB 10100111B ; number c
DB 10100001B ; number d
DB 10000110B ; number E
DB 10001110B ; number F
END

You might also like