Skip to Content

Si7021 Temperature Sensor Arduino Tutorial 

Si7021 Temperature Sensor Arduino Tutorial 

In this tutorial you will learn how to measure temperature and relative humidity using the Si7021 Sensor and an Arduino.

The Si7021 sensor is a popular choice for measuring temperature and humidity in DIY projects. It is a reliable and accurate sensor that communicates over I2C, making it easy to integrate with microcontrollers like Arduino and ESP32. With a wide operating range and low power consumption, the Si7021 is suitable for various applications, including weather stations, smart home devices, and environmental monitoring systems. Its compact size and simple interface make it ideal for both beginners and experienced makers looking to add environmental sensing capabilities to their projects.

Let’s get started with the required parts.

Required Parts

Obviously, you will need an Si7021 Temperature and Humidity Sensor. Typically, you don’t buy the raw sensor but a breakout board that has a few extra components, which make it easier to connect the sensor.

Furthermore, you will need a microcontroller. I used an Arduino Uno for this project, but any other Arduino or any ESP32/ESP8266 will be fine.

Finally, we want to display the measured temperature and humidity data. I chose an OLED but you could also go with an LCD display.

Si7021 Temperature & Humidity Sensor

Arduino

Arduino Uno

USB Data Sync cable Arduino

USB Cable for Arduino UNO

Dupont wire set

Dupont Wire Set

Half_breadboard56a

Breadboard

OLED display

OLED Display

Makerguides.com is a participant in the Amazon Services LLC Associates Program, an affiliate advertising program designed to provide a means for sites to earn advertising fees by advertising and linking to products on Amazon.com. As an Amazon Associate we earn from qualifying purchases.

The Si7021 Temperature & Humidity Sensor

The Si7021 is a very small, low power, humidity and temperature sensor with integrated electronics. It is factory-calibrated for accurate measurements and communicates via an I2C interface. The picture below shows the Functional Block Diagram of Si7021:

Functional Block Diagram of Si7021
Functional Block Diagram of Si7021 (source)

As you can see, it contains the humidity and temperature sensor elements, an analog-to-digital converter (ADC), the control logic with memory to store the calibration factors, and the electronics for the I2C interface.

Technical Specification

The temperature sensor element of the Si7021 can measure temperatures in the range from –10 to 85 °C with ±0.4 °C accuracy. And the humidity sensor measures relative humidity in the range from 0 to 80% RH with ± 3% RH accuracy.

The sensor operates on 1.9 to 3.6 V and the power consumption during operation is 150μA (60nA in standby mode).

A unique feature of the sensor is the integrated heating element that can be used to raise the temperature of the sensor to drive off condensation, or to implement dew-point measurements. Note that switching on the heater increases the power consumption up to 94.20mA (at 3.3V). For more details see the datasheet:

Typical Application Circuit

To use the Si7021 in an actual application you typically need to add pull-up resistors for the I2C interface and a capacitor to stabilize the power supply. The picture below shows the Typical Application Circuit:

Typical Application Circuit of Si7021
Typical Application Circuit of Si7021 (source)

In most cases, however, you want to use a breakout board that has these parts already integrated.

Breakout board for SI7021

The picture below shows a typical breakout board for the SI7021. It adds the aforementioned pull-up resistors and a voltage regulator, which allows you to run the board on 3.3V or 5V.

Front & Back of Si7021 breakout board
Front & Back of Si7021 breakout board

Note that many breakout board are labelled as “SI7021” but actually contain a different, albeit comparable sensor. In the example above, you can see the “SI7021” label on the board and the “HTU21” and “SHT21” label directly below the sensor.

The SI7021, HTU21 and SHT21 are interchangeable in terms of specification and communication protocols and even have the same I2C address (0x40). However, they store their serial numbers in a different format, which causes a minor issue when using the Adafruit_Si7021 or the SparkFun_Si7021 libraries. More about that later.

Finally, note that the SHT21, HTU21 and Si7021 are available with or without a protective PTFE membrane over the sensing element. See the following picture for the two types:

Si7021 Sensor with or without a protective membrane
Si7021 Sensor with or without a protective membrane

The protective membrane does not seem to make a difference.

Connecting the Si7021 to Arduino

Due to the I2C interface, connecting the Si7021 sensor to an Arduino is very simple. First, connect the SCL and SDA pins of the Si7021 breakout board to the corresponding pins on the Arduino board as shown below. Next, connect ground and VIN.

Wiring of Si7021sensor with Arduino
Wiring of Si7021sensor with Arduino

The breakout board runs on 5V or 3.3V and you can use either for VIN. In the wiring above, I am using 3.3V for VIN.

