ESP32 UNO - DHT22 Temperature Humidity Sensor - OLED

Need a tiny screen that shows the room climate at a glance? Pair a DHT22 sensor with an SSD1306 OLED and the ESP32 Uno form board, and you get the temperature and the humidity in big, centered digits. The AM2302 (another name for the DHT22) gives one decimal place, so even small changes from a warm hand show up on the I2C OLED display.

What you will do:

  1. Hook up a DHT22 module plus a 128x64 I2C OLED to the ESP32 Uno
  2. Get the Adafruit SSD1306 and DHT libraries from the Arduino IDE Library Manager
  3. Get °C and % values with readTemperature() and readHumidity()
  4. Draw both numbers in the middle of the OLED screen with getTextBounds()
ESP32 Uno DHT22 OLED

Components You Need

1×ESP32 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 128x64
1×SSD1306 I2C OLED Display 128x32
1×DHT22 Temperature Humidity Sensor Module
1×Alternatively, DHT22 Sensor
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 .

Buy Note: If you want a bigger OLED display, use the 2.42 inch OLED Display 128x64 .

Sensor and Screen at a Glance

After this part, you know what each module brings to the build.

Module Role Here Link to Board Supply
DHT22 (AM2302) module Senses air temperature and relative humidity Single DATA wire 3.3V to 5V
SSD1306 OLED 128x64 Shows the two values as white text I2C (SDA and SCL) 3.3V to 5V

The DHT22 spans -40 to 80°C with roughly ±0.5°C error, and 0 to 100% humidity with roughly ±2% error. It refreshes about every 2 seconds. The OLED has no backlight; each pixel makes its own light, so the text stays sharp in a dark room.

Good to know: the sketch asks the sensor for data in every loop. Faster requests than one per 2 seconds just return the last stored value, so the screen never flickers with bad data.

Want the full pinout, a basic sketch or the library notes for one part alone? Read these first:

ESP32 Uno Pinout

A header label like D2 is printed on the board, but the sketch needs the GPIO number behind it. Look up D2, SDA and SCL on the picture below before you push in a jumper.

ESP32 Uno pinout diagram

How to Connect

When this step is done, the sensor DATA line sits on D2 and the OLED sits on the I2C header.

The wiring diagram between ESP32 Uno DHT22 temperature humidity sensor module OLED

This image is created using Fritzing. Click to enlarge image

Step 1 — DHT22 module

DHT22 Pin ESP32 Uno Pin
VCC (+) 3.3V
GND (-) GND
DATA (OUT) D2 (GPIO26)

Step 2 — SSD1306 OLED

OLED Pin ESP32 Uno Pin
VCC 3.3V
GND GND
SDA SDA (GPIO21)
SCL SCL (GPIO22)

Good to know: A4 and A5 on the ESP32 Uno are input-only analog pins with no I2C role. The OLED goes on the separate SDA and SCL pins.

Good to know: the DHT22 module already carries a pull-up resistor on DATA. A bare 4-pin DHT22 needs a 10 kΩ resistor from DATA to 3.3V.

WARNING

ESP32 Uno pins work at 3.3V and are NOT 5V tolerant. The module pull-up ties DATA to whatever voltage feeds VCC. Run the DHT22 from 3.3V, so GPIO26 never sees 5V. The same idea applies to the OLED: power it from 3.3V so its SDA and SCL pull-ups stay at 3.3V.

ESP32 Uno Code

The sketch reads the DHT22 on GPIO26 again and again, then draws the temperature on the top line and the humidity on the bottom line of the OLED.

