In this tutorial, I’ll explain how to set up an LCD display on an Arduino, and show you all the functions available to program it (with examples). The display I’m using here is a 16×2 LCD display that I bought for under $10 on Amazon. LCDs are really useful in projects that output data, and they can make your project a lot more interesting and interactive.

You may be wondering why they’re called 16×2 LCDs. The part 16×2 means that the LCD has 2 lines and can display 16 characters per line. Therefore, a 16×2 LCD screen can display up to 32 characters at once. It is possible to display more than 32 characters though, with code that scrolls the text left or right.

The code in this article is written for LCD’s that use the standard Hitachi HD44780 driver. If your LCD has 16 pins, then it probably has the Hitachi HD44780 driver. These displays can be wired in either 4 bit mode or 8 bit mode. Wiring the LCD in 4 bit mode is usually preferred since it uses four less wires than 8 bit mode. In practice, there isn’t a noticeable difference in performance between the two modes. In this tutorial, I’ll connect the LCD in 4 bit mode.

Wire the LCD to the Arduino Board

You may need to solder a 16 pin header to the LCD before using it with a breadboard. Follow the diagram below to wire the LCD to your Arduino:

Arduino LCD

The resistor in the diagram above sets the back light brightness. A typical value here is 220 Ohms, but other values will work too. Larger resistors will make the back light darker. The potentiometer is used to adjust the screen contrast. I typically use a 10K Ohm potentiometer, but other values will work also.

Here is the datasheet for a 16×2 LCD with all of the technical information about the display:

Circuit Basics PDF Icon 16×2 LCD Datasheet

Programming the Arduino

Now we’re ready to get into the programming! I’ll go over more interesting things you can do in a moment, but for now lets just run a simple test program. This program will print “hello, world!” to the screen. Enter this code into the Arduino IDE and upload it to the board:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  
}

Your LCD screen should look like this:

Arduino 16x2 LCD

The code above uses the LiquidCrystal library that comes pre-installed with the Arduino IDE. A library is a set of functions that can be easily added to a program in an abbreviated format. For example, instead of having to write a long section of code to map a character to a position on the LCD, we can simply use the function lcd.print() in the LiquidCrystal library.

In order to use a library, it must first be included in the program. Line 1 in the code above does this with the command #include <LiquidCrystal.h>. When we include the library in the program, all of the code contained in the library is uploaded to the board along with the code for the program.

LCD Display Options

There are 19 different functions in the LiquidCrystal library available for us to use. These functions do things like change the position of the text, move text across the screen, or make the display turn on or off. What follows is a short description of each function, and how to use it in a program.

LiquidCrystal()

The LiquidCrystal() function sets the Arduino pins that correspond to the pins of the LCD. You can change which pins the Arduino uses to connect to the LCD by placing the desired Arduino pin numbers inside the parentheses in this order: LiquidCrystal(RS, E, D4, D5, D6, D7). This function needs to be placed before the void setup() section of the program (see line 3 in the code above).

lcd.begin()

This function sets the dimensions of the screen, and must be placed before any other LiquidCrystal function in the void setup() section of the program. For a 16×2 LCD, you would use lcd.begin(16,2) as we did in line 6 of the code above, where the number of rows and columns of the screen is specified as lcd.begin(columns, rows).

lcd.clear()

This function clears whatever is printed on the LCD screen. If we use lcd.clear() after lcd.print() in the void loop() section, and a short delay command, we can setup a simple blinking text program:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  }

void loop() {
  lcd.print("hello, world!");
  delay(500);
  lcd.clear();
  delay(500);
}

lcd.home()

This function simply places the cursor in the upper left hand corner of the screen, and prints any subsequent text from that position. For example, this code replaces the first three letters of “hello world!” with X’s:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  lcd.home();
  lcd.print("XXX");
}

Arduino LCD Programming

lcd.setCursor()

Similar to, yet more useful than lcd.home(), is lcd.setCursor(). This function places the cursor (and any printed text) at any position on the screen, as defined by lcd.setCursor(column, row). This function can be used in the void setup() or void loop() section of your program. For example, using lcd.setCursor(2, 1) in the void setup() section of the “hello, world!” test program above will print “hello, world!” to the lower line and shift it to the right two spaces:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.setCursor(2, 1);
  lcd.print("hello, world!");
}

void loop() {
 
}

Remember that the column and row coordinates start from zero (0-15 and 0-1 respectively).

Arduino LCD Install

lcd.write()

You can use this function to write different types of data to the LCD, for example the reading from a temperature sensor, or the coordinates from a GPS module. You can also use it to print custom characters that you have designed yourself (here is a nice website that will give you the code for custom characters). Use lcd.write() in the void setup() or void loop() section of a program.

lcd.print()

As we saw in the first sketch, lcd.print() can be used to print text to the LCD. This function can be used in the void setup() section or the void loop() section of the program.

To print letters and words, place quotation marks (” “) around the text. For example, to print hello, world!, we use lcd.print(“hello, world!”).

To print numbers, no quotation marks are necessary. For example, to print 123456789, we would use lcd.print(123456789).

