当前位置:首页 > 单片机 > 单片机
[导读] KS0108 128X64LCDC语言AVR程序/*LCD引脚定义1---GND2---VCC3---VLCD4---D/I5---R/W6---E7到14D0-D715--CS116--CS217--RESET18--VEE19--SW20--NC*/#include#includeunsignedcharCurOffset,CurRow,CurPag

KS0108 128X64LCDC语言AVR程序

/*
LCD引脚定义
1---GND
2---VCC
3---VLCD
4---D/I
5---R/W
6---E
7到14D0-D7
15--CS1
16--CS2
17--RESET
18--VEE

19--SW
20--NC
*/
#include
#include

unsignedcharCurOffset,CurRow,CurPage,CurCol;

/*常量定义*/
#defineLCD_STATUS_BUSY0x80
#defineSTART_LINE00xc0
#defineDISPLAY_ON0x3f
#defineDISPLAY_OFF0x3e
#definePARA10x40
//PORTA---数据口PORTB----控制口
volatileunsignedchar*LCD_DIR_PORT=&DDRA;
volatileunsignedchar*LCD_IP_PORT=&PINA;
volatileunsignedchar*LCD_OP_PORT=&PORTA;

volatileunsignedchar*LCD_EN_PORT=&PORTB;
volatileunsignedchar*LCD_CS2_PORT=&PORTB;
volatileunsignedchar*LCD_CS1_PORT=&PORTB;
volatileunsignedchar*LCD_RW_PORT=&PORTB;
volatileunsignedchar*LCD_DI_PORT=&PORTB;

charLCD_EN_BIT=BIT(4);
charLCD_CS2_BIT=BIT(3);
charLCD_CS1_BIT=BIT(2);
charLCD_RW_BIT=BIT(1);
charLCD_DI_BIT=BIT(0);

#defineSET_LCD_E*LCD_EN_PORT|=LCD_EN_BIT//LCD使能
#defineCLEAR_LCD_E*LCD_EN_PORT&=~LCD_EN_BIT//LCD禁止

#defineSET_LCD_DATA*LCD_DI_PORT|=LCD_DI_BIT//选择指令端口
#defineSET_LCD_CMD*LCD_DI_PORT&=~LCD_DI_BIT//选择数据端口

#defineSET_LCD_READ*LCD_RW_PORT|=LCD_RW_BIT//读模式
#defineSET_LCD_WRITE*LCD_RW_PORT&=~LCD_RW_BIT//写模式

#defineSET_LCD_CS2*LCD_CS2_PORT|=LCD_CS2_BIT//左屏选择禁止
#defineCLEAR_LCD_CS2*LCD_CS2_PORT&=~LCD_CS2_BIT//左屏选择使能

#defineSET_LCD_CS1*LCD_CS1_PORT|=LCD_CS1_BIT//左屏选择禁止
#defineCLEAR_LCD_CS1*LCD_CS1_PORT&=~LCD_CS1_BIT//左屏选择使能

#defineLEFT0
#defineRIGHT1
#defineCMD0
#defineDATA1

voidLCD_BUSY(unsignedcharlr)//判断忙标志
{
unsignedcharstatus;
CLI();
if(lr==LEFT)
{
CLEAR_LCD_CS2;//cs2=0
SET_LCD_CS1;//cs1=1
}
else
{
SET_LCD_CS2;//cs2=1
CLEAR_LCD_CS1;//cs1=0
}
SET_LCD_CMD;
*LCD_DIR_PORT=0x00;
*LCD_OP_PORT=0xff;
SET_LCD_READ;
SET_LCD_E;
asm("nop");asm("nop");
asm("nop");asm("nop");
while((*LCD_IP_PORT)&LCD_STATUS_BUSY)
{
CLEAR_LCD_E;
asm("nop");asm("nop");
asm("nop");asm("nop");
SET_LCD_E;
asm("nop");asm("nop");
asm("nop");asm("nop");
}
CLEAR_LCD_E;
SET_LCD_WRITE;
*LCD_OP_PORT=0xff;
SEI();
}

