LCD16x2 Interfacing in 8-bit with 8051

LCD 16x2 

LCDs (Liquid Crystal Displays) are used for displaying status or parameters in embedded systems.

LCD 16x2 is 16 pin device that has 8 data pins (D0-D7) and 3 control pins (RS, RW, EN). The remaining 5 pins are for the supply and the backlight for the LCD.

The control pins help us configure the LCD in command mode or data mode. They also help configure read mode or write mode and also when to read or write.

LCD 16x2 can be used in 4-bit mode or 8-bit mode depending on the requirement of the application. In order to use it we need to send certain commands to the LCD in command mode and once the LCD is configured according to our needs, we can send the required data in data mode.

For more information about LCD 16x2 and how to use it, refer to the topic LCD 16x2 display module in the sensors and modules section.

 

LCD 16x2 Pinout                       

Pin Diagram of LCD16x2 with Pin Names
LCD 16x2 Pin Diagram

 

LCD16x2 with 8051 Interfacing Diagram

8051 LCD16x2 Connection Diagram
LCD 16x2 Interface with 8051

 

LCD16x2 with 8051 Pin Connection

LCD 162 Pins89c51 Pins
Data Pins    D0-D7PORT1
RSPORT2.0
RWPORT2.1
EPORT2.2

 

Programming LCD16x2

Initialize LCD16x2 

It is very easy to initialize LCD

  1. Power ON LCD
  2. Wait for 15ms, Power-on initialization time for LCD16x2
  3. Send 0x38 command (initialize. 2 line, 5x8 matrix, 8-bit mode)
  4. Send any Display ON command (0x0E, 0x0C)
  5. Send 0x06 command (increment cursor)
void LCD_Init (void)		/* LCD Initialize function */
{
	delay(20);		/* LCD Power ON Initialization time >15ms */
	LCD_Command (0x38);	/* Initialization of 16X2 LCD in 8bit mode */
	LCD_Command (0x0C);	/* Display ON Cursor OFF */
	LCD_Command (0x06);	/* Auto Increment cursor */
	LCD_Command (0x01);	/* Clear display */
	LCD_Command (0x80);	/* Cursor at home position */
}

Now we successfully initialized LCD & it is ready to accept data to display.

 

LCD16x2 Command write function

  1. Send command to the data port
  2. Make RS pin low, RS=0 (command reg.)
  3. Make RW pin low, RW=0 (write operation)
  4. Give High to Low pulse at Enable (E) minimum of 450ns.

When we give Enable pulse, LCD latch the data present at D0 to D7 & execute a command as RS is command reg.

void LCD_Command (unsigned char cmd)	/* LCD16x2 command funtion */
{
	lcd_data_port= cmd;
	rs=0;				/* command reg. */
	rw=0;				/* Write operation */
	en=1; 
	delay(1);
	en=0;
	delay(5);
}

 

LCD16x2 Data write function

  1. Send command to the data port
  2. Make RS pin low, RS=1 (data reg.)
  3. Make RW pin low, RW=0 (write operation)
  4. Give High to Low pulse at Enable (E) minimum of 450 ns

When we give Enable pulse, LCD latch the data present at D0 to D7 & display it on the 5x8 matrix as RS is data reg.

void LCD_Char (unsigned char char_data)	/* LCD data write function */
{
	lcd_data_port=char_data;
	rs=1;				/*Data reg.*/
	rw=0;				/* Write operation*/
	en=1;   				
	delay(1);
	en=0;
	delay(5);
}

 

Note

  1. LCD Power on delay: after power on, we can’t send commands immediately, LCD16x2 needs a self-initialization time of 15ms. While programming we need to take care of providing sufficient power on delay> 15ms, and then send a command to LCD.
  2. After providing commands to execute, LCD16x2 takes time in microseconds but for 0x01 command (Clear display), it takes 1.64ms to execute. So after giving this command, we need to give sufficient delay> 1.63milliseconds.

 

LCD16x2 8051 Code 

