ESP32 UNO - Keypad - LCD
Press a button and see it on a screen: that is the whole idea of this ESP32 Uno keypad LCD build. A 3x4 membrane keypad gives the input, and a 16x2 LCD I2C display shows every digit, star or hash you type. The ESP32 Uno form board fills the top line from left to right, then wipes it and starts over. It is the first block of a PIN lock, a number entry box or a simple menu.
What you will do:
- Connect a 3x4 keypad and an I2C LCD display to the ESP32 Uno
- Add the DIYables_Keypad and DIYables_LCD_I2C libraries in Arduino IDE
- Catch each key press with getKey()
- Print the keys on the LCD and reset the line after 16 characters

Components You Need
Or you can buy the following kits:
| 1 | × | DIYables Sensor Kit (18 sensors/displays) |
Additionally, some of these links are for products from our own brand, DIYables .
Buy Note: Most LCD I2C displays available on the market are 5V displays. They may work with this board, but it is unsafe and can damage the board. We strongly recommend using the 3.3V LCD I2C display recommended above.
Keypad and LCD at a Glance
After this part, you know what each module does and how many pins it takes.
| Module | Role | Signal Pins Used | Supply |
|---|---|---|---|
| Keypad 3x4 (12 keys) | Input, sends which key is down | 7 (4 rows + 3 columns) | None, it is only switches |
| LCD I2C 16x2 | Output, shows 2 lines of 16 characters | 2 (SDA and SCL) | 5V |
The keypad is a grid of switches. A key joins one row line to one column line, and the library scans the grid many times per second to find it. The LCD sits on the I2C bus, so the two modules never fight over a pin.
Want the full pinout or a basic test sketch for each part? Read these guides:
ESP32 Uno Pinout
Your sketch talks to GPIO numbers, while the board shows Uno labels like D3 or D9. Match D3 to D9 and the SDA/SCL pins with their GPIO numbers in the picture before you wire anything.

How to Connect
When this step is done, the keypad sits on D3 to D9 and the screen sits on the I2C header.

This image is created using Fritzing. Click to enlarge image
※ NOTE THAT:
The wiring diagram may not show the correct wiring for the ESP32 Uno. The LCD backpack pulls SDA and SCL up to 5V, but ESP32 Uno pins are 3.3V only. The picture shows the LCD wired straight to SDA and SCL. We suggest a level converter between the LCD and the board, as the hardware list shows. We will update the diagram soon. Until then, follow the wiring table and the text on this page, not the picture.
Step 1 — Keypad 3x4
| Keypad Pin | ESP32 Uno Pin |
|---|---|
| R1 (Row 1) | D9 (GPIO13) |
| R2 (Row 2) | D8 (GPIO12) |
| R3 (Row 3) | D7 (GPIO14) |
| R4 (Row 4) | D6 (GPIO27) |
| C1 (Column 1) | D5 (GPIO16) |
| C2 (Column 2) | D4 (GPIO17) |
| C3 (Column 3) | D3 (GPIO25) |
WARNING
Row 2 lands on D8 (GPIO12), a boot strapping pin. The ESP32 Uno reads it at start-up to choose the flash voltage, and it must be LOW then. If a key in the 4-5-6 row is held while the board powers up, resets or starts an upload, the pin can be pulled the wrong way and the board may not start. Keep your hands off the keypad during reset and upload.
Step 2 — LCD I2C display
| LCD Pin | ESP32 Uno Pin |
|---|---|
| VCC | 5V |
| GND | GND |
| SDA | SDA (GPIO21) |
| SCL | SCL (GPIO22) |
Good to know: A4 and A5 on this board are input-only analog pins, not I2C. Plug the LCD into the separate SDA and SCL header pins.
WARNING
Every ESP32 Uno pin uses 3.3V logic, and none of them are 5V tolerant. The LCD backpack needs 5V, and many backpacks pull SDA and SCL up to that 5V. To keep the board safe for a long time, add a bidirectional 3.3V/5V level converter on SDA and SCL, or remove the pull-up resistors from the backpack.
ESP32 Uno Code
This sketch watches the keypad and writes each new key on line 1 of the LCD, one place to the right each time.
※ NOTE THAT:
LCD I2C boards from other makers may use another address. The code uses 0x27, the address of the DIYables LCD. If the backlight is on but no text appears, try 0x3F or scan the bus.
Upload and Test
- First time with this board? Set it up with ESP32 Uno - Getting Started before you continue.
- Build the circuit by following the wiring table above.
- Plug in the USB Type-C cable between the ESP32 Uno and your computer.
- Select the board in Arduino IDE: pick ESP32 Dev Module and the COM port of the board (CH340).
- Open the Library Manager with the Libraries icon in the left bar.
- Get the keypad library: type DIYables_Keypad, find the one by DIYables.io and press Install.
- Search for DIYables_Keypad created by DIYables.io and click the Install button.
- Get the screen library: type "DIYables LCD I2C", find DIYables_LCD_I2C by DIYables and press Install.
- Search for DIYables LCD I2C created by DIYables.io and click the Install button.
- Paste the sketch into a new Arduino IDE window.
- Click Upload and wait for "Done uploading". Do not touch the keypad while it uploads.

- Type a few keys, for example 7, 3, *, 0 and #.
- Watch the LCD: the top line shows each key in order.
| Keys Pressed | LCD Line 1 |
|---|---|
| 7 3 * 0 # | 73*0# |
| 16 keys in total | 2580#147*369#025 (full line) |
| One more key, 4 | 4 (screen cleared first) |
- Pro tip: press the same key fast five times. If you get more than five characters, a wire is loose and the contact bounces; press the jumpers in firmly.
Screen stays blank? Open the LCD I2C troubleshooting part.
Video Tutorial
See the ESP32 Uno build in action in the video below.
Code Explanation
By the end of this part, you can change the keys, pins or screen size yourself.
| Code Part | What It Does |
|---|---|
| keys[4][3] array | Gives each button its character, row by row |
| pin_rows and pin_column | List the GPIOs of the keypad, rows 13, 12, 14, 27 and columns 16, 17, 25 |
| DIYables_LCD_I2C lcd(0x27, 16, 2) | Makes the screen object with address 0x27 and size 16x2 |
| keypad.getKey() | Returns the pressed key, or 0 when no key is down |
| cursorColumn | Remembers the next free place on line 1 and resets to 0 after 16 |
The result: every press costs one place on the screen, and a full line clears by itself.
ESP32 Uno vs UNO R4 for This Project
This part shows what changes when you move this keypad LCD build from the UNO R4 to the ESP32 Uno.
| Item | Arduino UNO R4 | ESP32 Uno |
|---|---|---|
| Logic voltage | 5V | 3.3V |
| Keypad rows in code | 9, 8, 7, 6 | 13, 12, 14, 27 |
| Keypad columns in code | 5, 4, 3 | 16, 17, 25 |
| LCD I2C pins | SDA and SCL header | SDA (GPIO21) and SCL (GPIO22) header |
| Libraries | DIYables_Keypad, DIYables_LCD_I2C | Same, no change |
| Arduino IDE board | Arduino UNO R4 WiFi | ESP32 Dev Module |
The wires go to the same header holes, so the circuit works as-is. Watch two things: no key press on row 2 during boot, and the 5V pull-ups on the LCD backpack.
Go Wireless: Type on Your Phone, Show on the LCD
After this part, you have an idea to extend the build with WiFi or Bluetooth.
The ESP32 Uno has WiFi and Bluetooth (Classic and BLE) on board. Keep the keypad for local input, and add a phone chat box that sends text straight to the LCD. You can also send every keypad press to a web monitor, so you see the typed code on your phone too.
Try These Next
- Use the second LCD line, so you can type 32 characters before the screen clears.
- Make the # key work as "Enter" and the * key as "Delete".
- Show a star on the LCD instead of the real digit, like a PIN screen.
Troubleshooting
| Problem | Possible Cause | Solution |
|---|---|---|
| No COM port shows up in Arduino IDE | CH340 driver missing or the cable only charges | Install the CH340 driver and use a USB data cable |
| Upload stops at "Failed to connect" or "Waiting for download" | Board did not enter download mode | Hold the BOOT button when the upload starts, release it when writing begins |
| Board does not boot or upload with the keypad plugged in | A key on row 2 pulls D8 (GPIO12), a boot strapping pin, the wrong way | Keep your hands off the keypad at reset, or unplug the row 2 wire while you upload |
| Backlight on but the screen shows no text | Low contrast or a different I2C address | Turn the blue contrast screw on the back and try address 0x3F |
| LCD is fully dark | No 5V on VCC or a loose GND wire | Check that VCC goes to 5V and GND to GND, and reseat the jumpers |
| LCD worked on another Uno board but not here | SDA and SCL plugged into A4 and A5 | Move the two wires to the SDA (GPIO21) and SCL (GPIO22) header pins |
| Pressed key shows a different character | A row wire and a column wire are swapped | Check every keypad wire against the table, R1 on D9 and C1 on D5 |
| A whole row or column of keys is dead | That keypad wire is loose or broken | Replace the jumper for that row or column |
| Compile error "No such file or directory" | A library is not installed | Install DIYables_Keypad and DIYables_LCD_I2C from the Library Manager |
FAQ
Do I need resistors between the keypad and the ESP32 Uno?
No. The keypad library turns on the internal pull-up resistors of the column pins. D3 to D9 all have internal pull-ups on this board, so the keypad connects with plain jumper wires.
Can the LCD I2C run from the 3.3V pin?
Most 16x2 LCD I2C modules are built for 5V. At 3.3V the text is very pale or not there at all. Use 5V for the LCD and protect SDA and SCL with a level converter, or buy a 3.3V LCD module.
Which I2C address does my LCD have?
DIYables LCDs use 0x27. Other boards often use 0x3F. Load an I2C scanner sketch, open the Serial Monitor and it prints the address it finds.
Why are the numbers in the code 13, 12, 14 and 27 instead of 9, 8, 7 and 6?
In ESP32 Uno sketches you type the GPIO number, never the printed header label. D9 is GPIO13, D8 is GPIO12, D7 is GPIO14 and D6 is GPIO27. The wires still go to the same header holes as on other Uno boards.
Is D8 safe to use for a keypad row on the ESP32 Uno?
It works, but D8 is GPIO12, a boot strapping pin that must be LOW at start-up. A pressed key on that row during reset can stop the board from booting. Release all keys before you reset or upload, and the sketch runs normally.
Can I connect a 4x4 keypad instead of the 3x4 one?
Yes. Change COLUMN_NUM to 4, add the A, B, C and D keys to the keys array and add one more GPIO to pin_column. Pick a free pin with an internal pull-up, so not A2 to A5, because those are input only with no pull-up.
Can I plug a UNO LCD keypad shield into the ESP32 Uno?
The shield fits the headers, but most of them read their buttons on A0 with 5V logic. The ESP32 Uno ADC reads 0 to 4095 at 3.3V, so the button values change and the code needs new thresholds. Check the shield voltage before you plug it in.
How do I fix "COM port not found" for this board?
The ESP32 Uno uses a CH340 USB-to-serial chip. Install the CH340 driver, reconnect the board and pick the new COM port. A charge-only USB cable also hides the port, so try a data cable.
What if my project needs more pins than the Uno headers give?
The ESP32 Uno has a few extra holes near the power header: GPIO32 and GPIO33 (I/O, PWM, analog on ADC1, so they work with WiFi on) and GPIO15 (I/O, PWM, analog on ADC2). Solder pin headers and use the GPIO number in code. For a fourth keypad column or a buzzer, GPIO32 or GPIO33 is the best pick. Two warnings: GPIO15 and GPIO0 (the IO0 pin at the unused Uno NC position) are boot strapping pins, and a wrong connection can stop the board from booting or uploading, so use GPIO32/33 first. Never use the six holes under the digital header (SD0 to SD3, CMD, CLK = GPIO6 to GPIO11), because they go to the flash chip and using them crashes the board.
Can I check a password typed on the keypad and show "OK" on the LCD?
Yes. Collect the keys in a String, compare it with your password when # is pressed, then use lcd.print() to show "OK" or "Wrong". Add a relay or a servo later to make a real door lock.