Next, let us write some simple code to test the function of the Si7021 sensor.

Code to read data from the Si7021

Before we can read temperature and humidity data from the Si7021 sensor, we need to install a library. Two common choices are the Adafruit_Si7021 or the SparkFun_Si7021 library. I am going to use the Adafruit_Si7021 library.

Open the Library Manager, search for “Si7021″and install the Adafruit_Si7021 library as shown below.

Adafruit_Si7021 library installed in  Library Manager
Adafruit_Si7021 library installed in Library Manager

Now we can write some simple test code. We start by including the Adafruit_Si7021 library and creating the sensor object. In the setup() function we initialize the sensor via sensor.begin(), and in the loop function we read and print the measure humidity and temperature.

#include "Adafruit_Si7021.h"

Adafruit_Si7021 sensor = Adafruit_Si7021();

void setup() {
  Serial.begin(9600);
  sensor.begin();
}

void loop() {
  Serial.print("Hum:");
  Serial.println(sensor.readHumidity(), 2);
  Serial.print("Temp:");
  Serial.println(sensor.readTemperature(), 2);
  delay(1000);
}

If you upload and run this code you should see the following output on your Serial Monitor. Make sure that the baud rate is set correctly to 9600 baud.

Output of Si7021 measurements on Serial Monitor
Output of Si7021 measurements on Serial Monitor

You can also open the Serial Plotter and blow on the sensor. You should see an increase in measured humidity and temperature. In the picture below the blue line shows the humidity maxed out at 100% and a slight increase in temperature (red line).

Output of Si7021 measurements on Serial Plotter
Output of Si7021 measurements on Serial Plotter

If the sensor does not work, make sure that it is correctly wired and can be detected as an I2C device. You can verify this by running an I2C scanner.

#include "I2CScanner.h"

I2CScanner scanner;

void setup() {
  Serial.begin(9600);
  while (!Serial) {};

  scanner.Init();
}

void loop() {
  scanner.Scan();
  delay(5000);
}

If you upload and run the code above it should print the following output on the Serial Monitor

--- Scan started ---
I2C device found at address 0x40  !

where 0x40 is the default I2C address of the Si7021 sensor. If you don’t see this, either the wiring is not correct, or your sensor is broken, or has a different I2C address, which it shouldn’t.

Did not find Si7021 sensor

If you try running the example code si7021.ino that comes with the Adafruit_Si7021 library, you may see the error message “Did not find Si7021 sensor!”. The error is generated by the following piece of code in the setup() function:

void setup() {  
  ...
  if (!sensor.begin()) {
    Serial.println("Did not find Si7021 sensor!");
    while (true)
      ;
  }
  ...
}

You will see this message, even when the I2C scan confirms that the Si7021 sensor is detected at address 0x40 and is actually working fine.

I looked a bit closer into the initialization code for sensor and the error is caused by the call of the _readRegister8() function in the code below.

bool Adafruit_Si7021::begin() {
  if (!i2c_dev->begin())
    return false;

  reset();
  if (_readRegister8(SI7021_READRHT_REG_CMD) != 0x3A)
    return false;

  readSerialNumber();
  _readRevision();

  return true;
}

The reason is that many breakout boards that are labelled with “Si7021”, are actually using a SHT21 or HTU21 sensor. Those sensors are comparable to the Si7021 but apparently store the serial number in a different format/address, which causes this error.

The easiest way to get around this is to call the begin() function but to ignore the return value – as I have done in the example code above. The sensor itself and the remainder of the code works just fine but you will not be able to print the serial number or version of the sensor.

I also tried the SparkFun_Si7021 library and it suffered from the same problem. If you don’t want to use any of those two libraries, and fix this problem, you can implement the functionality yourself. It is not hard. The blog post Bare Si7021 temperature/relative humidity sensor, shows how it is done.

For any practical application, you probably want to show the temperature and humidity data on a display and not print to the Serial Monitor. That is what we are going to do in the next section. We are adding an OLED and display the sensor data there.

Adding an OLED to display Si7021 data

Since the OLED is also an I2C device, connecting it is straightforward. We simply connect SDA and SCL to the same pins the Si7021 sensor is connected to. Since the OLED runs on 3.3V, we can also share the power supply lines. The picture below shows the complete wiring.

Connecting OLED and Si7021 with Arduino
Connecting OLED and Si7021 with Arduino

If you have any difficulties with the OLED, have a look at the tutorial How to Interface the SSD1306 I2C OLED Graphic Display With Arduino. The picture below shows the complete wiring on a real breadboard:

Wiring of OLED and Si7021 with Arduino
Wiring of OLED and Si7021 with Arduino

