Understanding the LCM1602C LCD Display, Part 2

Gary Schafer, 1 November 2014

In my first post, I covered the basics of programming the LCD display. That programming used all eight data lines. The great thing about the HD44780 standard is that it also provides for the ability to use only four data lines to program it. I'm going to cover this 4-bit programming in this post.

The specification explicitly states that 4-bit programming should use data lines D7 - D4. The data and instruction commands are still 8-bits long. This means that each data transmission or instruction requires two EN cycles, meaning two 4-bit transfers. The specification states that the high-order bits be sent first, and the low order bits second. There's also a little-tidbit that is not well explained in the specification. It's that, in order to set-up the LCD for 4-bit transfer, the first command needs to be the function set command, except that the first 4-bit transfer has to be repeated. Also, remember that the EN (enable) line has to be cycled HIGH, then LOW between each 4-bit transfer.

CommandRSD7D6D5D4
Function set (4-bit, 2-lines, 5x8 font), high-order bits.00010
Function set (4-bit, 2-lines, 5x8 font), these particular high-order bits have to be repeated this one time.00010
Function set (4-bit, 2-lines, 5x8 font), low-order bits.01000
Turn the display and cursor ON, and set the cursor to blinking, high-order bits.00000
Turn the display and cursor ON, and set the cursor to blinking, low-order bits.01100
Set the entry mode, with the cursor incrementing and the display not shifting, high-order bits.00000
Set the entry mode, with the cursor incrementing and the display not shifting, low-order bits.00110
Change the cursor position to the 2nd line, 4th position from the left, high-order bits.01100
Change the cursor position to the 2nd line, 4th position from the left, low-order bits.00011
Enter a character "H" into the display at the current cursor position, high-order bits.10100
Enter a character "H" into the display at the current cursor position, low-order bits.11000
Enter a character "e" into the display, high-order bits.10110
Enter a character "e" into the display, low-order bits.10101
Enter a character "l" into the display, high-order bits.10110
Enter a character "l" into the display, low-order bits.11100
Enter a character "l" into the display, high-order bits.10110
Enter a character "l" into the display, low-order bits.11100
Enter a character "o" into the display, high-order bits.10110
Enter a character "o" into the display, low-order bits.11111

This should result in the following image:

This is programming the LCD at its most basic, nothing more than connecting the various lines to either +5 V or ground, in a particular sequence. It's "assembly language for the LCD". (Okay. Not really. We're not moving bits around registers. But I hope you get the point.) Many Arduino-to-LCD projects use only four data lines (4-bit transfers), such as this one and this one. Regardless of how its programmed, whether with an Arduino or with a Raspberry Pi running through its GPIO ports, ultimately, the logic being sent to the LCD must be that as shown above. For example, if you're programming the Arduino to display the letter "H", then it's sending the same two 4-bit transfers as shown when you sent the letter "H" in the table above. It's just that you've now created an abstract layer in between you and the LCD. You told the program "Display the letter 'H'", the program figured out what logic needs to be sent to the LCD (set RS line HIGH, set data lines D7-D0 to 01001000, then flash the EN line one time), then sent it. It's that straightforward.

In Part 3, we'll cover creating special characters.

Understanding the LCM1602C LCD Display, Part 1

This is the front of the LCM1602C display. The white, triangular part on the right end is the location of the LED backlight.
This is the underside of the display. The long pins will plug into a breadboard.
This is the pin-out for the LCM1602C LCD display.
This is a very basic set-up that can be used to program the LCD.
This is the basic set-up, with the switches set to send the FUNCTION SET command. This specific command will tell the LCD that it's set for 8-bit data transfers, 2-lines of display, and a 5x8 point font.

Gary Schafer, 1 November 2014

This particular post will cover a bit of technology that most people simply know as "the LCD display". I'm not talking about the computer monitor type of LCD display; no, I'm talking about that small screen on many common pieces of electronics, the one that looks like this.

I'm going to talk about the LCM1602C LCD. The purpose of this post is to get away from a lot of the esoteric "how tos" of this particular display. Ya see, this display is based on the Hitachi HD44780 LCD controller. The nice thing about that is the specifications are readily available. The problem is that the specifications are not readily understood. Yes, I believe that this is an example of "lost in translation".

If you read many of the "how tos" for this display, you'd think you have to know how to program an Arduino, or how to program in C language, to program this particular display. I'm here to tell you that you can actually do it with nothing more than some wire and a power supply for the display. Mind you, it will be a lot of work to program it this way, but it's definitely doable. It will also provide an understanding of what the Arduino, or Raspberry Pi, or C language, must be doing in order to program the display.

Let's talk about the display first. This particular display is a 16 character by 2-line display. Its memory can hold up to 80 characters, 40 on each line of the display. The actual part that displays the characters can only show 16 characters across at any one time. Using the SHIFT command, you can move the part of the lines that are displayed.

There are 16 connections you'll use to power and program the LCD. These connections can be sorted, which I've done as follows:

Let's talk about wiring up some basics on this not-so-beastly beast. Start with the logic power, which is pins 1 (GND) and 2 (Vcc, which for this board is +5 V). Since this board, which according to its specification, is powered by +5 V, that makes it ideal to power using a USB line. I used an Arduino Uno, which connects to a USB line and provides a 5 V output to power external devices. I'd also bought a couple of small mini-B USB connector break-out boards from Sparkfun to provide power for various 5 V projects.

You can do all of the wiring and logic with nothing more than some wire and switches, as you can see in this Youtube video. One issue of such a set-up is that of using a manual, human-operated switch on the EN (enable) line. The problem is that such switches create a condition called "bounce", which causes inputs to repeat.

I used an Arduino to drive my LCD display simply so that I could drive the various logic lines. I didn't use any of the specialized Arduino libraries for driving a LCD; instead, I simply used the standard digitalWrite command to send the commands and data. The digitalWrite command merely sets the targetted output pin to either 0 V (GND, or LOW) or to +5 V (HIGH). This is equivalent to opening (LOW) or closing (HIGH) a switch. The difference is that using the Arduino means you don't have the "bounce" problem. The hard part is that you have to code each HIGH and LOW of each line.

To simplify the steps, I'm going to use a table in which each HIGH is replaced by a 1, and a LOW is replaced by a 0. After each step, the EN (enable) line on the system has to be set HIGH, then LOW. This tells the LCD to read in the data or instructions.

CommandRSD7D6D5D4D3D2D1D0
Function set (8-bit, 2-lines, 5x8 font)000111000
Turn the display and cursor ON, and set the cursor to blinking.000001111
Set the entry mode, with the cursor incrementing and the display not shifting.000000110
Change the cursor position to the 2nd line, 4th position from the left.011000011
Enter a character "H" into the display at the current cursor position.101001000
Enter a character "e" into the display.101100101
Enter a character "l" into the display.101101100
Enter a character "l" into the display.101101100
Enter a character "o" into the display.101101111

This should result in the following image:

If you happen to be using the normal LCD library for an Arduino, or programming the LCD using a C or C++ based system, then when you program it to, say, show the letter "H", or program it to have the cursor blink, then your programming has to be setting the various lines in a manner similar to what we just did above. Think of this as "assembly language for the LCD".

We'll continue this in Part 2.

Here's a Random Fact...