/*写命令到LCD中*/
void SendCommandToLCD(uchar com)
{
CheckState();//状态检查,LCD是否忙
RS=0; //向LCD发送命令。RS=0写指令,RS=1写数据
RW=0;//R/W=“L” ,E=“H→L”数据被写到 IR 或 DR
DATA=com; //com :命令
EN=1;//EN下降源
_nop_();
_nop_();
EN=0;
}
/*设置页 0xb8是页的首地址*/
void SetLine(uchar page)
{
page=0xb8|page; //1011 1xxx 0<=page<=7 设定页地址--X 0-7,8行为一页64/8=8,共8页
SendCommandToLCD(page);
}
/*设定显示开始行,0xc0是行的首地址*/
void SetStartLine(uchar startline)
{
startline=0xc0|startline; //1100 0000
SendCommandToLCD(startline); //设置从哪行开始:0--63,一般从0 行开始显示
}
/*设定列地址--Y 0-63 ,0x40是列的首地址*/
void SetColumn(uchar column)
{
column=column &0x3f; //column最大值为64,越出 0=<column<=63
column= 0x40|column; //01xx xxxx
SendCommandToLCD(column);
}
/*开关显示,0x3f是开显示,0x3e是关显示*/
void SetOnOff(uchar onoff)
{
onoff=0x3e|onoff; //0011 111x,onoff只能为0或者1
SendCommandToLCD(onoff);
}
/*写显示数据 */
void WriteByte(uchar dat)
{
CheckState();//状态检查,LCD是否忙
RS=1; //RS=0写指令,RS=1写数据
RW=0;////R/W=“L” ,E=“H→L”数据被写到 IR 或 DR
DATA=dat;//dat:显示数据
EN=1; //EN下降源
_nop_();
_nop_();
EN=0;
}
/*选择屏幕screen: 0-全屏,1-左屏,2-右屏*/
void SelectScreen(uchar screen)
{
switch(screen)
{ case 0: cs1=0;//全屏
_nop_(); _nop_(); _nop_();
cs2=0;
_nop_(); _nop_(); _nop_();
break;
case 1: cs1=0;//左屏
_nop_(); _nop_(); _nop_();
cs2=1;
_nop_(); _nop_(); _nop_();
break;
case 2: cs1=1;//右屏
_nop_(); _nop_(); _nop_();
cs2=0;
_nop_(); _nop_(); _nop_();
break;
}
}
/*清屏screen: 0-全屏,1-左屏,2-右*/
void ClearScreen(uchar screen)
{
uchar i,j;
SelectScreen(screen);
for(i=0;i<8;i++) //控制页数0-7,共8页
{
SetLine(i);
SetColumn(0);
for(j=0;j<64;j++) //控制列数0-63,共64列
{
WriteByte(0x00); //写点内容,列地址自动加1
}
}
}
/*延时程序*/
void delay(uint z)
{
uint i,j;
for(i=0; i<z; i++)
for(j = 0; j < 110; j++);
}
/*初始化LCD*/
void InitLCD()
{
CheckState();
SelectScreen(0);
SetOnOff(0); //关显示
SelectScreen(0);
SetOnOff(1); //开显示
SelectScreen(0);
ClearScreen(0);//清屏
SetStartLine(0); //开始行:0
}
void GUI_Point(uchar x,uchar y,uchar flag)
{
uchar x_Dyte,x_byte; //定义列地址的字节位,及在字节中的哪1位
uchar y_Dyte,y_byte; //定义为上下两个屏(取值为0,1),行地址(取值为0~31)
uchar GDRAM_hbit;
uchar GDRAM_lbit;
uchar shuju;
/***X,Y坐标互换,即普通的X,Y坐标***/
x_Dyte=y/16; //计算在16个字节中的哪一个
x_byte=y&0x0f; //计算在该字节中的哪一位
y_Dyte=x/32; //0为上半屏,1为下半屏
y_byte=x&0x1f; //计算在0~31当中的哪一行
GDRAM_hbit=shuju&0xF0; //读取当前显示高8位数据
GDRAM_lbit=shuju&0x0F; //读取当前显示低8位数据
_nop_();
_nop_();
_nop_();
if(flag==1)
{
SetStartLine(0x80+y_byte); //设定行地址(y坐标)
SetColumn(0x80+x_Dyte); //设定列地址(x坐标)
if(y_Dyte<32)
{
SelectScreen(2);
}
else
{
SelectScreen(0);
}
if(x_byte<8) //判断其在高8位,还是在低8位
{
WriteByte(GDRAM_hbit|(0X01<<(7-x_byte))); //显示GDRAM区高8位数据
WriteByte(GDRAM_lbit); //显示GDRAM区低8位数据
}
else
{
WriteByte(GDRAM_hbit);
WriteByte(GDRAM_lbit|(0x01<<(15-x_byte)));
}
}
else
{
WriteByte(0x00); //清除GDRAM区高8位数据
WriteByte(0x00); //清除GDRAM区低8位数据
}
}
/**********读取当前地址的LCD显示数据**********/
void Read_data()
{
uchar shuju;
RS=1; // D/I=1,代表数据
RW=1; // R/W=1.读取
delay(10);
EN=1;
delay(100);
shuju=DATA; //读取当前显示的数据
_nop_();
EN=0;
return;
}
void hualinex(uchar x0,uchar x1,uchar y,uchar flag)
{
uchar temp;
if(x0>x1)
{
temp=x1;
x1=x0;
x0=temp;
}
for(;x0<=x1;x0++)
GUI_Point(x0, y,flag);
}
/*主函数*/
void main()
{
InitLCD();//初始12864
ClearScreen(0);
SetStartLine(0);//显示开始行
while(1)
{
hualinex(0,127,0,1);
}
}