51单片机实验——用3个按键控制8个LED灯闪烁状态

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
/*没有按键按下时,8个小灯亮500MS,灭500M循环*/
ORG 00H;程序起始
START:
MOV P0,#00H ;把P0口清零,灯就亮了
CALL DELAY
MOV P0,#0FFH ;把P0口都置1,灯灭
CALL DELAY
JMP START

/*按下第一个按键时,8个小灯间隔4个亮,4个灭,500MS循环*/
START:
MOV P0,#55H ;把P0口清零,灯就亮了
CALL DELAY
MOV P0,#0AAH ;把P0口都置1,灯灭
CALL DELAY
JMP START

/*按下第二个按键,8个小灯全灭,然后每隔500MS从左向右依次亮一个,全亮后再熄灭,如此循环*/
ORG 0FFH ;开始小灯全灭
MAIN:MOV DPTR,#TABLE ;TABLE是一个数组,下面会定义 。就是把数组中的值存入DPTR
MOV R0,#0 ;把R0的初始值设为0
LOOP:MOV A,R0 ;把初值给累加器A
MOVC A,@A+DPTR ;间接寻址,取表中的代码,@A等同于指向DPTR的指针。整句话的意思是从DPTR开始偏移A个地址的数读取到A中
MOV P0,A
CALL DELAY
INC R0 ;R0自增1
CJNE R0,#9,LOOP ;CJNE表示如果不相等就转移,这里是如果R0不等于9那么就跳转到LOOP函数继续执行,如果是9了那就接下去执行
JMP MAIN ;这里说明已经依次亮起了,那么就可以跳回MAIN函数重新大循环一遍



DELAY:MOV R5,#5 ;写一个延时函数,延时500MS
D1:MOV R6,#200
D2:MOV R7,#250
DJNZ R7,$
DJNZ R6,D2
DJNZ R5,D1
RET


/*下面是一个数组*/
TABLE: DB 0FEH,0FCH,0F8H,0F0H,0E0H,0C0H,80H,00H,0FFH
END


MAIN: MOV P1,#0FFH ;P1口初始值都是1,就是都不被按下
/*当P1口有一个按钮被按下,P1口就不会都是11111111了,肯定有一个是0*/
LOOP: MOV A,P1 ;当一个按钮被按下的时候,P1变成比如11011111,我们把这个值移给累加器
MOV P0,A ;再把累加器的值给P0,P0是灯的接口。这是对应的,比如P2的0口被按下,那么P0的0口就会亮
JMP LOOP
END

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
FIRST BIT P1.0
SECOND BIT P1.1
THIRD BIT P1.2
ORG 00H
MAIN:MOV P0,#00H
/*MOV DPTR,#TABLE这条可能不用*/


KEY1:JB FIRST,KEY2 ;如果FIRST没有被按下即为1,则跳转到KEY2,如果被按下,则执行下面语句
CALL DELAY ;调用延时,消除抖动
JNB FIRST,$ ;松手检测,只有按下之后松手FIRST为1之后,程序才能执行
CALL DELAY ;调用延时,消除抖动
/*开始执行*/
LOOP1:
JNB THIRD,KEY3 ;如果THIRD被按下,则跳转到KEY3
MOV P0,#55H
CALL DELAY
MOV P0,#0AAH
CALL DELAY
JMP LOOP1

KEY2:JB SECOND,KEY3
CALL DELAY ;调用延时,消除抖动
JNB FIRST,$ ;松手检测,只有按下之后松手,程序才能执行
CALL DELAY ;调用延时,消除抖动
/*开始执行*/
ORG 0FFH ;开始小灯全灭
LOOP2:
JNB THIRD,KEY3 ;如果THIRD被按下,则跳转到KEY3
MOV DPTR,#TABLE ;TABLE是一个数组,下面会定义 。就是把数组中的值存入DPTR
MOV R0,#0 ;把R0的初始值设为0
LOOP3:MOV A,R0 ;把初值给累加器A
MOVC A,@A+DPTR ;间接寻址,取表中的代码,@A等同于指向DPTR的指针。整句话的意思是从DPTR开始偏移A个地址的数读取到A中
MOV P0,A
CALL DELAY
INC R0 ;R0自增1
CJNE R0,#9,LOOP3 ;CJNE表示如果不相等就转移,这里是如果R0不等于9那么就跳转到LOOP函数继续执行,如果是9了那就接下去执行
JMP LOOP2 ;这里说明已经依次亮起了,那么就可以跳回LOOP2函数重新大循环一遍

KEY3:JB THIRD,KEY0
CALL DELAY ;调用延时,消除抖动
JNB FIRST,$ ;松手检测,只有按下之后松手,程序才能执行
CALL DELAY ;调用延时,消除抖动
/*开始执行*/
JMP MAIN

KEY0:;没有按键被按下
MOV P0,#00H ;把P0口清零,灯就亮了
CALL DELAY
MOV P0,#0FFH ;把P0口都置1,灯灭
CALL DELAY
JMP KEY1

DELAY:MOV R5,#5 ;写一个延时函数,延时500MS
D1:MOV R6,#200
D2:MOV R7,#250
DJNZ R7,$
DJNZ R6,D2
DJNZ R5,D1
RET

/*下面是一个数组*/
TABLE: DB 0FEH,0FCH,0F8H,0F0H,0E0H,0C0H,80H,00H,0FFH
END

上面的这个有bug,没有实现KEY2的操作,现在写一个没有KEY2的程序(以下代码已经通过测试)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
FIRST BIT P1.0
SECOND BIT P1.1
THIRD BIT P1.2
MAIN:
KEY1:JB FIRST,KEY2
CALL DELAY
JNB FIRST,$
CALL DELAY
LOOP1:
JNB THIRD,KEY2
MOV P0,#55H
CALL DELAY
MOV P0,#0AAH
CALL DELAY
JMP LOOP1
KEY2:
JB THIRD,KEY0
CALL DELAY
JNB FIRST,$
CALL DELAY
JMP MAIN

KEY0:
MOV P0,#00H
CALL DELAY
MOV P0,#0FFH
CALL DELAY
JMP KEY1
DELAY:MOV R5,#5
D1:MOV R6,#200
D2:MOV R7,#250
DJNZ R7,$
DJNZ R6,D2
DJNZ R5,D1
RET
END

本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!