Understanding the Principles and Code of the 12864 LCD Module

Understanding the Principles and Code of the 12864 LCD Module

The 12864 dot matrix LCD display module (LCM) consists of an array of 128 columns and 64 rows, made up of 128*64 liquid crystal display points. Each display point corresponds to a binary number, where 1 indicates on and 0 indicates off. The RAM that stores this dot matrix information is called the display data memory. To display a certain graphic or Chinese character, the corresponding dot matrix information must be written into the appropriate storage unit.

The dot matrix information for graphics or Chinese characters is designed by the user. The key issue is the relationship between the position of the display points on the LCD screen (rows and columns) and their addresses in the memory. Since most LCD display modules are driven by one row driver and two column drivers, the 12864 LCD screen is actually made up of two independent 64*64 LCD screens stitched together, with each half screen having a 512*8 bits display data RAM.

The driving circuits and memory for the left and right half screens are selected by chip select signals CS1 and CS2. (Some manufacturers simplify user designs by adding decoding circuits in the module, making the 128*64 LCD screen a complete screen that only requires one chip select signal.) The position of the display points on the 64*64 LCD screen is determined by the row number (line, 0~63) and column number (column, 0~63). The address of a certain storage unit in the 512*8 bits RAM is determined by the page address (Xpage, 0~7) and column address (Yaddress, 0~63). Each storage unit stores the display information of 8 liquid crystal points.

To make the correspondence between the liquid crystal point position information and storage addresses more intuitive, the 64*64 LCD screen is divided into 8 display blocks from top to bottom, with each block consisting of 8 rows and 64 columns of points. The 8 rows of dot matrix information in each column form an 8-bit binary number stored in a storage unit. (It should be noted that the order of the high and low bits of the binary number corresponds to the row number and may vary by manufacturer.) The RAM area that stores one display block is called a storage page. Therefore, the dot matrix information of the 64*64 LCD screen is stored in 8 storage pages, each containing 64 bytes, with each byte storing one column (8 rows) of dot matrix information. Thus, the address of a storage unit includes the page address (Xpage, 0~7) and column address (Yaddress, 0~63).

For example, to light up the liquid crystal point at position (20, 30) on the 128*64 screen, since the column address 30 is less than 64, this point is in the left half screen at the 29th column, so CS1 is valid; the row address 20 divided by 8 gives a quotient of 2 and a remainder of 4, meaning this point has a page address of 2 in RAM and a sequence number of 4 in the byte; therefore, the binary data 00010000 (or possibly 00001000, depending on the manufacturer) is written into the storage unit at Xpage=2 and Yaddress=29 to light up the liquid crystal point at (20, 30).

    /////LCD12864 LCD Screen Test Program (Passed)//////////////LCD Screen Model: HJ12864M-1//////////
///////////////////////////////////////
#include <reg52.h>
#define uchar unsigned char
#define uint unsigned int
//8bit data connected to IO port
#define Part P0    //P0 connects to 8-bit data line//Control data port
sbit LCD_RS=P2^5;  //Define 12864 LCD RS terminal, register select signal H: data register L: instruction register
sbit LCD_RW=P2^6;  //Define 12864 LCD RW terminal, read/write signal H: read   L: write
sbit LCD_EN=P2^7;  //Define 12864 LCD LCDEN terminal, chip select signal, falling edge triggered, latch data//
sbit LCD_PSB=P3^2;  //Define 12864 LCD PSB terminal, H: parallel L: serial
sbit LCD_RST=P3^4;  //Define 12864 LCD RST terminal, H: no reset  L: reset
uchar code dis1[]={"The bright moon before my bed"};
uchar code dis2[]={"I suspect it’s frost on the ground"};
uchar code dis3[]={"I raise my head to gaze at the bright moon"};
uchar code dis4[]={"I lower my head and think of my hometown"};
//=====================================
//Millisecond delay function
void delay(uint xms)
{
uint i,j;
for(j=0;j<xms;j++)
for(i=0;i<110;i++);
}
//=====================================
//LCD busy detection function
bit lcd_busy()
{
bit result;
LCD_RS=0;
LCD_RW=1;
LCD_EN= 1;
result=(bit)(Part & 0x80);
LCD_EN=0;
return result;
}
//=====================================
//LCD write command function
void lcd_write_cmd(uchar com)
{
while(lcd_busy());
LCD_RS=0;  //Select instruction register
LCD_RW=0;  //Write
LCD_EN=0;
Part=com;    //Assign instruction value to P0 port
delay(5);
LCD_EN=1;
delay(5);
LCD_EN=0;
}
//=====================================
//LCD write a character data function
void lcd_write_dat(uchar date)
{
while(lcd_busy());
LCD_RS=1;  //Select data register
LCD_RW=0;  //Write
LCD_EN=0;
P0=date;    //Assign data value to P0 port
delay(5);
LCD_EN=1;
delay(5);
LCD_EN=0;
}
//=====================================
//LCD write a string function
void lcd_write_string(uchar *str)
{
while(*str!='\0')  //Not ended
{
lcd_write_dat(*str++);
delay(5);
}
}
//=====================================
//LCD display position function
void lcd_pos(uchar x,uchar y)  //Start displaying from the Y position of the X row
{
uchar pos;
if(x==1)        //First row
{ x=0x80;}
else if(x==2)  //Second row
{ x=0x90;}
else if(x==3)  //Third row
{ x=0x88;}
else if(x==4)  //Fourth row
{ x=0x98;}
pos=x+y-1;     //Starting address is 0X80
lcd_write_cmd(pos);
}
//=====================================
//LCD initialization function
void lcd_init()
{
LCD_PSB=1;  //Parallel mode
LCD_RST=1;  //No reset
lcd_write_cmd(0x30);
delay(5);
lcd_write_cmd(0x0c);  //Turn on display, do not show cursor
delay(5);
lcd_write_cmd(0x06);  //After writing a character, the address pointer automatically increments
delay(5);
lcd_write_cmd(0x01);   //Clear screen
delay(5);
}
//=====================================
//Main function
void main()
{
// uchar i;
lcd_init();
while(1)
{
lcd_pos(1,1);
// lcd_write_string(dis1);
lcd_write_string("The bright moon before my bed");
delay(5);
lcd_pos(2,1);
// lcd_write_string(dis2);
lcd_write_string("I suspect it’s frost on the ground");
delay(5);
lcd_pos(3,1);
// lcd_write_string(dis3);
lcd_write_string("I raise my head to gaze at the bright moon");
delay(5);
lcd_pos(4,1);
// lcd_write_string(dis4);
lcd_write_string("I lower my head and think of my hometown");
delay(500);
}
}

Understanding the Principles and Code of the 12864 LCD Module

Understanding the Principles and Code of the 12864 LCD Module

Leave a Comment

×