lcd.print() can print numbers in decimal, binary, hexadecimal, and octal bases. For example, lcd.print(100, DEC) (or just lcd.print(100)) prints “100”; lcd.print(100, BIN) prints “1100100”; lcd.print(100, HEX) prints “64”; and lcd.print(100, OCT) prints “144”.

lcd.Cursor()

This function creates a cursor. This cursor is a horizontal line underneath the position of the next character to be printed to the LCD. The function lcd.noCursor() turns the cursor off. lcd.cursor() and lcd.noCursor() can be used together in the void loop() section of a program to make the blinking cursor found in many text input fields:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  lcd.cursor();
  delay(500);
  lcd.noCursor();
  delay(500);
}

This places a blinking cursor after the exclamation point in “hello, world!”

A blinking cursor can be placed anywhere on the screen with the function lcd.setCursor(). This code places a blinking cursor directly below the exclamation point in “hello, world!”:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  lcd.setCursor(12, 1);
  lcd.cursor();
  delay(500);
  lcd.setCursor(12, 1);
  lcd.noCursor();
  delay(500);
}

lcd.blink()

This function creates a block style cursor that blinks on and off at approximately 500 milliseconds per cycle. Use it in the void loop() section. The function lcd.noBlink() disables the blinking block cursor. The position of the blinking cursor can be changed by using it with the lcd.setCursor() command.

lcd.display()

This function turns on any text or cursors that have been printed to the LCD screen. The function lcd.noDisplay() turns off any text or cursors printed to the LCD, without clearing it from the LCD’s memory. These two functions can be used together in the void loop() section to create a blinking text effect. This code will blink the “hello, world!” text on and off:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  lcd.display();
  delay(500);
  lcd.noDisplay();
  delay(500);
}

lcd.scrollDisplayLeft()

This function takes anything printed to the LCD and moves it to the left. It should be used in the void loop() section with a delay command following it. The function will move the text 40 spaces to the left before it loops back to the first character. This code moves the “hello, world!” text to the left, at a rate of one second per character:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.print("hello, world!");
}

void loop() {
  lcd.scrollDisplayLeft();
  delay(1000);
}

Text strings longer than 40 spaces will be printed to line 1 after the 40th position, while the start of the string will continue printing to line 0.

lcd.scrollDisplayRight()

This function behaves similarly to lcd.scrollDisplayLeft(), but moves the text to the right.

lcd.autoscroll()

This function will take a string of text and scroll it from right to left in increments of the character count of the string. For instance, if you have a string of text that is 3 characters long, it will scroll the text three spaces to the left each loop cycle:

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
}

void loop() {
  lcd.setCursor(0, 0);
  lcd.autoscroll();
  lcd.print("ABC");
  delay(500);
}

Just like in the lcd.scrollDisplay() functions, the strings can be up to 40 characters in length before repeating. At first glance, this function seems less useful than the lcd.scrollDisplay() functions at scrolling text, however it could be very useful when creating animations with custom characters.

lcd.noAutoscroll()

lcd.noAutoscroll() turns the lcd.autoscroll() function off. Use this function when lcd.autoscroll() is used in the void loop() section to create custom sequences of scrolling text or animations.

lcd.rightToLeft()

This function sets the direction that text is output to the screen, not the direction it is scrolled across the screen. The default mode of text output is from left to right using the command lcd.leftToRight(), but you may find some instances where it is useful to output text in the reverse direction, from right to left (i.e. special character animations):

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

void setup() {
  lcd.begin(16, 2);
  lcd.setCursor(12, 0);
  lcd.rightToLeft();
  lcd.print("hello, world!");
}

void loop() {
  
}
 

This code prints our “hello, world!” text as “!dlrow ,olleh”. Unless you specify the placement of the cursor with lcd.setCursor(), the text will print from the (0, 1) position and only the first character of the string will be visible.

Arduino LCD LiquidCrystal

lcd.createChar()

This command allows you to create your own custom characters. Each character of a 16×2 LCD has a 5 pixel width and an 8 pixel height. Up to 8 different custom characters can be defined in a single program. To design your own characters, you will need to get the binary matrix of your custom character from an LCD character generator or map it yourself. This code creates a degree symbol (°):

#include <LiquidCrystal.h>

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
byte customChar[8] = {
	0b00110,
	0b01001,
	0b01001,
	0b00110,
	0b00000,
	0b00000,
	0b00000,
	0b00000
};

void setup()
{
  lcd.createChar(0, customChar);
  lcd.begin(16, 2);
  lcd.write((uint8_t)0);
 }

void loop() {
}

Arduino LCD Programming degree symbol

Take it to the next level by trying different combinations of the functions and see what happens. There are a lot of cool things you can make happen with these 16×2 LCDs!

Here’s a video version of this tutorial so you can see what each function does on the LCD in real time:

If you found this article useful, subscribe via email to get notified when we publish of new posts! And as always, if you are having trouble with anything posted here, just leave a comment and I will try to help you solve it.


Need an easy-to-use way to design circuits and layout PCBs?

Try EasyEDA, a free circuit design software that also offers low cost, high quality PCB manufacturing.