voidwrite_LCD(unsignedcharlr,unsignedcharcd,unsignedchardata)/*写入指令或数据*/
{
CLI();
LCD_BUSY(lr);
if(cd==CMD)SET_LCD_CMD;
elseSET_LCD_DATA;
SET_LCD_WRITE;
SET_LCD_E;
*LCD_DIR_PORT=0xff;
*LCD_OP_PORT=data;
asm("nop");asm("nop");
asm("nop");asm("nop");
CLEAR_LCD_E;
*LCD_OP_PORT=0xff;
SEI();
}
unsignedcharread_LCD(unsignedcharlr)/*读显示数据*/
{
unsignedchardata;

CLI();
LCD_BUSY(lr);
SET_LCD_DATA;
*LCD_DIR_PORT=0x00;
*LCD_OP_PORT=0xff;
SET_LCD_READ;
SET_LCD_E;
asm("nop");asm("nop");
asm("nop");asm("nop");
data=*LCD_IP_PORT;
CLEAR_LCD_E;
SET_LCD_WRITE;

LCD_BUSY(lr);
SET_LCD_DATA;
*LCD_DIR_PORT=0x00;
*LCD_OP_PORT=0xff;
SET_LCD_READ;
SET_LCD_E;
asm("nop");asm("nop");
asm("nop");asm("nop");
data=*LCD_IP_PORT;
CLEAR_LCD_E;
SET_LCD_WRITE;

SEI();
returndata;
}

voidset_start_line_L(unsignedcharline)/*设置显示起始行*///0-63
{
write_LCD(LEFT,CMD,0xc0|line);
}

voidset_start_line_R(unsignedcharline)/*设置显示起始行*///0-63
{
write_LCD(RIGHT,CMD,0xc0|line);
}

voidset_page_L(unsignedcharpage)/*设置X地址设置页*///0-7
{
write_LCD(LEFT,CMD,0xb8|page);
}
voidset_page_R(unsignedcharpage)/*设置X地址设置页*///0-7
{
write_LCD(RIGHT,CMD,0xb8|page);
}

voidset_col_addr_L(unsignedcharcol)/*设置Y地址*///0-63
{
write_LCD(LEFT,CMD,0x40|col);
}

voidset_col_addr_R(unsignedcharcol)/*设置Y地址*///0-63
{
write_LCD(RIGHT,CMD,0x40|col);
}

voidinit_lcd(void)/*初始化函数*/
{
set_start_line_L(0);/*显示起始行为0*/
set_start_line_R(0);/*显示起始行为0*/
write_LCD(LEFT,CMD,DISPLAY_ON);/*开显示*/
write_LCD(RIGHT,CMD,DISPLAY_ON);/*开显示*/
}

voidclr_lcd(void)/*清屏函数*/
{
unsignedcharpages,i;
for(pages=0;pages<8;pages++)
{
set_page_L(pages);/*X页地址*/
set_page_R(pages);/*X页地址*/
for(i=0;i<64;i++)
{
set_col_addr_L(i);//Y
set_col_addr_R(i);//Y
write_LCD(LEFT,DATA,0x0);
write_LCD(RIGHT,DATA,0x0);
}
}
}

//ASCII字模宽度及高度
#defineASC_CHR_WIDTH8
#defineASC_CHR_HEIGHT12

