[Elixir Nerves] Character LCD with serial interface (I2C)
7 min read
As a Nerves IoT framework hobbyist, I enjoy learning the very basics of the electronics through writing Elixir programs that run on my Raspberry Pis. Today I will talk about the HD44780 Character LCD display with the serial interface. There are multiple ways to use the serial interface between an LCD and a Raspberry Pi, but here I will use a typical inexpensive I2C piggyback board as an example.
Here are the items I prepared:
- Raspberry Pi Zero W
- This can be any target device that the Nerves project supports.
- Micro SD card
- We will burn our firmware on a micro SD card.
- 16x2 LCD display with I2C serial interface
- Typically this is less than US$10 and it is pre-assembled.
- Many inexpensive I2C boards use 8-Bit I/O Expander PCF8574 but please check what I/O expander yours uses.
- Handson Technology I2C Serial Interface 1602 LCD Module User Guide summarizes the typical specifications of the PCF8574-based I2C module.
- Four female-to-female jumber wires
- Nerves - IoT platform built with Elixir
- elixir-circuits/circuits_i2c - Communicate over I2C from Elixir
- mnishiguchi/lcd_display - Use character liquid crystal display (LCD) in Elixir
Wiring and connections
|I2C module||Raspberry Pi|
Demo Nerves project
Clone the demo project
$ git clone firstname.lastname@example.org:mnishiguchi/lcd_display.git $ cd lcd_display/examples/nerves_hello_lcd
Set necessary environment variables. The demo project assumes you will use WIFI so two WIFI related values (ssid and psk) are required to be set. The
MIX_TARGET environment variable can be any target tag that Nerves supports.
$ export WIFI_SSID=_____ # your WIFI id $ export WIFI_PSK=______ # your WIFI password $ export MIX_TARGET=rpi0 # your target board
$ mix deps.get
$ mix firmware
Insert the SD card into your host machine (e.g. laptop) and run the following command to burn the firmware to that SD card.
$ mix firmware.burn
Insert that SD card into your target board (e.g. Raspberry Pi) and power it on.
Connect to your target board
Check the connection.
$ ping nerves.local
SSH into your target board, then interactive Elixir shell will start.
$ ssh nerves.local Interactive Elixir (1.11.2) - press Ctrl+C to exit (type h() ENTER for help) Toolshed imported. Run h(Toolshed) for more info. RingLogger is collecting log messages from Elixir and Linux. To see the messages, either attach the current IEx session to the logger: RingLogger.attach or print the next messages in the log: RingLogger.next iex(1)>
RingLogger.attach then log messages will be outputted.
Follow the instructions in mnishiguchi/lcd_display README to show "Hello" text.
For the other supported commands, please refer to
Here is the command I use for testing the LCD. It runs various commands one after another.
Some mistakes I made
I thought all I2C boards were the same
Different products out there may use a differnt I/O expander internally.
At first, I was under the impression that all the I2C boards would do exactly the same thing. That is not true at all. There is no gurantee the same program works for all the serial interface boards.
Embarrasingly, I posted to the Adafruit Forum saying the products I purchased might be defective, blindly using my old code for other I2C module.
So the lesson I learned is even if two products look similar, it is a good idea to still check what I/O expander is mounted on a board and check the pin assignment between the I/O expander and the LCD display.
I underestimated the desoldering
I totally underestimated the difficulty level of desoldering. I messed up two LCDs. First of all, desoldering itself is difficult to me at least. Secondly, a solder sucker can peel the printed metal sheet. I do not know the name of it, but I mean by the metal bits on which we solder to connect the header pins.
The lesson I learned is to avoid desoldering whenever possible.
I connected only the Red LED pin for the backlight
Many I2C boards only support one pin for the backlight, using pins 1 to 16.
For the 16-pin standard LCDs, there is no issue, but for the 18-pin RGB LCDs, the pin #16 is for the Red LED. So the backlight can always be red if only that pin is connected not the Green and the Blue pins. I should have use a standard LCD, not the RGB one.
The lesson I learned is to make plans before using the RGB LCD.
Other serial interfaces
They say SparkFun Qwiic Connect System makes the I2C connection easy.
The USB port can be used for connecting a LCD.
Here are my study notes on HD44780 LCD, I/O expanders, I2C interface etc in case they may be helpful for somebody.