Code to display Si7021 data on OLED

In this section we write the code to show the temperature and humidity measured by the Si7021 sensor on an OLED screen. To write to the OLED we will use the Adafruit_SSD1306 library. You can install it via the Library Manager as usual:

Adafruit_SSD1306 library installed in Library Manager
Adafruit_SSD1306 library installed in Library Manager

The code below reads the measurements from the Si7021 sensor and displays the temperature and humidity values on the OLED. Have a look at the complete code first, and then we dive into its details.

#include "Adafruit_Si7021.h"
#include "Adafruit_SSD1306.h"

Adafruit_Si7021 sensor = Adafruit_Si7021();
Adafruit_SSD1306 oled(128, 64, &Wire, -1);

void oled_init() {
  oled.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  oled.clearDisplay();
  oled.setTextSize(2);
  oled.setTextColor(WHITE);
}

void centered(const char* text, int y) {
  int16_t x1, y1;
  uint16_t w, h;
  oled.getTextBounds(text, 0, 0, &x1, &y1, &w, &h);
  oled.setCursor(64 - w / 2, y);
  oled.print(text);
}

void display() {
  static char text[30];
  float temp = sensor.readTemperature();
  float hum = sensor.readHumidity();

  oled.clearDisplay();
  sprintf(text, "%.1f c", temp);
  centered(text, 12);
  sprintf(text, "%.1f %%", hum);
  centered(text, 38);
  oled.display();
}

void setup() {
  oled_init();
  sensor.begin();
}

void loop() {
  display();
  delay(1000);
}

Libraries and Display Initialization

We start by including the necessary libraries for the Si7021 sensor and the Adafruit SSD1306 OLED display. We then initialize the OLED display in the oled_init() function. This function sets up the display, clears it, sets the text size, and color for the text.

#include "Adafruit_Si7021.h"
#include "Adafruit_SSD1306.h"

Adafruit_Si7021 sensor = Adafruit_Si7021();
Adafruit_SSD1306 oled(128, 64, &Wire, -1);

void oled_init() {
  oled.begin(SSD1306_SWITCHCAPVCC, 0x3C);
  oled.clearDisplay();
  oled.setTextSize(2);
  oled.setTextColor(WHITE);
}

Note that the I2C address for the OLED display is set to 0x3C in oled.begin(). Most of these small OLEDs use this address but yours might be different. If you don’t see anything on the OLED, it most likely has a different I2C address and you have change the address passed on to oled.begin(). If you don’t know the I2C address have a look at the How to Interface the SSD1306 I2C OLED Graphic Display With Arduino tutorial.

Display Functions

The centered() function is used to print text centered on the OLED display at a specified y-coordinate. The display() function reads the temperature and humidity data from the sensor and displays them on the OLED screen.

void centered(const char* text, int y) {
  // Function to center text on OLED
}

void display() {
  // Function to display temperature and humidity on OLED
}

Setup Function

In the setup() function, we initialize the serial communication for debugging purposes, initialize the OLED display, and begin communication with the Si7021 sensor. As mentioned before, if the Si7021 sensor is not detected, check the wiring, the I2C address and ignore the return value of sensor.begin().

void setup() {
  oled_init();
  sensor.begin();
}

Loop Function

The loop() function continuously calls the display() function to update and display value on the OLED screen. It then waits for 1 second (1000ms) before the next update.

void loop() {
  display();
  delay(1000);
}

Output on OLED

If you upload and run the code, you should see the temperature in Celsius and relative humidity in percent displayed on the OLED.

Si7021Output on OLED
Si7021Output on OLED

And there you have a nice, little environmental sensor setup!

Conclusions

In this tutorial you learned how to use the Si7021 temperature and humidity sensor, an OLED and an Arduino Uno to build an environmental sensor.

Since the Si7021 has a low power mode and runs on 3.3V it would be also suitable for building a battery-powered, environmental sensor using an ESP32. Have a look at the at the Simple ESP32 Internet Weather Station, where we use a battery-powered ESP32, for instance. If you want to reduce the power consumption even further, I would recommend an e-Paper display instead of an OLED. The Weather Station on e-Paper Display tutorial, might come in handy here.

Note that there are many, many alternative temperature (and humidity) sensors you can use. Here is a list of tutorials, where we use some of these sensors.

Most comparable, when it comes to power consumption, ease of use and accuracy, is probably the BME280 sensor. There is a very nice comparison of Temperature/Humidity sensors, worth reading.

Finally, if you prefer the ESP32 over an Arduino, have a look at the following tutorials.

I hope you had fun building and playing with this project. If you have any questions, feel free to ask in the comment section.

Happy tinkering ; )