typedefstructtypFNT_ASC16/*汉字字模显示数据结构*/
{
charIndex[1];
charMsk[16];
};
structtypFNT_ASC16constASC_16[]={/*显示为8*16Curier10常规*/
"1",0x00,0x00,0x08,0x08,0xFC,0x00,0x00,0x00,0x00,0x00,0x04,0x04,0x07,0x04,0x04,0x00,
"2",0x00,0x00,0x08,0x04,0x84,0x44,0x38,0x00,0x00,0x00,0x06,0x05,0x04,0x04,0x04,0x00,
"3",0x00,0x00,0x08,0x04,0x44,0x44,0xB8,0x00,0x00,0x00,0x02,0x04,0x04,0x04,0x03,0x00,
"4",0x00,0x00,0x80,0x60,0x18,0xFC,0x00,0x00,0x00,0x00,0x01,0x01,0x05,0x07,0x05,0x00,
"5",0x00,0x00,0x7C,0x44,0x44,0x44,0x84,0x00,0x00,0x00,0x02,0x04,0x04,0x04,0x03,0x00,
"6",0x00,0x00,0xF0,0x48,0x44,0x44,0x80,0x00,0x00,0x00,0x03,0x04,0x04,0x04,0x03,0x00,
"7",0x00,0x00,0x0C,0x04,0x84,0x64,0x1C,0x00,0x00,0x00,0x00,0x06,0x01,0x00,0x00,0x00,
"8",0x00,0x00,0xB8,0x44,0x44,0x44,0xB8,0x00,0x00,0x00,0x03,0x04,0x04,0x04,0x03,0x00,
"9",0x00,0x00,0x38,0x44,0x44,0x44,0xF8,0x00,0x00,0x00,0x00,0x04,0x04,0x02,0x01,0x00,
"0",0x00,0x00,0xF8,0x04,0x04,0x04,0xF8,0x00,0x00,0x00,0x03,0x04,0x04,0x04,0x03,0x00,
".",0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,
",",0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x04,0x00,0x00,0x00,
":",0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,
";",0x00,0x00,0x00,0x00,0x20,0x00,0x00,0x00,0x00,0x00,0x00,0x08,0x04,0x00,0x00,0x00,
"-",0x00,0x80,0x80,0x80,0x80,0x80,0x80,0x80,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
"_",0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,
"A",0x00,0x00,0x80,0x64,0x1C,0x60,0x80,0x00,0x00,0x04,0x07,0x05,0x01,0x05,0x07,0x04,
"B",0x00,0x04,0xFC,0x44,0x44,0x44,0x44,0xB8,0x00,0x04,0x07,0x04,0x04,0x04,0x04,0x03,
"C",0x00,0xF0,0x08,0x04,0x04,0x04,0x04,0x08,0x00,0x01,0x02,0x04,0x04,0x04,0x04,0x02,
"D",0x00,0x04,0xFC,0x04,0x04,0x04,0x08,0xF0,0x00,0x04,0x07,0x04,0x04,0x04,0x02,0x01,
"E",0x00,0x04,0xFC,0x44,0x44,0xE4,0x04,0x0C,0x00,0x04,0x07,0x04,0x04,0x04,0x04,0x06,
"F",0x00,0x04,0xFC,0x44,0x44,0xE4,0x04,0x0C,0x00,0x04,0x07,0x04,0x04,0x00,0x00,0x00,
"",0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
"=",0x00,0x00,0xA0,0xA0,0xA0,0xA0,0xA0,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
"(",0x00,0x00,0x00,0xE0,0x18,0x04,0x00,0x00,0x00,0x00,0x00,0x03,0x0C,0x10,0x00,0x00,
")",0x00,0x00,0x00,0x04,0x18,0xE0,0x00,0x00,0x00,0x00,0x00,0x10,0x0C,0x03,0x00,0x00,
"V",0x00,0x04,0x3C,0xC4,0x00,0xC4,0x3C,0x04,0x00,0x00,0x00,0x01,0x06,0x01,0x00,0x00,
"m",0x00,0x20,0xE0,0x20,0xC0,0x20,0xC0,0x00,0x00,0x04,0x07,0x00,0x07,0x00,0x07,0x04,
"H",0x00,0x04,0xFC,0x44,0x40,0x44,0xFC,0x04,0x00,0x04,0x07,0x04,0x00,0x04,0x07,0x04,
"*",0x90,0x90,0x60,0xFC,0x60,0x90,0x90,0x00,0x00,0x00,0x00,0x03,0x00,0x00,0x00,0x00,
};

#defineASC_Hz_WIDTH12
//#defineASC_HZ_HEIGHT12

typedefstructtypFNT_GB16/*12*16汉字字模显示数据结构*/
{
charIndex[2];
charMsk[24];
};
structtypFNT_GB16constGB_16[]={/*宋体9显示为12*16*/
"科",0x8A,0x6A,0xFE,0x29,0x49,0x80,0x92,0xA4,0x80,0xFF,0x40,0x00,0x01,0x00,0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x07,0x00,0x00,
"技",0x44,0x44,0xFF,0x24,0x00,0x64,0xA4,0x3F,0xA4,0x64,0x04,0x00,0x04,0x04,0x07,0x00,0x04,0x04,0x02,0x01,0x02,0x04,0x04,0x00,
"有",0x42,0x22,0x12,0xFA,0x4E,0x4B,0x4A,0x4A,0xFA,0x02,0x02,0x00,0x00,0x00,0x00,0x07,0x01,0x01,0x01,0x05,0x07,0x00,0x00,0x00,
"限",0xFF,0x81,0x99,0xE7,0x00,0xFF,0x25,0xE5,0x25,0xBF,0x40,0x00,0x07,0x00,0x00,0x00,0x00,0x07,0x04,0x02,0x01,0x02,0x04,0x00,
"公",0x20,0x10,0x08,0x07,0xC0,0x30,0x83,0x0C,0x10,0x20,0x20,0x00,0x00,0x04,0x06,0x05,0x04,0x04,0x02,0x03,0x06,0x00,0x00,0x00,
"司",0x08,0x09,0xE9,0x29,0x29,0x29,0xED,0x09,0x01,0xFF,0x00,0x00,0x00,0x00,0x01,0x01,0x01,0x01,0x01,0x04,0x04,0x07,0x00,0x00,
};

unsignedcharGetPage(void)/*得到当前页*/
{
returnCurPage;
}