/* * This ESP32 Uno code was developed by newbiely.com * * This ESP32 Uno code is made available for public use without any restriction * * For comprehensive instructions and wiring diagrams, please visit: * https://newbiely.com/tutorials/esp32-uno/esp32-uno-dht22-temperature-humidity-sensor-oled */ #include <Wire.h> #include <Adafruit_GFX.h> #include <Adafruit_SSD1306.h> #include <DHT.h> #define SCREEN_WIDTH 128 // screen width of the OLED in pixels #define SCREEN_HEIGHT 64 // screen height of the OLED in pixels (set 32 for a 128x32 module) #define DHT22_PIN 26 // D2 (GPIO26) reads the DHT22 DATA line Adafruit_SSD1306 oled(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, -1); // OLED object on the default I2C bus: SDA (GPIO21), SCL (GPIO22) DHT dht22(DHT22_PIN, DHT22); String temperature; String humidity; void setup() { Serial.begin(9600); // start the 128x64 OLED at I2C address 0x3C if (!oled.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { Serial.println(F("SSD1306 allocation failed")); while (true); } delay(2000); // give the screen time to power up oled.clearDisplay(); // wipe the screen buffer oled.setTextSize(3); // large font oled.setTextColor(WHITE); // white pixels on black oled.setCursor(0, 10); // starting point of the text dht22.begin(); // start talking to the DHT22 sensor temperature.reserve(10); // book memory early so String does not fragment the heap humidity.reserve(10); // same for the humidity text } void loop() { float humi = dht22.readHumidity(); // get relative humidity in % float tempC = dht22.readTemperature(); // get temperature in °C // NaN means the sensor did not answer if (isnan(humi) || isnan(tempC)) { temperature = "Failed"; humidity = "Failed"; } else { temperature = String(tempC, 1); // keep one digit after the point temperature += char (247); // degree sign in the OLED font temperature += "C"; humidity = String(humi, 1); // keep one digit after the point humidity += "%"; Serial.print(tempC); // log the temperature Serial.print("°C | " ); // separator text Serial.print(humi); // log the humidity Serial.println("%"); // end the line } oledDisplayCenter(temperature, humidity); // draw both values on the OLED } void oledDisplayCenter(String temperature, String humidity) { int16_t x1; int16_t y1; uint16_t width_T; uint16_t height_T; uint16_t width_H; uint16_t height_H; oled.getTextBounds(temperature, 0, 0, &x1, &y1, &width_T, &height_T); oled.getTextBounds(temperature, 0, 0, &x1, &y1, &width_H, &height_H); // place each line in the middle of the screen oled.clearDisplay(); // start from a blank buffer oled.setCursor((SCREEN_WIDTH - width_T) / 2, SCREEN_HEIGHT/2 - height_T - 5); oled.println(temperature); // top line: temperature oled.setCursor((SCREEN_WIDTH - width_H) / 2, SCREEN_HEIGHT/2 + 5); oled.println(humidity); // bottom line: humidity oled.display(); }

Upload and Test

  1. First time with this board? Set it up with ESP32 Uno - Getting Started before you continue.
  2. Build the circuit by following the wiring table above.
  3. Plug in the USB Type-C cable between the ESP32 Uno and your computer.
  4. Select the board in Arduino IDE: pick ESP32 Dev Module and the COM port of the board (CH340).
  5. Open the Library Manager with the Libraries icon in the left bar.
  6. Type "SSD1306" in the search box and pick the SSD1306 library from Adafruit.
  7. Install it with 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
