节日彩灯控制器设计
1. 设计要求
以单片机为核心,设计一个节日彩灯控制器:
P1.2—开始,按此键则灯开始流动(由上而下)。
P1.3—停止,按此键则停止流动,所有灯为暗。
P1.4—上,按此键则灯由上向下流动。
P1.5—下,按此键则灯由下向上流动。
P1.6—向外,按此键则灯由中间向两边流动。
P1.7—向中,按此键则灯由两边向中间流动。
2. 实验原理
本题目本质上是由按键控制功能的流水灯,LED工作的方式通过键盘的扫描实现。其中的LED采取共阳极接法,通过依次向连接LED的I/O口送出低电平,可实现题目要求的功能。本题目需要控制的流水灯较多,共48个,需要I/O口扩展。
3. Proteus仿真
晶振频率为11.0592MHz。仿真结果根据按键变化。
单片机汇编语言源码:
- ORG 0000H
- AJMP MAIN ;/ 复位入口,跳主程序MAIN
- ORG 0003H ;/ INT0*中断入口
- LJMP KEY_INT ;/ 跳向INTO*的中断服务子程序KEY_INT
- ORG 0100H ;/ 主程序入口
- MAIN: MOV SP,60H ;/ 重新设堆栈指针
- SETB IT0 ;/ INTO*为跳沿触发
- MOV IP,#01H ;/ INTO*为高优先级
- SETB EA ;/ 总中断允许
- SETB EX0 ;/ 允许INTO*中断
- MOV P1,0FFH ;/ P1口写入全1,设置P1口为输入状态
- ORG 0300H ;/ 中断入口,查询扫描键盘
- KEY_INT: MOV A,P1 ;/ 读入8个按键的状态
- CPL A ;/ 取反,键闭合的相应位为1
- JZ RETURN ;/ 如A中内容为0,则无键闭合,返回
- LCALL D10ms ;/ A非全0,可能有键闭合,延时10ms,软件去抖
- MOV A,P1 ;/ 重读8个按键的状态,键闭合相应位为0
- CPL A ;/ 取反,键闭合的相应位为1
- JZ RETURN ;/ A中全0,无键闭合,返回;非全0,确认有键闭合
- JB ACC.2,Pkey2 ;/ S2键闭合,跳S2键处理标号Pkey2
- JB ACC.3,Pkey3 ;/ S3键闭合,跳S3键处理标号Pkey3
- JB ACC.4,Pkey4 ;/ S4键闭合,跳S4键处理标号Pkey4
- JB ACC.5,Pkey5 ;/ S5键闭合,跳S5键处理标号Pkey5
- JB ACC.6,Pkey6 ;/ S6键闭合,跳S6键处理标号Pkey6
- JB ACC.7,Pkey7 ;/ S7键闭合,跳S7键处理标号Pkey7
- LJMP RETURN ;/ 查询结束,重新开始
- Pkey2: MOV P2,#0BFH ;/ S0键处理子程序
- MOV A,#80H ;/ PA口、PB口、PC口方式0输出的控制字送A
- MOV R0,#7FH ;/ 8255A控制寄存器地址7FH送入R0
- MOVX @R0,A ;/ 方式控制字送入控制寄存器
- START1: MOV DPTR,#TABLE ;/ 指针指向表头地址
- AP0: MOV A,#00H ;/ 设置地址偏移量
- MOVC A,@A+DPTR ;/ 查表取得数据,送A
- CJNE A,#01H,AP1 ;/ 判断A中数据是否为结束符01H,不是则跳AP1继续执行
- LJMP START2 ;/ 是结束符01H,跳START2继续执行
- AP1: MOV R0,#7CH ;/ PA口地址7CH送入DPTR
- MOVX @R0,A ;/ 将A送PA口输出
- INC DPTR ;/ 指针加1
- LJMP AP0 ;/ 跳AP0执行循环体
- START2: MOV DPTR,#TABLE ;/ 指针指向表头地址
- BP0: MOV A,#00H ;/ 设置地址偏移量
- MOVC A,@A+DPTR ;/ 查表取得数据,送A
- CJNE A,#01H,BP1 ;/ 判断A中数据是否为结束字符01H,不是则跳BP1继续执行
- LJMP START3 ;/ 是结束符01H,跳START3继续执行
- BP1: MOV R0,#7DH ;/ PB口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PB口输出
- INC DPTR ;/ 指针加1
- LJMP BP0 ;/ 跳BP0执行循环体
- START3: MOV DPTR,#TABLE ;/ 指针指向表头地址
- CP0: MOV A,#00H ;/ 设置地址偏移量
- MOVC A,@A+DPTR ;/ 查表取得数据,送A
- CJNE A,#01H,CP1 ;/ 判断A中数据是否为结束字符01H,不是则跳CP1继续执行
- LJMP LD2 ;/ 是结束符01H,跳LD2继续执行
- CP1: MOV R0,#7DH ;/ PC口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PC口输出
- INC DPTR ;/ 指针加1
- LJMP CP0 ;/ 跳CP0执行循环体
- LD2: MOV P2,#7FH
- MOV A,#80H ;/ PA口、PB口、PC口方式0输出的控制字送A
- MOV R0,#7FH ;/ 8255A控制寄存器地址7FH送入R0
- MOVX @R0,A ;/ 方式控制字送入控制寄存器
- START4: MOV DPTR,#TABLE ;/ 指针指向表头地址
- AP01: MOV A,#00H ;/ 设置指针偏移量
- MOVC A,@A+DPTR ;/ 查表取得数据,送A
- CJNE A,#01H,AP1 ;/ 判断A中数据是否为结束字符01H,不是则跳AP11继续执行
- LJMP START5 ;/ 是结束字符跳START5继续执行
- AP11: MOV R0,#7CH ;/ PA口地址7CH送入DPTR
- MOVX @R0,A ;/ 将A送PA口输出
- INC DPTR ;/ 指针加1
- LJMP AP01 ;/ 跳AP01执行循环体
- START5: MOV DPTR,#TABLE
- BP01: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,BP11
- LJMP START6
- BP11: MOV R0,#7DH ;/ PB口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PB口输出
- INC DPTR
- LJMP BP01
- START6: MOV DPTR,#TABLE
- CP01: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,CP11
- LJMP LD3
- CP11: MOV R0,#7DH ;/ PC口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PC口输出
- INC DPTR
- LJMP CP01
- LD3: LJMP RETURN ;/ 跳向中断返回
- Pkey3: MOV P2,#0FFH ;/ S0键处理子程序
- LJMP RETURN ;/ 跳向中断返回
- Pkey4: LJMP Pkey2
- LJMP RETURN
- Pkey5: MOV P2,#0BFH
- MOV A,#80H ;/ PA口、PB口、PC口方式0输出的控制字送A
- MOV R0,#7FH ;/ 8255A控制寄存器地址7FH送入R0
- MOVX @R0,A ;/ 方式控制字送入控制寄存器
- START11: MOV DPTR,#TABLE
- AP02: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,AP12
- LJMP START2
- AP12: MOV R0,#7EH ;/ PC口地址7EH送入DPTR
- MOVX @R0,A ;/ 将A送PC口输出
- INC DPTR
- LJMP AP02
- START21: MOV DPTR,#TABLE
- BP02: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,BP12
- LJMP START3
- BP12: MOV R0,#7DH ;/ PB口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PB口输出
- INC DPTR
- LJMP BP02
- START31: MOV DPTR,#TABLE
- CP02: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,CP12
- LJMP LD2
- CP12: MOV R0,#7CH ;/ PA口地址7CH送入DPTR
- MOVX @R0,A ;/ 将A送PA口输出
- INC DPTR
- LJMP CP02
- LJMP RETURN
- Pkey6: MOV A,#80H ;/ PA口、PB口、PC口方式0输出的控制字送A
- MOV R0,#7FH ;/ 8255A控制寄存器地址7FH送入R0
- MOVX @R0,A ;/ 方式控制字送入控制寄存器
- START12: MOV DPTR,#TABLE
- AP03: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,AP13
- LJMP START2
- AP13: MOV R0,#7EH ;/ PC口地址7EH送入DPTR
- MOVX @R0,A ;/ 将A送PC口输出
- INC DPTR
- LJMP AP03
- START22: MOV DPTR,#TABLE
- BP03: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,BP13
- LJMP START3
- BP13: MOV R0,#7DH ;/ PB口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PB口输出
- INC DPTR
- LJMP BP03
- START32: MOV DPTR,#TABLE
- CP03: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,CP13
- LJMP LD2
- CP13: MOV R0,#7CH ;/ PA口地址7CH送入DPTR
- MOVX @R0,A ;/ 将A送PA口输出
- INC DPTR
- LJMP CP03
- LJMP RETURN
- Pkey7: MOV A,#80H ;/ PA口、PB口、PC口方式0输出的控制字送A
- MOV R0,#7FH ;/ 8255A控制寄存器地址7FH送入R0
- MOVX @R0,A ;/ 方式控制字送入控制寄存器
- START13: MOV DPTR,#TABLE
- AP04: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,AP14
- LJMP START2
- AP14: MOV R0,#7CH ;/ PA口地址7CH送入DPTR
- MOVX @R0,A ;/ 将A送PA口输出
- INC DPTR
- LJMP AP04
- START23: MOV DPTR,#TABLE
- BP04: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,BP14
- LJMP START3
- BP14: MOV R0,#7DH ;/ PB口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PB口输出
- INC DPTR
- LJMP BP04
- START33: MOV DPTR,#TABLE
- CP04: MOV A,#00H
- MOVC A,@A+DPTR
- CJNE A,#01H,CP14
- LJMP LD2
- CP14: MOV R0,#7DH ;/ PC口地址7DH送入DPTR
- MOVX @R0,A ;/ 将A送PC口输出
- INC DPTR
- LJMP CP04
- LJMP RETURN ;/ 跳向中断返回
- D10ms: MOV R7,#25 ;/ 延时10ms子程序,采用双重循环
- D1: MOV R6,#200
- DJNZ R6,[ DISCUZ_CODE_1 ]nbsp; ;/ R6减1非0,原地跳转
- DJNZ R7,D1
- RET
- RETURN: RETI ;/ INTO*中断返回
- TABLE: DB 7FH,0BFH,0DFH,0EFH,0F7H,0FBH,0FDH,0FEH
- DB 01H
- END
复制代码
|