unsignedcharGetCol(void)/*得到当前列*/
{
returnCurCol;
}

voidSetPageCol(unsignedcharupage,unsignedcharucol)/*设置液晶的页和列*/
{
CurPage=upage;
CurCol=ucol;
if(ucol<64)
{
set_page_L(upage);
set_col_addr_L(ucol);
}
else
{
set_page_R(upage);
set_col_addr_R(ucol-64);
}
}

/*设置当前显示的页和列*/
voidSetRowCol(unsignedcharurow,unsignedcharucol)
{
unsignedcharpage;
CurRow=urow;
CurCol=ucol;

switch(urow)
{
case1:
page=0;
CurOffset=1;
break;
case2:
page=1;
CurOffset=2;
break;
case3:
page=3;
CurOffset=1;
break;
case4:
page=4;
CurOffset=2;
break;
case5:
page=6;
CurOffset=1;
break;
}
SetPageCol(page,ucol);
}

voiddisp_ch(unsignedcharc)
{
unsignedchark,j,uPage,uCol,ch_r,ch_w;
unsignedcharwidth;
unsignedcharlen;
uPage=GetPage();
uCol=GetCol();
len=sizeof(ASC_16)/sizeof(ASC_16[0]);
for(k=0;k{
if(c==ASC_16[k].Index[0])break;
}
if(k{

if(c==’-’||c==’:’)
width=ASC_CHR_WIDTH-2;
elseif(c==’|’)
width=ASC_HZ_WIDTH-ASC_CHR_WIDTH;
else
width=ASC_CHR_WIDTH;

if(CurOffset==1)//下半部是写半个字节
{
for(j=0;j{
SetPageCol(uPage,uCol+j);
ch_w=ASC_16[k].Msk[j];
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage+1,uCol);

for(j=0;j{
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)ch_r=read_LCD(LEFT);
elsech_r=read_LCD(RIGHT);
ch_r&=0xf0;
ch_w=ASC_16[k].Msk[ASC_CHR_WIDTH+j]&0x0f;
ch_w|=ch_r;
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
}
else//上半部是写半个字节
{
for(j=0;j{
SetPageCol(uPage,uCol+j);
if(uCol+j<64)ch_r=read_LCD(LEFT);
elsech_r=read_LCD(RIGHT);
ch_r&=0x0f;
ch_w=ASC_16[k].Msk[j];
ch_w=ch_w<<4;
ch_w|=ch_r;
SetPageCol(uPage,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage+1,uCol);
for(j=0;j{
SetPageCol(uPage+1,uCol+j);

ch_r=ASC_16[k].Msk[j];
ch_w=ASC_16[k].Msk[ASC_CHR_WIDTH+j];
ch_r=ch_r>>4;
ch_w=ch_w<<4;
ch_w|=ch_r;
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
}
}
SetPageCol(uPage,uCol+width);
}


voiddisp_hz(unsignedchar*hz)
{
unsignedchark,j,uPage,uCol,ch_r,ch_w;
uPage=GetPage();
uCol=GetCol();
for(k=0;k{
if(hz[0]==GB_16[k].Index[0]&&hz[1]==GB_16[k].Index[1])
break;
}

if(CurOffset==1)
{
for(j=0;j{
SetPageCol(uPage,uCol+j);
ch_w=GB_16[k].Msk[j];
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage+1,uCol);

for(j=0;j{
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)ch_r=read_LCD(LEFT);
elsech_r=read_LCD(RIGHT);
ch_r&=0xf0;
ch_w=GB_16[k].Msk[ASC_HZ_WIDTH+j]&0x0f;
ch_w|=ch_r;
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage,uCol+ASC_HZ_WIDTH);
}

else//汉字上半部是写半个字节
{
for(j=0;j{
SetPageCol(uPage,uCol+j);
if(uCol+j<64)ch_r=read_LCD(LEFT);
elsech_r=read_LCD(RIGHT);
ch_r&=0x0f;
ch_w=GB_16[k].Msk[j];
ch_w=ch_w<<4;
ch_w|=ch_r;
SetPageCol(uPage,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage+1,uCol);
for(j=0;j{
SetPageCol(uPage+1,uCol+j);

ch_r=GB_16[k].Msk[j];
ch_w=GB_16[k].Msk[ASC_HZ_WIDTH+j];
ch_r=ch_r>>4;
ch_w=ch_w<<4;
ch_w|=ch_r;
SetPageCol(uPage+1,uCol+j);
if(uCol+j<64)write_LCD(LEFT,DATA,ch_w);
elsewrite_LCD(RIGHT,DATA,ch_w);
}
SetPageCol(uPage,uCol+ASC_HZ_WIDTH);
}
}

voiddisp_str(unsignedchar*p)
{
unsignedchari=0;
while(p[i]>0)
{
if(p[i]<128)
{/*ASCII*/
disp_ch(p[i]);
}
else
{/*中文*/
disp_hz(&p[i]);
i++;
}
i++;
}
}

/*************************************/
/*绘点函数*/
/*************************************/
/*XX--(0-128)YY--(0-63)FLAG=1绘点FLAG=0清点*/
voidpixel(unsignedcharxx,unsignedcharyy,unsignedcharflag)
{
unsignedinty,ch;
ch=yy%8;//余数

y=1;
for(;ch!=0;)
{
y=y*2;
ch--;
}
if(xx<64)
{
set_page_L(yy/8);
set_col_addr_L(xx);
ch=read_LCD(LEFT);
set_col_addr_L(xx);
if(flag)
write_LCD(LEFT,DATA,ch|y);
else
{
y=~y;
ch&=y;
write_LCD(LEFT,DATA,ch|y);
}
}
else
{
set_page_R(yy/8);
set_col_addr_R(xx-64);
ch=read_LCD(RIGHT);
set_col_addr_R(xx-64);
if(flag)
write_LCD(RIGHT,DATA,ch|y);
else
{
y=~y;
ch&=y;
write_LCD(RIGHT,DATA,ch|y);
}
}
}

本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除( 邮箱:macysun@21ic.com )。
换一批
延伸阅读

March 13, 2026 ---- 根据TrendForce集邦咨询最新面板产业研究,由于技术世代更替与生产成本竞争压力提升,以及8.6代线新产能陆续开出,近年台系面板厂逐步关闭小世代产线,并积极发展新兴事业。另一方...

关键字: LCD 面板 笔电

Feb. 11, 2026 ---- Sharp(夏普)于2月10日公告,将执行日本龟山K2工厂(Gen8 2160mmx2460mm)停产计划,后续并将寻找买家接手。TrendForce集邦咨询表示,K2工厂生产的面板...

关键字: IT面板 电子纸 LCD

在软件开发中,边界条件检查是确保程序稳定性的关键环节。当面对参数验证、资源分配或数据完整性校验时,开发者常在if语句和assert断言间徘徊。两者虽都能捕捉错误,但设计哲学与适用场景迥异。

关键字: assert 程序

上海2026年1月8日 /美通社/ -- 近日,MPS芯源系统(NASDAQ: MPWR)发布车规级薄膜晶体管液晶显示器(TFT LCD)偏压驱动器 —— MPQ5613D-...

关键字: LCD TFT 驱动IC 车载显示屏

Jan. 6, 2026 ---- 根据TrendForce集邦咨询最新调查,由于中国农历春节将于二月来临,BOE(京东方)、TCL CSOT(华星)和HKC(惠科)等三大LCD电视面板厂均规划针对后端模组厂实施五至十天...

关键字: LCD 电视面板

在嵌入式系统、智能设备及消费电子领域,LCD显示屏作为人机交互的核心部件,其接口技术直接影响显示性能与系统设计复杂度。其中,RGB接口与MCU接口作为两种主流连接方式,在硬件架构、数据传输机制及适用场景上存在显著差异。

关键字: LCD RGB MCU

【2025年12月19日,中国深圳讯】全彩胆甾相液晶(ChLCD)电子纸技术领导企业——虹彩光电,于本周参与在深圳举办的第16届中国(国际)商用显示系统产业领袖高峰会,并获颁2025年度商显行业「ICDA华显奖-创新应用...

关键字: LCD 太阳能 电子纸

系统通过AHT21传感器连续测量周围环境的温度和湿度。STM32不使用内置库,而是通过定制软件I²C(位敲击)驱动程序与传感器通信,从而完全控制时序和数据传输。

关键字: STM32 AHT21传感器 LCD

没有标记就很难知道齐纳二极管的电压。如果齐纳二极管上的标记被抹去,没有测试电路和适当的设备,我们无法判断齐纳二极管的额定值。因此,今天我们将制作一个齐纳测试仪来获得齐纳二极管的额定电压。一个简单而精确的仪表,然后我们就会...

关键字: 齐纳二极管 Arduino LCD

我的第一个版本是匆忙制作的,我留下了一些重要的东西,比如从microSD卡中检索俳句文本,集成bmp帧,字体管理,开/关开关和一个更好看的3D打印外壳。

关键字: MKRZero 3D打印 LCD
关闭