单片机控制KS0074实现电压表,电流表功能的源码如下:
- ;引脚为:1VCC,2VCC,3GND,4BLA,5DB7,6DB6,7DB5,8DB4,9E,10RW,11RS,12V0,13GND,14GND,15VCC.实际上,可任用其中一个VCC引脚和一个GND引脚。
- ;KS0074有8线并行、4线并行和2线串行输入方式,但set1602默认的输入方式为4数据总线并行输入方式
- ;V0引脚应通过串接800欧左右电阻后接VCC(5V)。或者,在VCC和GND之间串接一个5~10可调电位器,滑动端接V0,利用调节滑动端控制LCD显示对比度。
- ;BLA输入电压应为3.3V,可通过串接合适电阻后接VCC(5V),避免高温烧坏LCD。
- ;---------------------------------------------------------------------------------------------------------------------
- ;以下为硬件连接要求
- DB4 equ p0.4
- DB5 equ p0.5
- DB6 equ p0.6
- DB7 equ p0.7
- RS EQU P2.5
- RW EQU P2.6
- E EQU P2.7
- RCOMDATE equ 70H;作为读取的BF相关指令信息的暂存单元
- WCOMdate equ 71H;作为拟写入指令代码的暂存单元
- RLCDDATE Equ 72H;作为读取LCD相关显示代码或信息的暂存单元
- WLCDDATe EQU 73H;作为拟写入LCD显示信息的暂存单元
- ;-------------------------------------------------------------------------------------------------------
- P1ASF EQU 9DH ;P1口设置寄存器
- ADC_CONTOR EQU 0BCH ;ADC控制寄存器
- ADC_RES EQU 0BDH ;ADC输出高8位
- ADC_RESL EQU 0BEH ;ADC低8为输出
- AUXR1 EQU 0A2H ;设置寄存器
- IJISHU EQU 30H ;电流比较次数计数
- UJISHU EQU 31H ;电压比较次数计数
- IL EQU 32H ;电流低位
- IH EQU 33H ;电流高位
- UL EQU 34H ;电压低位
- UH EQU 35H ;电压高位
- ORG 0000H
- LJMP START
- ORG 002BH
- START:
- MOV P1ASF,#00000011B ;开启P1.0和P1.1作为AD的输入端口
- MOV AUXR1,#04H ;设置AD输出方式
- MOV SP,#5FH ;设置栈底
- MOV IJISHU,#00H
- MOV UJISHU,#00H
- ;×××××××××××××××××××××××××
- LCD:
- MOV SP,#80H
- ;------------------------- -------------------------------------------------------------
- ;首先,开机或复位后,应进行4数据总线和LCD初始化,将默认的8位数据接口改为4位。
- ;---------------------------------------------------------------------------------------------------------------------
- ;开机或复位后,至少应等待20MS以上
- LCALL Delay1MS
- LCALL Delay1MS
- ;第一步功能设置,设为4位数据总线方式输入(DL=0)
- MOV WCOMDATE,#20H
- LCALL INPUTCOMMAND;输入指令0010XXXX(低四位忽略)
- ;第二步功能设置,在保持4位数据总线输入方式下设为两行模式(输入指令00101XXX)
- MOV WCOMDATE,#28H;设成2行显示
- LCALL INPUTCOMMAND;输入指令00101XXX
- ;第三步显示开关设置
- MOV WCOMDATE,#0CH;设成显示开,而光标开和光标闪烁关
- LCALL INPUTCOMMAND;输入指令00001111
- ;第四步清屏
- MOV WCOMDATE,#01H;
- LCALL INPUTCOMMAND;输入指令00000001
- LCALL DELAY1MS;输入功能设置指令需延迟1.53MS以上(除归位指令和本指令执行时间为1.53MS,其余指令执行时间均不足0.1MS)
- ;第五步输入模式设置
- MOV WCOMDATE,#06H;
- LCALL INPUTCOMMAND;输入指令00000110
- ;- ------------------------------------------------------------------------------------------------------------------
- ;然后,将逆序显示变更为正常显示(即使用KS0074的镜向功能)
- ;--------------------------------------------------------------------------------------------------------------------
- ;第一步,功能设置指令,使RE=1
- MOV WCOMDATE,#2CH;
- LCALL INPUTCOMMAND;输入指令00101100
- ;第二步,输入模式设置指令,使BID=1(逆序显示)
- MOV WCOMDATE,#07H;
- LCALL INPUTCOMMAND;输入指令00000111
- ;第三步,功能设置指令,使RE=0,以便后续应用时可使用正常指令
- MOV WCOMDATE,#28H;
- LCALL INPUTCOMMAND;输入指令00101000
- ;-----------------------------------------------------------------------------------------------------------------
- ;第一步,显示第一行的固定字符(40H~4EH,起始位址40H),测试要求全部显示出来
- MOV WCOMDATE,#2CH;功能设置指令,使RE=1,以执行扩充命令
- LCALL INPUTCOMMAND;输入指令00101100
- MOV WCOMDATE,#40H;设SEGRAM地址(格式为01XXABCD,起始地址为40H)
- LCALL INPUTCOMMAND;输入指令40H
- ;(1)显示第一个段码字符即信号强度标志,默认为不显示
- MOV WLCDDATe,#20H;40H控制第一个字符的大部分段码位
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H;41H控制第一个字符中除40H控制段码外的其它位
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H;42H无用
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H;43H无用
- LCALL INPUTDATACODE
- ;(2)显示第二个段码字符即电量显示符号,默认显示满电量
- MOV WLCDDATe,#0FFH;44H控制全部电量显示段码位,对应关系应进一步测试
- LCALL INPUTDATACODE
- ;(3)显示第三个段码字符主菜单标志符,默认显示主菜单符号
- MOV WLCDDATe,#20H;45H控制全部主菜单显示段码位
- LCALL INPUTDATACODE
- MOV WLCDDATe,#00H;46H无用
- LCALL INPUTDATACODE
- MOV WLCDDATe,#00H;47H无用
- LCALL INPUTDATACODE
- MOV WLCDDATe,#00H;48H无用
- LCALL INPUTDATACODE
- ;(4)显示第四个段码字符即闹铃符号,默认不显示
- MOV WLCDDATe,#20H;49H控制闹铃所有段码位
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H;4A无用
- LCALL INPUTDATACODE
- ;(5)显示第五个段码字符打开修笺(书本)符号,默认不显示
- MOV WLCDDATe,#0FFH;4BH控制该符号全部段码
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H;4CH无用
- LCALL INPUTDATACODE
- ;(6)显示第六个段码字符,默认显示
- MOV WLCDDATe,#20H;4DH控制该符号全部段码
- LCALL INPUTDATACODE
- MOV WLCDDATe,#00H;4EH无用
- LCALL INPUTDATACODE
- ;(7)显示第七个段码字符即接听电话符号,默认显示
- MOV WLCDDATe,#20H;55H控制该符号全部段码
- LCALL INPUTDATACODE
- MOV WCOMDATE,#28H;功能设置指令,使RE=0,恢复正常命令状态
- LCALL INPUTCOMMAND
- ;输入指令00101000
- MOV WCOMDATE,#80H;设置DDRAM地址,该行起始80H
- LCALL INPUTCOMMAND
- MOV WLCDDATe,#"Q"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"Q"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#":"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"2"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"8"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"7"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"0"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"5"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"5"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"5"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- MOV WLCDDATe,#"3"
- LCALL INPUTDATACODE
- LCALL DELAY100MS
- LCALL DELAY100MS
- LCALL DELAY100MS
- LCALL DELAY100MS
- LCALL DELAY100MS
- LCALL DELAY100MS
- MOV WCOMDATE,#01H;
- LCALL INPUTCOMMAND;输入指令00000001
- MAIN:
- MOV ADC_CONTOR,#11001001B ;开启P1.1的AD转换,电流
- LCALL AD ;调用AD子程序
- MOV A,ADC_RES
- CJNE A,IH,MAINI
- MOV A,ADC_RESL
- CJNE A,IL,MAINI
- MOV IJISHU,#00H
- SJMP MAINI1
- MAINI: INC IJISHU
- MOV A,#20
- CJNE A,IJISHU,MAINI1
- MOV IJISHU,#00H
- MOV IH,ADC_RES ;保存电流数据
- MOV IL,ADC_RESL
- MAINI1: MOV 0AH,IH
- MOV 0BH,IL
- LCALL TO10
- MOV 0CH,18H
- MOV 0DH,19H
- MOV 0EH,1AH
- MOV A,0AH
- RRC A
- MOV 0AH,A
- MOV A,0BH
- RRC A
- MOV 0BH,A
- MOV A,0AH
- RRC A
- MOV A,0BH
- RRC A
- MOV 09H,A ;09H保存8位电流数据
- MOV ADC_CONTOR,#11001000B ;开启P1.0的AD转换 电压
- LCALL AD ;调用AD子程序
- MOV A,ADC_RES
- CJNE A,UH,MAINU
- MOV A,ADC_RESL
- CJNE A,UL,MAINU
- MOV UJISHU,#00H
- SJMP MAINU1
- MAINU: INC UJISHU
- MOV A,#20
- CJNE A,UJISHU,MAINU1
- MOV UJISHU,#00H
- MOV UH,ADC_RES ;保存电压数据
- MOV UL,ADC_RESL
- MAINU1: MOV 0AH,UH
- MOV 0BH,UL
- LCALL TO10
- MOV 10H,18H
- MOV 11H,19H
- MOV 12H,1AH
- MOV A,0AH
- RRC A
- MOV 0AH,A
- MOV A,0BH
- RRC A
- MOV 0BH,A
- MOV A,0AH
- RRC A
- MOV A,0BH
- RRC A
- MOV 08H,A ;08H保存8位电压数据
- MOV B,09H
- MUL AB
- MOV R2,B
- MOV R3,A
- MOV R4,#61H ;/25000
- MOV R5,#0A8H
- LCALL DIVD
- MOV A,R7
- ADD A,#30H
- MOV 13H,A
- MOV R4,#09H
- MOV R5,#0C4H ;/2500
- LCALL DIVD
- MOV A,R7
- ADD A,#30H
- MOV 14H,A
- MOV R4,#00H
- MOV R5,#250 ;/250
- LCALL DIVD
- MOV A,R7
- ADD A,#30H
- MOV 15H,A
- MOV R4,#00H
- MOV R5,#25 ;/25
- LCALL DIVD
- MOV A,R7
- ADD A,#30H
- MOV 16H,A
- MOV A,R3
- CLR C
- RLC A
- CLR C
- RLC A
- MOV R3,A
- MOV R5,#10
- LCALL DIVD
- MOV A,R7
- ADD A,#30H
- MOV 17H,A
- LCALL XIANSHI
- LJMP MAIN
- ;×××××××××××××××××××××××××××××××××××××××××××××××××××××××××××
- ;AD转换子程序
- ;×××××××××××××××××××××××××××××××××××××××××××××××××××××××××××
- AD: MOV A,ADC_CONTOR
- JNB 0E4H,AD
- CLR 0E4H
- MOV ADC_CONTOR,A
- ;×××××××××××××××××××××××××××××××××××××××××××××××××××××××××××
- ;二-十进制转换子程序,同时加便宜量完成1602的0-9字模地址的转换 输出结果18H 19H 1AH
- ;×××××××××××××××××××××××××××××××××××××××××××××××××××××××××××
- TO10: MOV R2,0AH
- MOV R3,0BH
- MOV R4,#0
- MOV R5,#2
- LCALL DIVD
- MOV A,R6
- MOV R2,A
- MOV A,R7
- MOV R3,A
- MOV R4,#00H
- MOV R5,#100
- LCALL DIVD
- MOV 18H,R7
- MOV A,#30H
- ADD A,18H
- MOV 18H,A
- MOV R5,#10
- LCALL DIVD
- MOV 19H,R7
- MOV A,#30H
- ADD A,19H
- MOV 19H,A
- MOV 1AH,R3
- MOV A,#30H
- ADD A,1AH
- MOV 1AH,A
- RET
- ;×××××××××××××××××××××××××××××××××××××××××××××××××××
- ;双字节除法运算子程序
- ;入口条件: 被除数在R2、R3、除数在R4、R5中,商在R6、R7中。R1用于计数位移量
- ;出口信息: 余数在R2、R3中,双字节商在R4、R5中,OV=1 时溢出。
- ;影响资源: PSW、A、R1~R7
- ;××××××××××××××××××××××××××××××××××××××××××××××××××××××××
- DIVD:PUSH PSW
- PUSH ACC
- MOV R1,#00H ;计数器清零
- MOV R6,#00H
- MOV R7,#00H
- LCALL SUBBD ;判断够不够减
- JC DIVDE
- DIVD1: MOV A,R4
- JB ACC.7,DIVD3 ;判断最高位是不是1
- CLR C ;除数左移一位
- MOV A,R5
- RLC A
- MOV R5,A
- MOV A,R4
- RLC A
- MOV R4,A
- INC R1 ;左移计数器计数
- LCALL SUBBD ;比较左移后够不够减
- JNC DIVD1 ;够减转移,不够减继续
- LCALL DIVDR ;除数右移一位
- DEC R1 ;右移了,所以要-1
- DIVD3: CLR C
- MOV A,R3 ;开始减法
- SUBB A,R5
- MOV R3,A
- MOV A,R2
- SUBB A,R4
- MOV R2,A
- INC R7
- DIVD4: CJNE R1,#00H,DIVD5 ;判断是不是到最后一位了
- SJMP DIVDE
- DIVD5: LCALL DIVDR ;除数右移一位
- MOV A,R7
- CLR C
- RLC A
- MOV R7,A
- MOV A,R6
- RLC A
- MOV R6,A
- DEC R1 ;位置计数器-1
- LCALL SUBBD ;比较够不够减
- JC DIVD4
- SJMP DIVD3
- SUBBD: CLR C ;判断够不够减子程序
- MOV A,R3
- SUBB A,R5
- MOV A,R2
- SUBB A,R4
- RET
- DIVDR: CLR C
- MOV A,R4
- RRC A
- MOV R4,A
- MOV A,R5
- RRC A
- MOV R5,A
- RET
- DIVDE: SETB OV
- POP ACC
- POP PSW
- RET
- XIANSHI:
- ;第二步,在第二行(起始位址为80H)显示“2013-05-15”
- MOV WCOMDATE,#80H;设置DDRAM地址,该行起始80H
- LCALL INPUTCOMMAND
- MOV A,#30H
- CJNE A,10H,DYXY
- MOV WLCDDATe,#20H
- SJMP DYXY1
- DYXY: MOV WLCDDATe,10H ;电压最高位显示0时消隐
- DYXY1: LCALL INPUTDATACODE
- MOV WLCDDATe,11H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#2EH
- LCALL INPUTDATACODE
- MOV WLCDDATe,12H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#56H
- LCALL INPUTDATACODE
-
- MOV WLCDDATe,#20H ;功率部分(13H,14H,15H,16H,17H对应功率的5个数值)
- LCALL INPUTDATACODE ; MOV P
- MOV WLCDDATe,#20H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#20H
- LCALL INPUTDATACODE
- MOV WLCDDATe,13H
- LCALL INPUTDATACODE
- MOV WLCDDATe,14H
- LCALL INPUTDATACODE
- MOV WLCDDATe,15H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#2EH
- LCALL INPUTDATACODE
- MOV WLCDDATe,16H
- LCALL INPUTDATACODE
- MOV WLCDDATe,17H
- LCALL INPUTDATACODE
- MOV WLCDDATe,#57H
- LCALL INPUTDATACODE
-
- ;第三步,在第三行
- ;电流部分(0CH,0DH,0EH对应电流的3个数值)
- MOV WCOMDATE,#90H;设置DDRAM地址
- LCALL INPUTCOMMAND
- MOV WLCDDATe,0CH
- LCALL INPUTDATACODE
- MOV WLCDDATe,#"."
- LCALL INPUTDATACODE
- MOV WLCDDATe,0DH
- LCALL INPUTDATACODE
- MOV WLCDDATe,0EH
- LCALL INPUTDATACODE
- MOV WLCDDATe,#"A"
- LCALL INPUTDATACODE
- RET
- SJMP $
- ;读BF并判断状态子程序
- ;直到LCD空闲时退出本程序
- ;------------------------------------------------------------------------------------------------------------------
- READBFAC:
- PUSH ACC
- BFWAIT:
- SETB DB4;将4位数据线设置到读有效状态
- SETB DB5
- SETB DB6
- SETB DB7
- CLR RS;设置成读BF及AC值操作状态
- SETB RW
- SETB E;第一次读,使LCD将BF及AC值的高4位信息释放到数据总线上。
- MOV C,DB7
- MOV ACC.7,C
- CLR E;高半字节读取完成
- CLR RW
- SETB DB4;将4位数据线设置到读有效状态
- SETB DB5
- SETB DB6
- SETB DB7
- SETB RW
- SETB E;第二次读,使LCD将BF及AC值的低4位信息释放到数据总线上。
- CLR E;第二次读取完成
- JB ACC.7,BFWAIT;LCD忙碌时继续等待并监控,空闲时执行下面指令
- POP ACC
- RET
- ;-------------------------------------------------------------------------------------------------------------------
- ;输入指令子程序INPUTCOMMAND
- ;拟写指令代码存放在WCOMDATE中
- ;-------------------------------------------------------------------------------------------------------------------
- INPUTCOMMAND:
- PUSH ACC
- ;首先,判断LCD是否空闲并视具体情况处理
- LCALL READBFAC
- ;然后,为写指令代码作好准备
- MOV A,WCOMDATE;将拟写指令代码取到A中
- ;再后,将拟写指令代码的高4位写入LCD
- CLR RS;设置成写指令状态
- CLR RW
- SETB E
- MOV C,ACC.7;将高4位送出
- MOV DB7,C
- MOV C,ACC.6
- MOV DB6,C
- MOV C,ACC.5
- MOV DB5,C
- MOV C,ACC.4
- MOV DB4,C
- CLR E
- SETB RW
- CLR RW
- ;最后,将拟写指令代码的低4位写入LCD
- SETB E
- MOV C,ACC.3;将低4位送出
- MOV DB7,C
- MOV C,ACC.2
- MOV DB6,C
- MOV C,ACC.1
- MOV DB5,C
- MOV C,ACC.0
- MOV DB4,C
- CLR E;E的下降沿执行上述指令,将低4位写入LCD
- LCALL DELAY1ms
- POP ACC
- RET
- ;------------------------------------------------------------------------------------------------------------------
- ;写显示数据子程序INPUTDATACODE
- ;拟写数据代码存放在WLCDDATA中
- ;------------------------------------------------------------------------------------------------------------------
- INPUTDATACODE:
- PUSH ACC
- ;首先,判断LCD是否空闲并视具体情况处理
- LCALL READBFAC
- ;然后,为写显示数据作好准备
- MOV A,WLCDDATE;将拟写显示数据取到A中
- ;第三,将拟写数据代码的高4位写入LCD的DDRAM
- SETB RS;设置成写显示数据状态
- clr rw
- setb E
- MOV C,ACC.7;将高4位送出
- MOV DB7,C
- MOV C,ACC.6
- MOV DB6,C
- MOV C,ACC.5
- MOV DB5,C
- MOV C,ACC.4
- MOV DB4,C
- clr E
- setb RW
- CLR RW
- ;最后,将拟写数据代码的低4位写入LCD的DDRAM
- SETB E
- MOV C,ACC.3;将低4位送出
- MOV DB7,C
- MOV C,ACC.2
- MOV DB6,C
- MOV C,ACC.1
- MOV DB5,C
- MOV C,ACC.0
- MOV DB4,C
- CLR E
- LCALL DELAY1ms
- POP ACC
- RET
- ;---------------------------------------------------------------------------------------------------------------------
- ;延时子程序DELAY1MS:针对32MHZ晶振编程,延时不少1MS
- DELAY1MS:
- MOV r6,#22H
- DELAY1ms1:MOV R7,#064H
- DELAY1ms2: NOP
- DJNZ R7,DELAY1ms2
- DJNZ R6,DELAY1ms1
- NOP
- RET
- DELAY100MS: ;@12.000MHz
- PUSH 30H
- PUSH 31H
- PUSH 32H
- MOV 30H,#4
- MOV 31H,#166
- MOV 32H,#206
- NEXT:
- DJNZ 32H,NEXT
- DJNZ 31H,NEXT
- DJNZ 30H,NEXT
- POP 32H
- POP 31H
- POP 30H
- RET
- ;---------------------------------------------------------------------------------------------------------------------
- END
复制代码
|