ESP32 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
ESP32 Dev Module on COM15
1
  1. Accept the extra libraries (Adafruit GFX and BusIO) by clicking Install All.
  • Search for Adafruit GFX Library created by Adafruit and click the Install button.
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32 Dev Module
Library Manager
Type:
All
Topic:
All
Adafruit GFX Library by Adafruit
Install this library in addition to the display library for your hardware. More info
1.12.6
INSTALL
Newbiely.ino
···
1 void setup() {
Output
Serial Monitor
Ln 1, Col 1
ESP32 Dev Module on COM15
1
  1. Type "DHT" and pick the DHT sensor library from Adafruit.
  2. Install it with the Install button.
  • Search for DHT sensor library created by Adafruit and click the Install button.
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32 Dev Module
Library Manager
Type:
All
Topic:
All
DHT sensor library by Adafruit
Arduino library for DHT11, DHT22, etc Temp & Humidity Sensors More info
1.4.6
INSTALL
Newbiely.ino
···
1 void setup() {
Output
Serial Monitor
Ln 1, Col 1
ESP32 Dev Module on COM15
1
  1. Accept the Adafruit Unified Sensor dependency by clicking Install All.
  • Search for Adafruit Unified Sensor created by Adafruit and click the Install button.
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32 Dev Module
Library Manager
Type:
All
Topic:
All
Adafruit Unified Sensor by Adafruit
A unified sensor abstraction layer used by many Adafruit sensor libraries. More info
1.1.14
INSTALL
Newbiely.ino
···
1 void setup() {
Output
Serial Monitor
Ln 1, Col 1
ESP32 Dev Module on COM15
1
  1. Paste the sketch into a new Arduino IDE window.
  2. Upload with the Upload button and wait for "Done uploading".
  3. Change the air around the sensor. Put a cup of hot tea next to it, or set it near a cold window for a minute.
  4. Read the values on the OLED, and in the Serial Monitor set to 9600 baud.
  5. Pro tip: fold a small piece of paper into a shield between the board and the DHT22. Heat from the board then reaches the sensor less, and the reading stays closer to the real room value.
∞
Newbiely | Arduino IDE 2.3.8
──
☐
✕
File
Edit
Sketch
Tools
Help
ESP32 Dev Module
Newbiely.ino
···
8 Serial.println("Hello World!");
Output
Serial Monitor
Message (Enter to send message to 'ESP32 Dev Module' on 'COM15')
New Line
9600 baud
22.70°C | 47.30% 22.80°C | 47.10% 23.60°C | 52.80% 24.90°C | 61.40% 25.30°C | 64.20%
Ln 11, Col 1
ESP32 Dev Module on COM15
2

※ NOTE THAT:

You never set an x or y position by hand. The code measures each text line and places it in the middle of the screen, both across and down.

Video Tutorial

See the ESP32 Uno build in action in the video below.

How the Code Works

After this part, you can find and change any piece of the sketch.

Code Part What It Does
#define DHT22_PIN 26 Tells the DHT library that DATA is on D2 (GPIO26)
oled.begin(SSD1306_SWITCHCAPVCC, 0x3C) Starts the OLED at I2C address 0x3C and stops with an error text if it is not found
dht22.readHumidity() and readTemperature() Return the humidity in % and the temperature in °C, or NaN on a failed read
String(tempC, 1) + char(247) Builds text with one decimal and a degree sign from the OLED font
oledDisplayCenter() Uses getTextBounds() to measure the text, then centers two lines on the screen

The result is two large lines, such as "23.6°C" over "52.8%", that update as fast as the sensor gives new data.

ESP32 Uno vs UNO R4 for This Project

Moving this build from the UNO R4 to the ESP32 Uno changes one pin number and a few wiring details.

Item Arduino UNO R4 ESP32 Uno
Logic voltage 5V 3.3V
DHT22 DATA pin in code 2 (D2) 26 (D2 header)
OLED I2C pins SDA and SCL header (also A4 and A5) SDA GPIO21 and SCL GPIO22 header only
Safe sensor supply 3.3V or 5V 3.3V
Libraries Adafruit SSD1306 and DHT Same libraries, no change
Wireless WiFi only on the R4 WiFi WiFi and Bluetooth built in
Arduino IDE board Arduino UNO R4 WiFi ESP32 Dev Module

The wiring diagram stays the same, so the jumpers land in the same header spots. Only feed both modules from 3.3V, because ESP32 Uno pins do not take 5V.

Go Wireless: Climate Readout on Your Phone

With this idea, you can check the room from another place, not just at the OLED.

The ESP32 Uno has WiFi and Bluetooth on the board. Keep the OLED for people near the desk, and also send the same temperature and humidity to a browser or a phone app. A live chart makes it easy to see how the air changes over a whole day.

Try These Next

  • Show °F under the °C value by calling dht22.readTemperature(true).
  • Add a small warning icon when the humidity goes above 70%.
  • Keep the lowest and the highest temperature since power-on and show them every 10 seconds.

Troubleshooting

Problem Possible Cause Solution
Arduino IDE lists no COM port CH340 driver not installed or a power-only USB cable Install the CH340 driver and swap to a USB cable that carries data
"Failed to connect" or "Waiting for download" during upload The board did not switch to download mode Press and hold BOOT as the upload begins, then release it
"SSD1306 allocation failed" in the Serial Monitor OLED not answering on I2C Check VCC and GND on the OLED and that SDA and SCL go to GPIO21 and GPIO22
OLED stays black Module uses address 0x3D, or wires sit on A4 and A5 Try 0x3D in oled.begin() and move the I2C wires to the SDA and SCL header
Both lines read "Failed" The DHT22 sends no valid data Check DATA on D2 (GPIO26), the 3.3V and GND jumpers, and the pull-up on a bare sensor
Text sits low or is cut on a 128x32 screen SCREEN_HEIGHT is still 64 Change SCREEN_HEIGHT to 32 and upload again
Compile error about Adafruit_Sensor.h or DHT.h A library is missing Install DHT sensor library and Adafruit Unified Sensor in the Library Manager
Temperature reads 1 to 3 degrees high Board heat reaches the sensor Put the DHT22 on longer wires a few centimeters away from the board

FAQ

Is the DHT22 better than the DHT11 for this OLED display?

Yes, for most rooms. The DHT22 shows one decimal place, covers -40 to 80°C and 0 to 100% humidity, and is more accurate. The DHT11 is cheaper but rounds to whole numbers and covers a smaller range.

Should the DHT22 get 3.3V or 5V on the ESP32 Uno?

Use 3.3V. The module pull-up lifts DATA to its supply voltage, and ESP32 Uno pins are not made for 5V. The DHT22 works well at 3.3V with normal jumper wire lengths.

Which pins do SDA and SCL use on the ESP32 Uno?

The OLED goes to the pins marked SDA (GPIO21) and SCL (GPIO22). Wire.begin() inside the SSD1306 library picks them by default, so you add no pin code. A4 and A5 have no I2C role on this board.

Why is DHT22_PIN 26 and not 2?

The code uses GPIO numbers, not header labels. The D2 header spot on the ESP32 Uno is wired to GPIO26, so the sketch writes 26.

How do I make the text smaller to fit more values?

Change oled.setTextSize(3) to 2 or 1. Size 2 leaves room for a third line, for example a heat index value from dht22.computeHeatIndex().

Can this sketch run on the 128x32 OLED module?

Yes. Set SCREEN_HEIGHT to 32 and lower the text size to 2, because size 3 text in two lines is too tall for 32 pixels.

Does the original DHT22 OLED sketch run on the ESP32 Uno unchanged?

Almost. Compared with the UNO R4 version, only the DHT22 pin number changes from 2 to 26. The Adafruit SSD1306, GFX and DHT libraries all support the ESP32 Uno.

Why does my PC need a CH340 driver for this board?

The ESP32 Uno talks to the computer through a CH340 USB-to-serial chip. Without the driver, Windows or macOS shows no COM port, and the IDE cannot upload.

Can I move the DHT22 to another header pin?

Yes. D3 (GPIO25), D6 (GPIO27) or D7 (GPIO14) are good choices. Put the GPIO number in DHT22_PIN. Avoid D8 (GPIO12), D10 (GPIO5) and A0 (GPIO2), which are boot strapping pins, and A2 to A5, which are input only.

Could I see these readings on a web page too?

Yes. The ESP32 Uno has WiFi, so you can keep the OLED and also serve the values to a browser, or send them to a phone over Bluetooth. The DIYables Web Apps and Bluetooth App tutorials linked above show how.

What if this climate screen needs more pins than the Uno headers give?

The ESP32 Uno has a few extra holes near the power header. GPIO32 and GPIO33 give I/O, PWM and analog on ADC1, so they also read analog values while WiFi is on. GPIO15 gives I/O, PWM and analog on ADC2. Fit pin headers into those holes, then type the GPIO number in the sketch. GPIO32 or GPIO33 suit a second DHT22 or a light sensor here. Two warnings: GPIO15 and GPIO0 (the IO0 pin at the unused Uno NC spot) are boot strapping pins, and a wrong connection can stop the board from booting or uploading code, so use GPIO32/33 first. Never use the six holes under the digital header (SD0 to SD3, CMD, CLK = GPIO6 to GPIO11), because they connect to the flash chip and using them crashes the board.

※ 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!