/*  
   LCD16x2 8 bit 8051 interface
   http://www.electronicwings.com
*/


#include<reg51.h>

sfr lcd_data_port=0x90;		/* P1 port as data port */
sbit rs=P2^0;			/* Register select pin */
sbit rw=P2^1;			/* Read/Write pin */
sbit en=P2^2;			/* Enable pin */


void delay(unsigned int count)  /* Function to provide delay Approx 1ms */
{
	int i,j;
	for(i=0;i<count;i++)
	for(j=0;j<112;j++);
}

void LCD_Command (unsigned char cmd)  /* LCD16x2 command funtion */
{
	lcd_data_port= cmd;
	rs=0;			/* command reg. */
	rw=0;			/* Write operation */
	en=1; 
	delay(1);
	en=0;
	delay(5);
}

void LCD_Char (unsigned char char_data)  /* LCD data write function */
{
	lcd_data_port=char_data;
	rs=1;			/* Data reg.*/
	rw=0;			/* Write operation*/
	en=1;   				
	delay(1);
	en=0;
	delay(5);
}

void LCD_String (unsigned char *str) /* Send string to LCD function */
{
	int i;
	for(i=0;str[i]!=0;i++)  /* Send each char of string till the NULL */
	{
		LCD_Char (str[i]);  /* Call LCD data write */
	}
}

void LCD_String_xy (char row, char pos, char *str)  /* Send string to LCD function */
{
	if (row == 0)
	LCD_Command((pos & 0x0F)|0x80);
	else if (row == 1)
	LCD_Command((pos & 0x0F)|0xC0);
	LCD_String(str);	/* Call LCD string function */
}

void LCD_Init (void)		/* LCD Initialize function */
{	
	delay(20);		/* LCD Power ON Initialization time >15ms */
	LCD_Command (0x38);	/* Initialization of 16X2 LCD in 8bit mode */
	LCD_Command (0x0C);	/* Display ON Cursor OFF */
	LCD_Command (0x06);	/* Auto Increment cursor */
	LCD_Command (0x01);	/* clear display */
	LCD_Command (0x80);	/* cursor at home position */
}

void main()
{

	LCD_Init();		/* initialization of LCD*/

	LCD_String("ElectronicWINGS");  /* write string on 1st line of LCD*/
	LCD_Command(0xC0);
	LCD_String("Hello World");  /*write string on 2nd line*/

	while(1);		/* Infinite loop. */
	
}
 

 

LCD 16x2 Code Output

Photo of LCD16x2 string output using 8051
LCD16x2 string output

 

LCD16x2 Rolling Display

To roll the string or character on the LCD, we need to use the following commands

Commandmeaning
0x1cShift entire display right
0x18Shift entire display left

 

For rolling the display, simply we have to put these commands in loops.

Rolling Display:

  • Display string on the LCD
  • Roll it to the right using the ‘0x1C’ command
  • Roll it to the left using the ‘0x18’ command

 

Main function code for LCD16x2 Scrolling Display

void main()
{
  unsigned char i,shift;
	delay(5);
	LCD_Init();			/* initilize LCD */

	LCD_String("ElectronicWings");  /* display string */
	delay(1000);

	shift=15;			/* number of time shifts count=15 */
	
while(1)
{
	for(i=0;i<shift;i++)				
  {
		LCD_Command(0x1c);  	/* shift display right */
		delay(300);
  }
	
	shift=30;			/* number of time shifts 30 */
	
  for(i=0;i<30;i++)
  {
		LCD_Command(0x18);  	/* shift display left */
		delay(300);
  }
 }	
}

 

Video of LCD16x2 Scrolling Display using 8051


Components Used

LCD16x2 Display
LCD16x2 Display
1
8051 AT89c51
8051 AT89c51
1

Downloads

LCD Datasheet Download
8051_LCD_8bit_Interface_Simulation Download
8051_LCD16x2_8bit_Interface_Project Download
8051_LCD16x2_Rolling_Display_Project Download
Ad