📄 lcd12864.s
字号:
.module lcd12864.c
.area text(rom, con, rel)
.dbfile D:\mega16\drive\lcd12864.c
.dbfunc e wcodeL _wcodeL fV
; left_code -> R20
.even
_wcodeL::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 80
; /******************************************************************************
; /* LCD12864驱动程序
; /* 文 件 名:LCD12864
; /* 创建时间:2004年12月24日
; /* 创 建 人:胡勇刚
; /* Email: hygbeyond@163.com
; //******************************************************************************
; /* 这是根据我以前所做的C51的程序移值的,这个驱动已经在mega16L上运行成功了
; /* 这个驱动要注意的是:你用的mega系列的话,要注意和JTAG,ISP的冲突问题,如果
; /* 用的是C口作为数据口的话,就一定要关闭JTAG,记住如果要用JTAG作为仿真用的话
; /* 尽量的不要用这几个脚,否则就关闭JTAG(特别是作为I/O口)
; /* 我就是因为这个问题浪费了不少时间,主要的现象是插上LCD就不工作,
; /* 拔掉LCD就一切正常,好像应该是LCD触发了JTAG,从而使芯片进入仿真状态了
; /* 还有一点就是时钟频率,如果时钟频率高的话,需要修改DELAY_COUNT值
; /* 不然的话显示会有问题,这是因为12864本身的反应速度比较慢的原因
; /* 我现在所用的是mege16L 频率: 3.6864M
; /*
; /* 各位大虾如果有比这个驱动更优化的程序,请给我一份,就用上面的邮箱.谢谢了
; //*****************************************************************************/
; #define LCD_12864_H
;
; #include "..\c\config.h"
;
; //****************************************************************************
; #ifndef uchar
; #define uchar unsigned char
; #define uint unsigned int
; #endif
; //***************************************************************************/
;
;
; /***************************************************************************
; #ifndef LCD_DI
;
; #define LCD_DI PB0
; #define LCD_RW PB1
; #define LCD_EN PB2
; #define LCD_CS1 PB3
; #define LCD_CS2 PB4
;
; #define LCD_DATA_IN PINC
; #define LCD_DATA_OUT PORTC
; #define LCD_DATA_DDR DDRC
;
; #define LCD_CODE_OUT PORTB
;
; #define LCD_DI_H LCD_CODE_OUT |= BIT(LCD_DI)
; #define LCD_DI_L LCD_CODE_OUT &= ~BIT(LCD_DI)
; #define LCD_RW_H LCD_CODE_OUT |= BIT(LCD_RW)
; #define LCD_RW_L LCD_CODE_OUT &= ~BIT(LCD_RW)
; #define LCD_EN_H LCD_CODE_OUT |= BIT(LCD_EN)
; #define LCD_EN_L LCD_CODE_OUT &= ~BIT(LCD_EN)
; #define LCD_CS1_H LCD_CODE_OUT |= BIT(LCD_CS1)
; #define LCD_CS1_L LCD_CODE_OUT &= ~BIT(LCD_CS1)
; #define LCD_CS2_H LCD_CODE_OUT |= BIT(LCD_CS2)
; #define LCD_CS2_L LCD_CODE_OUT &= ~BIT(LCD_CS2)
;
; #endif
; //****************************************************************************/
;
; #define PRE_PAGE 0xb8 //预设LCD页地址
; #define PRE_COL 0x40 //预设LCD列地址
; #define DELAY_COUNT 50 //LCD延迟时间数
;
; #define LCD_NOP lcd_delay() //延迟
; #define LCD_STAY LCD_NOP,LCD_NOP,LCD_CS1_H,LCD_CS2_H
;
; #define addressL(page,col) wcodeL(PRE_PAGE+page),wcodeL(PRE_COL+col)
; #define addressR(page,col) wcodeR(PRE_PAGE+page),wcodeR(PRE_COL+col)
;
; //*****************************************************************************
; void lcd_delay(void); //延迟
; void wcodeL(uchar left_code); //左屏写入命令
; void wdataL(uchar left_data); //左屏写入数据
; void wcodeR(uchar right_code); //右屏写入命令
; void wdataR(uchar right_data); //右屏写入数据
; //***************************************************************************/
;
; void wcodeL(uchar left_code)//左屏写指令
; {
.dbline 81
; LCD_DATA_DDR = 0X00;
clr R2
out 0x1a,R2
xjmp L3
L2:
.dbline 82
; while(1){
.dbline 84
; //如果液晶空闲开始写数据和命令
; LCD_CODE_OUT |= ((1<<LCD_EN) | (1<<LCD_RW) | (1<<LCD_CS2));
in R24,0x18
ori R24,22
out 0x18,R24
.dbline 85
; LCD_CODE_OUT &= ~((1<<LCD_DI) | (1<<LCD_CS1));
in R24,0x18
andi R24,246
out 0x18,R24
.dbline 86
; if(!(LCD_DATA_IN & 0X80)){
sbic 0x19,7
rjmp L5
.dbline 86
.dbline 87
; break;
xjmp L4
L5:
.dbline 89
L3:
.dbline 82
xjmp L2
L4:
.dbline 90
; }
; }
; LCD_RW_L;
cbi 0x18,1
.dbline 91
; LCD_DATA_DDR = 0XFF;
ldi R24,255
out 0x1a,R24
.dbline 92
; LCD_DATA_OUT = left_code;
out 0x1b,R20
.dbline 93
; LCD_NOP;
xcall _lcd_delay
.dbline 94
; LCD_EN_L;
cbi 0x18,2
.dbline -2
L1:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r left_code 20 c
.dbend
.dbfunc e wdataL _wdataL fV
; left_data -> R20
.even
_wdataL::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 100
; }
;
; //---------------------------------------------------------------------------------
;
; void wdataL(uchar left_data)//左屏写数据
; {
.dbline 101
; LCD_DATA_DDR = 0X00;
clr R2
out 0x1a,R2
xjmp L9
L8:
.dbline 102
; while(1){
.dbline 104
; //如果液晶空闲开始写数据和命令
; LCD_CODE_OUT |= ((1<<LCD_EN) | (1<<LCD_RW) | (1<<LCD_CS2));
in R24,0x18
ori R24,22
out 0x18,R24
.dbline 105
; LCD_CODE_OUT &= ~((1<<LCD_DI) | (1<<LCD_CS1));
in R24,0x18
andi R24,246
out 0x18,R24
.dbline 106
; if(!(LCD_DATA_IN & 0X80)){
sbic 0x19,7
rjmp L11
.dbline 106
.dbline 107
; break;
xjmp L10
L11:
.dbline 109
L9:
.dbline 102
xjmp L8
L10:
.dbline 110
; }
; }
; LCD_RW_L;
cbi 0x18,1
.dbline 111
; LCD_DI_H;
sbi 0x18,0
.dbline 112
; LCD_DATA_DDR = 0XFF;
ldi R24,255
out 0x1a,R24
.dbline 113
; LCD_DATA_OUT = left_data;
out 0x1b,R20
.dbline 114
; LCD_NOP;
xcall _lcd_delay
.dbline 115
; LCD_EN_L;
cbi 0x18,2
.dbline -2
L7:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r left_data 20 c
.dbend
.dbfunc e wcodeR _wcodeR fV
; right_code -> R20
.even
_wcodeR::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 121
; }
;
; //----------------------------------------------------------------------------------
;
; void wcodeR(uchar right_code)//右屏写指令
; {
.dbline 122
; LCD_DATA_DDR = 0X00;
clr R2
out 0x1a,R2
xjmp L15
L14:
.dbline 123
; while(1){
.dbline 125
; //如果液晶空闲开始写数据和命令
; LCD_CODE_OUT |= ((1<<LCD_EN) | (1<<LCD_RW) | (1<<LCD_CS1));
in R24,0x18
ori R24,14
out 0x18,R24
.dbline 126
; LCD_CODE_OUT &= ~((1<<LCD_DI) | (1<<LCD_CS2));
in R24,0x18
andi R24,238
out 0x18,R24
.dbline 127
; if(!(LCD_DATA_IN & 0X80)){
sbic 0x19,7
rjmp L17
.dbline 127
.dbline 128
; break;
xjmp L16
L17:
.dbline 130
L15:
.dbline 123
xjmp L14
L16:
.dbline 131
; }
; }
; LCD_RW_L;
cbi 0x18,1
.dbline 132
; LCD_DATA_DDR=0XFF;
ldi R24,255
out 0x1a,R24
.dbline 133
; LCD_DATA_OUT=right_code;
out 0x1b,R20
.dbline 134
; LCD_NOP;
xcall _lcd_delay
.dbline 135
; LCD_EN_L;
cbi 0x18,2
.dbline -2
L13:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r right_code 20 c
.dbend
.dbfunc e wdataR _wdataR fV
; right_data -> R20
.even
_wdataR::
xcall push_gset1
mov R20,R16
.dbline -1
.dbline 141
; }
;
; //-------------------------------------------------------------------------------
;
; void wdataR(uchar right_data)//写右屏数据
; {
.dbline 142
; LCD_DATA_DDR = 0X00;
clr R2
out 0x1a,R2
xjmp L21
L20:
.dbline 143
; while(1){
.dbline 145
; //如果液晶空闲开始写数据和命令
; LCD_CODE_OUT |= ((1<<LCD_EN) | (1<<LCD_RW) | (1<<LCD_CS1));
in R24,0x18
ori R24,14
out 0x18,R24
.dbline 146
; LCD_CODE_OUT &= ~((1<<LCD_DI) | (1<<LCD_CS2));
in R24,0x18
andi R24,238
out 0x18,R24
.dbline 147
; if(!(LCD_DATA_IN & 0X80)){
sbic 0x19,7
rjmp L23
.dbline 147
.dbline 148
; break;
xjmp L22
L23:
.dbline 150
L21:
.dbline 143
xjmp L20
L22:
.dbline 151
; }
; }
; LCD_RW_L;
cbi 0x18,1
.dbline 152
; LCD_DI_H;
sbi 0x18,0
.dbline 153
; LCD_DATA_DDR = 0XFF;
ldi R24,255
out 0x1a,R24
.dbline 154
; LCD_DATA_OUT = right_data;
out 0x1b,R20
.dbline 155
; LCD_NOP;
xcall _lcd_delay
.dbline 156
; LCD_EN_L;
cbi 0x18,2
.dbline -2
L19:
xcall pop_gset1
.dbline 0 ; func end
ret
.dbsym r right_data 20 c
.dbend
.dbfunc e lcd_init _lcd_init fV
; x -> R20
; y -> R22
.even
_lcd_init::
xcall push_gset2
.dbline -1
.dbline 162
; }
;
; //----------------------------------------------------------------------------------
;
; void lcd_init(void)
; {
.dbline 165
; uchar x,y;
; //设置显示起始行
; wcodeL(0x0c0);
ldi R16,192
xcall _wcodeL
.dbline 166
; wcodeR(0x0c0);
ldi R16,192
xcall _wcodeR
.dbline 169
;
; //开显示
; wcodeL(0x3f);
ldi R16,63
xcall _wcodeL
.dbline 170
; wcodeR(0x3f);
ldi R16,63
xcall _wcodeR
.dbline 172
clr R20
xjmp L29
L26:
.dbline 172
;
; for(x=0;x<8;x++){
.dbline 173
; wcodeL(PRE_PAGE+x);
mov R16,R20
subi R16,72 ; addi 184
xcall _wcodeL
.dbline 174
clr R22
xjmp L33
L30:
.dbline 174
.dbline 175
mov R16,R22
subi R16,192 ; addi 64
xcall _wcodeL
.dbline 176
clr R16
xcall _wdataL
.dbline 177
L31:
.dbline 174
inc R22
L33:
.dbline 174
cpi R22,64
brlo L30
.dbline 178
L27:
.dbline 172
inc R20
L29:
.dbline 172
cpi R20,8
brlo L26
.dbline 179
clr R20
xjmp L37
L34:
.dbline 179
; for(y=0;y<64;y++){
; wcodeL(PRE_COL+y);
; wdataL(0);
; }
; }
; for(x=0;x<8;x++){
.dbline 180
; wcodeR(PRE_PAGE+x);
mov R16,R20
subi R16,72 ; addi 184
xcall _wcodeR
.dbline 181
clr R22
xjmp L41
L38:
.dbline 181
.dbline 182
mov R16,R22
subi R16,192 ; addi 64
xcall _wcodeR
.dbline 183
clr R16
xcall _wdataR
.dbline 184
L39:
.dbline 181
inc R22
L41:
.dbline 181
cpi R22,64
brlo L38
.dbline 185
L35:
.dbline 179
inc R20
L37:
.dbline 179
cpi R20,8
brlo L34
.dbline -2
L25:
xcall pop_gset2
.dbline 0 ; func end
ret
.dbsym r x 20 c
.dbsym r y 22 c
.dbend
.dbfunc e lcd_clear_range _lcd_clear_range fV
; x -> R20
; range -> R22
.even
_lcd_clear_range::
xcall push_gset2
mov R22,R16
.dbline -1
.dbline 189
; for(y=0;y<64;y++){
; wcodeR(PRE_COL+y);
; wdataR(0);
; }
; }
; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -