ESP32 S3 UNO - OLED 128x32

This ESP32 S3 Uno OLED 128x32 tutorial shows you how to connect a small SSD1306 I2C display to the ESP32 S3 Uno form board and control it with Arduino code. You will print text and numbers, draw shapes, and show a bitmap image on the 128x32 OLED screen.

In this tutorial, you will:

  1. Wire an SSD1306 128x32 OLED display to the I2C pins of the board
  2. Install the Adafruit SSD1306 and GFX libraries in Arduino IDE
  3. Show text and numbers on the ESP32 S3 Uno OLED 128x32 screen
  4. Draw rectangles, circles and triangles, and display a bitmap image
  5. Center text and numbers both horizontally and vertically
ESP32 S3 Uno OLED 128x32

Hardware Preparation

1×ESP32 S3 Uno-form Board
1×USB Cable Type-A to Type-C (for USB-A PC)
1×USB Cable Type-C to Type-C (for USB-C PC)
1×SSD1306 I2C OLED Display 128x32
1×Jumper Wires

Or you can buy the following kits:

1×DIYables Sensor Kit (18 sensors/displays)
Disclosure: Some of the links provided in this section are Amazon affiliate links. We may receive a commission for any purchases made through these links at no additional cost to you.
Additionally, some of these links are for products from our own brand, DIYables .

Overview of OLED Display

A 128x32 OLED is a tiny screen with 128 columns and 32 rows of pixels. Each pixel makes its own light, so the display needs no backlight and stays sharp even in a dark room. The module talks over I2C, which means you only need two signal wires.

I2C OLED Display Pinout

The module has four pins. Two are for power and two are for the I2C bus.

Pin Description
GND Ground. Connect it to GND on the ESP32 S3 Uno
VCC Power supply for the display. Connect it to 3.3V on the ESP32 S3 Uno
SCL I2C clock line
SDA I2C data line
OLED Pinout

※ NOTE THAT:

The pin order on an OLED module can change from one maker or model to another. Always read the labels printed on your module before you wire it.

This guide is for OLED displays with the SSD1306 I2C driver. We tested it with an OLED display from DIYables, and it worked with no problems.

ESP32 S3 Uno Pinout

The image below shows the pinout of the ESP32 S3 Uno form board. Use it to find the SDA and SCL header pins and their GPIO numbers before you wire the OLED.

ESP32 S3 Uno pinout diagram

Wiring Diagram

The OLED needs only four wires: power, ground, and the two I2C lines. Connect SDA and SCL to the SDA and SCL header pins of the board.

The wiring diagram between ESP32 S3 Uno OLED 128x32

This image is created using Fritzing. Click to enlarge image

Component Pin ESP32 S3 Uno Pin
VCC 3.3V
GND GND
SDA SDA (GPIO8)
SCL SCL (GPIO9)

※ NOTE THAT:

On the ESP32 S3 Uno, A4 and A5 are NOT I2C pins. Always connect the OLED to the SDA (GPIO8) and SCL (GPIO9) header pins. Wire.begin() uses these two pins by default, so the code needs no pin setting.

WARNING

The ESP32 S3 Uno pins work at 3.3V and are NOT 5V tolerant. Power the OLED from 3.3V. If you power the module from 5V, its I2C pull-up resistors may pull SDA and SCL up to 5V, which can harm the board.

How To Use OLED with ESP32 S3 Uno

Before you can draw anything, Arduino IDE needs the right libraries, and your sketch needs a few setup lines. This part shows both.

Install SSD1306 OLED library

  1. Click the Libraries icon on the left side of Arduino IDE.
  2. Type "SSD1306" in the search box and find the SSD1306 library by Adafruit.
  3. Click the Install button.
  • Search for Adafruit SSD1306 created by Adafruit and click the Install button.
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32S3 Dev Module
Library Manager
Type:
All
Topic:
All
Adafruit SSD1306 by Adafruit
SSD1306 oled driver library for monochrome 128x64 and 128x32 displays More info
2.5.9
INSTALL
Newbiely.ino
···
1 void setup() {
Output
Serial Monitor
Ln 1, Col 1
ESP32S3 Dev Module on COM15
1
  1. Arduino IDE asks to install some other libraries that SSD1306 depends on. Click the Install All button to add them all.

How to program for OLED

Every OLED sketch starts the same way. You include the libraries, set the screen size, create the display object, and start it in setup().

Include the libraries

#include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h>

Set the screen size to 128x32

#define SCREEN_WIDTH 128 // Defines the width of the OLED display in pixels #define SCREEN_HEIGHT 32 // Defines the height of the OLED display in pixels

Create the SSD1306 OLED object

// Initialize an Adafruit SSD1306 display object for I2C communication Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1);

Start the OLED in setup()

// Start OLED display with specific I2C address (0x3C) for 128x32 resolution if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); // Print error message if initialization fails while (true); // Enter an infinite loop to halt further execution }

After this, you are free to show text, draw shapes and display pictures.

ESP32 S3 Uno Code - Display Text on OLED

This first sketch is the simplest test. It starts the display, waits two seconds, and prints "Hello World!" in small white text.

/* * This ESP32 S3 Uno code was developed by newbiely.com * * This ESP32 S3 Uno code is made available for public use without any restriction * * For comprehensive instructions and wiring diagrams, please visit: * https://newbiely.com/tutorials/esp32-s3-uno/esp32-s3-uno-oled-128x32 */ #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #define SCREEN_WIDTH 128 // OLED display width, in pixels #define SCREEN_HEIGHT 32 // OLED display height, in pixels // declare an SSD1306 display object connected to I2C Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); void setup() { Serial.begin(9600); // initialize OLED display with address 0x3C for 128x32 if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); while (true); } delay(2000); // wait for initializing oled.clearDisplay(); // clear display oled.setTextSize(1); // text size oled.setTextColor(WHITE); // text color oled.setCursor(0, 10); // position to display oled.println("Hello World!"); // text to display oled.display(); // show on OLED } void loop() { }

Detailed Instructions

  1. New to the ESP32 S3 Uno? Follow ESP32 S3 Uno - Getting Started first.
  2. Wire it up as shown in the diagram.
  3. Connect the board to your computer with a USB Type-C cable.
  4. Open Arduino IDE, choose the ESP32S3 Dev Module board and the correct COM port.
  5. Install the libraries Adafruit SSD1306 and Adafruit GFX as shown above.
  6. Copy the code and paste it into Arduino IDE.
  7. Upload the code by clicking the Upload button.
  8. Check the screen. "Hello World!" should appear on the OLED after about two seconds.
  9. Tip: If the screen stays black, open the Serial Monitor at 9600 baud. The message "SSD1306 allocation failed" means the board cannot find the OLED on the I2C bus.

Useful text functions

The Adafruit library gives you many functions for text. These are the ones you will use most:

Function What it does
oled.clearDisplay() Turns off all pixels
oled.drawPixel(x, y, color) Draws one pixel at x, y
oled.setTextSize(n) Sets the text size, from 1 to 8
oled.setCursor(x, y) Sets where the text starts
oled.setTextColor(WHITE) Makes the text white
oled.setTextColor(BLACK, WHITE) Makes black text on a white background
oled.println("message") Prints text
oled.println(number) Prints a number
oled.println(number, HEX) Prints a number in hexadecimal
oled.display() Sends all changes to the screen
oled.startscrollright(start, stop) Scrolls text from left to right
oled.startscrollleft(start, stop) Scrolls text from right to left
oled.startscrolldiagright(start, stop) Scrolls text diagonally from bottom left to top right
oled.startscrolldiagleft(start, stop) Scrolls text diagonally from bottom right to top left
oled.stopscroll() Stops any scrolling

Remember that drawing functions only change a memory buffer. Nothing shows on the screen until you call oled.display().

ESP32 S3 Uno Code - Drawing on OLED

Shapes are a good way to build simple icons, bars and frames. This sketch draws a rectangle, a rounded rectangle, a circle and a triangle, first as an outline and then filled, and changes shape every two seconds.

/* * This ESP32 S3 Uno code was developed by newbiely.com * * This ESP32 S3 Uno code is made available for public use without any restriction * * For comprehensive instructions and wiring diagrams, please visit: * https://newbiely.com/tutorials/esp32-s3-uno/esp32-s3-uno-oled-128x32 */ #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #define SCREEN_WIDTH 128 // OLED display width, in pixels #define SCREEN_HEIGHT 32 // OLED display height, in pixels // declare an SSD1306 display object connected to I2C Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); void setup() { Serial.begin(9600); // initialize OLED display with address 0x3C for 128x32 if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); while (true); } delay(2000); // wait for initializing oled.setCursor(0, 0); } void loop() { // draw rectangle oled.clearDisplay(); oled.drawRect(0, 15, 60, 40, WHITE); oled.display(); delay(2000); // fill rectangle oled.clearDisplay(); oled.fillRect(0, 15, 60, 40, WHITE); oled.display(); delay(2000); // draw the round rectangle oled.clearDisplay(); oled.drawRoundRect(0, 15, 60, 40, 8, WHITE); oled.display(); delay(2000); // fill the round rectangle oled.clearDisplay(); oled.fillRoundRect(0, 15, 60, 40, 8, WHITE); oled.display(); delay(2000); // draw circle oled.clearDisplay(); oled.drawCircle(20, 35, 20, WHITE); oled.display(); delay(2000); // fill circle oled.clearDisplay(); oled.fillCircle(20, 35, 20, WHITE); oled.display(); delay(2000); // draw triangle oled.clearDisplay(); oled.drawTriangle(30, 15, 0, 60, 60, 60, WHITE); oled.display(); delay(2000); // fill triangle oled.clearDisplay(); oled.fillTriangle(30, 15, 0, 60, 60, 60, WHITE); oled.display(); delay(2000); }

The screen is only 32 pixels tall, so the lower part of some shapes falls outside the screen. You will see only the top part of them. Change the y and height values if you want the full shape to fit.

ESP32 S3 Uno Code – Display Image

A logo or icon makes your project look finished. To show a picture, you first turn it into a bitmap array that the code can draw.

Convert the image to a bitmap array

Use the Image to Bitmap Converter tool to change any image file into a bitmap array. The image below shows how the Arduino icon is turned into an array.

image to bitmap array

Copy the array that the tool makes, and paste it in place of the icon array in the code below.

The video below shows the same steps with a 128x64 OLED and the Arduino icon:

Code for the ESP32 S3 Uno and the 128x32 OLED

The steps are the same on the ESP32 S3 Uno with a 128x32 OLED. The sketch below shows a 72x32 DIYables icon in the middle of the screen.

/* * This ESP32 S3 Uno code was developed by newbiely.com * * This ESP32 S3 Uno code is made available for public use without any restriction * * For comprehensive instructions and wiring diagrams, please visit: * https://newbiely.com/tutorials/esp32-s3-uno/esp32-s3-uno-oled-128x32 */ #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #define SCREEN_WIDTH 128 // OLED display width, in pixels #define SCREEN_HEIGHT 32 // OLED display height, in pixels // declare an SSD1306 display object connected to I2C Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); // bitmap of DIYable-icon image int bitmap_width = 72; // MUST match to bitmap image size int bitmap_height = 32; // MUST match to bitmap image size const unsigned char bitmap_DIYables [] PROGMEM = { // 'DIYables Icon', 72x32 0x00, 0x0f, 0xff, 0xff, 0x8f, 0xf8, 0x07, 0x38, 0x07, 0x00, 0x0f, 0xff, 0xff, 0x8f, 0xfe, 0x07, 0x1c, 0x0e, 0x00, 0x0f, 0xff, 0xff, 0x8f, 0xff, 0x07, 0x1c, 0x1c, 0x00, 0x0f, 0xff, 0xff, 0x8e, 0x07, 0x87, 0x0e, 0x1c, 0x00, 0x0f, 0xff, 0xff, 0x8e, 0x03, 0xc7, 0x0f, 0x38, 0x00, 0x0f, 0xff, 0xff, 0x8e, 0x01, 0xc7, 0x07, 0x38, 0x00, 0x0f, 0xff, 0xff, 0x8e, 0x01, 0xc7, 0x03, 0xf0, 0xf0, 0x0f, 0xff, 0xff, 0x8e, 0x01, 0xc7, 0x03, 0xe0, 0xfc, 0x0f, 0xff, 0xff, 0x8e, 0x01, 0xc7, 0x01, 0xe0, 0xfe, 0x0f, 0xff, 0xff, 0x8e, 0x03, 0xc7, 0x01, 0xc0, 0xff, 0x8f, 0xff, 0xff, 0x8e, 0x03, 0x87, 0x01, 0xc0, 0xff, 0x8f, 0xff, 0xff, 0x8e, 0x0f, 0x87, 0x01, 0xc0, 0xff, 0xcf, 0xff, 0xff, 0x8f, 0xff, 0x07, 0x01, 0xc0, 0xff, 0xef, 0xff, 0xff, 0x8f, 0xfc, 0x07, 0x01, 0xc0, 0xff, 0xef, 0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x80, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xfd, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xfc, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0f, 0xfc, 0xfc, 0xff, 0xff, 0xff, 0xef, 0xff, 0xff, 0x0e, 0x0c, 0x0c, 0xc3, 0x07, 0xff, 0xef, 0xff, 0xfe, 0x0f, 0xec, 0xec, 0x99, 0x7f, 0xff, 0xef, 0xff, 0xfe, 0x0f, 0x04, 0xe4, 0x81, 0x0f, 0xff, 0xcf, 0xff, 0xfc, 0x0e, 0x32, 0xe4, 0x9f, 0xc7, 0xff, 0x8f, 0xff, 0xf8, 0x0e, 0x32, 0x4c, 0x9b, 0x67, 0xff, 0x0f, 0xff, 0xf0, 0x0e, 0x04, 0x0c, 0xc3, 0x0f, 0xfe, 0x0f, 0xff, 0xe0, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xfc, 0x0f, 0xff, 0x80, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xe0, 0x0f, 0xfc, 0x00, 0x0f, 0xff, 0xff, 0xff, 0xff }; void setup() { Serial.begin(9600); // initialize OLED display with address 0x3C for 128x32 if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); while (true); } delay(2000); // wait for initializing } void loop() { oled.clearDisplay(); // display bitmap to the center int x = (SCREEN_WIDTH - bitmap_width) / 2; int y = (SCREEN_HEIGHT - bitmap_height) / 2; oled.drawBitmap(x, y, bitmap_DIYables, bitmap_width, bitmap_height, WHITE); oled.display(); delay(2000); }

※ NOTE THAT:

The image must be the same size as the screen or smaller. If you use your own picture with a 128x32 OLED, resize it first, then set the matching width and height in the oled.drawBitmap() call (the bitmap_width and bitmap_height values).

How to vertical and horizontal center align text/number on OLED

Centered text looks clean on a small screen. This sketch measures the text with getTextBounds(), then places it in the middle of the 128x32 display. It shows the word "DIYables" and the number 21 in turn, every two seconds.

/* * This ESP32 S3 Uno code was developed by newbiely.com * * This ESP32 S3 Uno code is made available for public use without any restriction * * For comprehensive instructions and wiring diagrams, please visit: * https://newbiely.com/tutorials/esp32-s3-uno/esp32-s3-uno-oled-128x32 */ #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #define SCREEN_WIDTH 128 // OLED display width, in pixels #define SCREEN_HEIGHT 32 // OLED display height, in pixels Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); // // create SSD1306 display object connected to I2C void setup() { Serial.begin(9600); // initialize OLED display with address 0x3C for 128x32 if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); while (true); } delay(2000); // wait for initializing oled.clearDisplay(); // clear display oled.setTextSize(2); // text size oled.setTextColor(WHITE); // text color oled.setCursor(0, 10); // position to display } void loop() { // display string String text = "DIYables"; oledDisplayCenter(text); delay(2000); // display number int number = 21; String str = String(number); oledDisplayCenter(str); delay(2000); } void oledDisplayCenter(String text) { int16_t x1; int16_t y1; uint16_t width; uint16_t height; oled.getTextBounds(text, 0, 0, &x1, &y1, &width, &height); // display on horizontal and vertical center oled.clearDisplay(); // clear display oled.setCursor((SCREEN_WIDTH - width) / 2, (SCREEN_HEIGHT - height) / 2); oled.println(text); // text to display oled.display(); }

The oledDisplayCenter() function gets the width and height of the text, then sets the cursor to half of the free space on each side. You can call it with any string, so it also works for sensor values once you turn them into a String.

OLED Not Working? Find the I2C Address

A black screen is usually caused by a wiring mistake or a wrong I2C address. Go through these checks:

  1. Check every wire again, especially SDA on GPIO8 and SCL on GPIO9.
  2. Make sure your OLED uses the SSD1306 driver.
  3. Find the real I2C address of your OLED with the I2C scanner code below on the ESP32 S3 Uno.
// I2C address scanner program #include <Wire.h> void setup() { Wire.begin(); Serial.begin(9600); Serial.println("I2C Scanner"); } void loop() { byte error, address; int nDevices; Serial.println("Scanning..."); nDevices = 0; for(address = 1; address < 127; address++ ) { Wire.beginTransmission(address); error = Wire.endTransmission(); if (error == 0) { Serial.print("I2C device found at address 0x"); if (address < 16) Serial.print("0"); Serial.print(address,HEX); Serial.println(" !"); nDevices++; } else if (error==4) { Serial.print("Unknown error at address 0x"); if (address < 16) Serial.print("0"); Serial.println(address,HEX); } } if (nDevices == 0) Serial.println("No I2C devices found"); else Serial.println("done"); delay(5000); // wait 5 seconds for next scan }

The Serial Monitor shows something like this:

∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32S3 Dev Module
Newbiely.ino
···
8 Serial.println("Hello World!");
Output
Serial Monitor
Message (Enter to send message to 'ESP32S3 Dev Module' on 'COM15')
New Line
9600 baud
Scanning... I2C device found at address 0x3C ! done Scanning... I2C device found at address 0x3C ! done
Ln 11, Col 1
ESP32S3 Dev Module on COM15
2

If the address is not 0x3C (for example 0x3D), change it in the oled.begin() line of your sketch.

FAQ

Which pins do I use for the OLED on the ESP32 S3 Uno?

Use the SDA (GPIO8) and SCL (GPIO9) header pins. On this board, A4 and A5 are only analog pins, not I2C. Wire.begin() uses GPIO8 and GPIO9 by default, so the sketch needs no pin numbers.

Should I power the OLED from 3.3V or 5V?

Use 3.3V. The ESP32 S3 Uno pins are not 5V tolerant, and on many OLED modules the I2C pull-up resistors connect to VCC. With 3.3V power, the SDA and SCL lines stay at a safe level.

Does the same code work as on the UNO R4?

Yes. The Adafruit SSD1306 and GFX libraries work the same on the ESP32 S3 Uno, so the sketches need no change. Only the wiring is different, because the I2C pins are SDA/SCL instead of A4/A5.

Why does my 128x32 OLED show squashed or cut text?

The code must set SCREEN_HEIGHT to 32. If you use a sketch made for a 128x64 OLED, the text and shapes end up in the wrong place. Also check that the image size is not bigger than 128x32.

What if my project needs more pins than the Uno headers give?

The ESP32 S3 Uno has two extra rows of holes with more GPIOs: GPIO15 and GPIO16 (I/O, PWM, analog), GPIO45 and GPIO35 to GPIO42 (I/O, PWM), and GPIO47/GPIO48 (output only, PWM). Solder pin headers to them and write the GPIO number in code. The OLED stays on the I2C pins, but if you add buttons or sensors to your display project, use GPIO35 to GPIO42 for digital inputs and GPIO15/GPIO16 for analog sensors, and never GPIO47/GPIO48 for inputs. Be careful with two things. First, GPIO47/GPIO48 may run at 1.8V instead of 3.3V on some modules (especially ones with "V" in the name, like R8V or R16V), so 3.3V devices can be damaged or act strangely. Second, GPIO0, GPIO3 (D6), GPIO45 and GPIO46 (D9) are boot strapping pins, and a wrong connection can stop the board from booting or uploading code. Use the other extra pins first.

Can I connect more than one I2C device with the OLED?

Yes. Many I2C devices can share the same SDA and SCL wires, as long as each one has a different address. Run the I2C scanner to see all the addresses on the bus.

Troubleshooting

Problem Possible Cause Solution
No COM port in Arduino IDE USB driver missing or charge-only cable Install the CP210x or CH340 driver, use a data USB cable, or hold BOOT while pressing RESET
OLED shows nothing OLED wired to A4/A5 or loose wire Move SDA to GPIO8 and SCL to GPIO9 and check VCC and GND
Serial Monitor shows SSD1306 allocation failed OLED not found at address 0x3C Run the I2C scanner and put the real address (often 0x3D) in oled.begin()
I2C scanner finds no device Power or wiring problem Power the OLED from 3.3V, check GND, and swap SDA and SCL if they are reversed
Text is cut or in the wrong place SCREEN_HEIGHT set to 64 Set SCREEN_HEIGHT to 32 for a 128x32 OLED
Image looks broken Bitmap size does not match the code Set bitmap_width and bitmap_height to the real image size and keep it at 128x32 or smaller
Missing library error when compiling Adafruit SSD1306 or GFX library not installed Install both libraries from the Library Manager
Screen does not change oled.display() not called Call oled.display() after each drawing step

※ OUR MESSAGES

  • As freelancers, We are AVAILABLE for HIRE. See how to outsource your project to us
  • Please feel free to share the link of this tutorial. However, Please do not use our content on any other websites. We invested a lot of effort and time to create the content, please respect our work!