In this article, we are going to learn how to interface the DHT22 Temperature and Humidity sensor with the PIC16F877A microcontroller. DHT22 is related to DHT11 with some changes in data communication. This sensor is also known as AM2302/RHT03. As the Proteus library of DHT22 is not so available, so the library file will be attached in this article below. So let’s interface DHT22 with PIC microcontroller.
Disclaimer:
Handling electricity carries inherent risks. It’s essential to have the appropriate skills to manage it safely. Proceed at your own risk, as the author disclaims responsibility for any misuse, harm, or errors. All content on this website is unique and copyrighted; please avoid unauthorized copying. While most articles are open-source for your benefit, feel free to use the knowledge provided. If you find our resources helpful, consider purchasing available materials to support our work.
For assistance or guidance, leave a comment below; the author is committed to helping. Some articles may contain affiliate links that support the author with a commission at no additional cost to you. Thank you for your understanding and support.
Table of Contents
About DHT22 sensor:
Before interfacing DHT22 with PIC microcontroller we need to know about the DHT22 first, The DHT22(AM2302, RHT03) sensor comes in a single row 4-pin package and operates from 3.3 to 5.5V power supply. It can measure temperature from -40-80 °C with an accuracy of ±0.5°C and relative humidity ranging from 0-100% with an accuracy of ±2%. The sensor provides fully calibrated digital outputs for the two measurements.
It has got its own proprietary 1-wire protocol, and therefore, the communication between the sensor and a microcontroller is not possible through a direct interface with any of its peripherals. The protocol must be implemented in the firmware of the MCU with precise timing required by the sensor.
The following timing diagrams describe the data transfer protocol between an MCU and the DHT22 sensor. The MCU initiates data transmission by issuing a “Start” signal. The MCU pin must be configured as output for this purpose. The MCU first pulls the data line low for at least 18 ms and then pulls it high for the next 20-40 us before it releases it. Next, the sensor responds to the MCU “Start“ signal by pulling the line low for 80 us followed by a logic high signal that also lasts for 80 us.
Remember that the MCU pin must be configured to input after finishing the “Start“ signal. Once detecting the response signal from the sensor, the MCU should be ready to receive data from the sensor. The sensor then sends 40 bits (5 bytes) of data continuously in the data line. Note that while transmitting bytes, the sensor sends the most significant bit first.
Data consists of decimal and integral parts. Complete data transmission is 40bit, and the sensor sends higher data bit first. Data format: 16 bits RH data + 16 bits temperature data + 8bit checksum. If the data transmission is right, the check-sum should be the last 8bit of “MSB 8-bit RH data + LSB 8-bit RH data + MSB 8-bit temperature data + LSB 8-bit temperature data”.
The DHT22 is a digital sensor so it sends 1’s and 0’s, but it is very important to know how it sends the digital data. The figure below shows how the sensor sends its information:
Download DHT22 Proteus Library.
Example1:
MCU has received 40 bits of data from AM2302 as
0000 0010 1000 1100 0000 0001 0101 1111 1110 1110
16 bits RH data 16 bits T data checksum
Here we convert 16 bits RH data from binary system to decimal system,
0000 0010 1000 1100 → 652
Binary system Decimal system
RH=652/10=65.2%RH
Here we convert 16 bits T data from binary system to decimal system,
0000 0001 0101 1111 → 351
Binary system Decimal system
T=351/10=35.1℃
When the highest bit of temperature is 1, it means the temperature is below 0 degrees Celsius.
Example2:
1000 0000 0110 0101, T= minus 10.1℃
16 bits T data
Sum=0000 0010+1000 1100+0000 0001+0101 1111=1110 1110
Check-sum=the last 8 bits of Sum=1110 1110
Circuit diagram:
Here is the circuit diagram of our project DHT22 with PIC microcontroller:
You may find this helpful too: PCB design & Software help.
MicroC coding:
/******************************************************************************* Program for, "DHT11 interfacing with PIC16F877A" Program written by_ Engr. Mithun K. Das MCU: PIC16F877A; X-tal: 8MHz; mikroC pro for PIC v7.6.0 Date: 15-05-2020 *******************************************************************************/ // LCD module connections sbit LCD_RS at RB2_bit; sbit LCD_EN at RB3_bit; sbit LCD_D4 at RB4_bit; sbit LCD_D5 at RB5_bit; sbit LCD_D6 at RB6_bit; sbit LCD_D7 at RB7_bit; sbit LCD_RS_Direction at TRISB2_bit; sbit LCD_EN_Direction at TRISB3_bit; sbit LCD_D4_Direction at TRISB4_bit; sbit LCD_D5_Direction at TRISB5_bit; sbit LCD_D6_Direction at TRISB6_bit; sbit LCD_D7_Direction at TRISB7_bit; // END of LCD initialization // DHT22 pin connection (here data pin is connected to pin RB0) #define DHT22_PIN RB1_bit #define DHT22_PIN_DIR TRISB1_bit #include <stdint.h> // read one byte from sensor uint8_t dht22_read_byte() { uint8_t i = 8, dht22_byte = 0; while(i--) { while( !DHT22_PIN ); Delay_us(40); if( DHT22_PIN ) { dht22_byte |= (1 << i); // set bit i while( DHT22_PIN ); } } return(dht22_byte); } // read humidity (in hundredths rH%) and temperature (in hundredths °Celsius) from sensor void dht22_read(uint16_t *dht22_humi, int16_t *dht22_temp) { // send start signal DHT22_PIN = 0; // connection pin output low DHT22_PIN_DIR = 0; // configure connection pin as output Delay_ms(25); // wait 25 ms DHT22_PIN = 1; // connection pin output high Delay_us(30); // wait 30 us DHT22_PIN_DIR = 1; // configure connection pin as input // check sensor response while( DHT22_PIN ); while(!DHT22_PIN ); while( DHT22_PIN ); // read data *dht22_humi = dht22_read_byte(); // read humidity byte 1 *dht22_humi = (*dht22_humi << 8) | dht22_read_byte(); // read humidity byte 2 *dht22_temp = dht22_read_byte(); // read temperature byte 1 *dht22_temp = (*dht22_temp << 8) | dht22_read_byte(); // read temperature byte 2 dht22_read_byte(); // read checksum (skipped) if(*dht22_temp & 0x8000)// if temperature is negative { *dht22_temp &= 0x7FFF; *dht22_temp *= -1; } } char message[] = "00.0"; int humidity, temperature; // main function void main() { ADCON1 = 0x07;//ADC Off ADCON0 = 0x00; CMCON = 0x07;//comparator off Lcd_Init(); Lcd_Cmd(_LCD_CLEAR); Lcd_Cmd(_LCD_CURSOR_OFF); Lcd_Out(1,1,"DHT22 WITH"); Lcd_Out(2,1,"PIC16F877A"); Delay_ms(2000); Lcd_Cmd(_LCD_CLEAR); while(1) { dht22_read(&humidity, &temperature); Lcd_Out(1,1,"HUMIDITY:"); Lcd_Out(2,1,"TEMP:"); message[0] = humidity/100 + 48; message[1] = humidity/10%10 + 48; message[3] = humidity%10 + 48; Lcd_Out(1,11, message); Lcd_Out(1,16,"%"); message[0] = temperature/100 + 48; message[1] = temperature/10%10 + 48; message[3] = temperature%10 + 48; Lcd_Out(2,11, message); Lcd_Chr_CP(223); Lcd_Out(2,16,"C"); Delay_ms(1000); // wait a second }//while(1) } // end of code.
Code explanation:
uint8_t dht22_read_byte() { uint8_t i = 8, dht22_byte = 0; while(i--) { while( !DHT22_PIN ); Delay_us(40); if( DHT22_PIN ) { dht22_byte |= (1 << i); // set bit i while( DHT22_PIN ); } } return(dht22_byte); }
This sub-function is to read each byte of 8bit data from the DHT22 sensor. This function is called from the main DHTread function.
void dht22_read(uint16_t *dht22_humi, int16_t *dht22_temp) { // send start signal DHT22_PIN = 0; // connection pin output low DHT22_PIN_DIR = 0; // configure connection pin as output Delay_ms(25); // wait 25 ms DHT22_PIN = 1; // connection pin output high Delay_us(30); // wait 30 us DHT22_PIN_DIR = 1; // configure connection pin as input // check sensor response while( DHT22_PIN ); while(!DHT22_PIN ); while( DHT22_PIN ); // read data *dht22_humi = dht22_read_byte(); // read humidity byte 1 *dht22_humi = (*dht22_humi << 8) | dht22_read_byte(); // read humidity byte 2 *dht22_temp = dht22_read_byte(); // read temperature byte 1 *dht22_temp = (*dht22_temp << 8) | dht22_read_byte(); // read temperature byte 2 dht22_read_byte(); // read checksum (skipped) if(*dht22_temp & 0x8000)// if temperature is negative { *dht22_temp &= 0x7FFF; *dht22_temp *= -1; } }
Like DHT11, a start signal is required for DHT22 too. Then we need to check the response from DHT22. If the response is ok, then we can start the reading. The first two bytes are for humidity and the next two bytes are for temperature data. Finally, we eliminated the negative data from the result if any.
Test result:
Simulation works fine, real hardware works fine too. This library file can be used in suitable designs and real devices can be made. I tested the hardware before, at that time I had no plan for blogging. That is why did not record any video of those projects.
Anyway, in this article, you learned how to interface the DHT22 sensor with the PIC16F877A microcontroller. If you understand the concept of the code, then you can use any similar micro-controller. I hope you’ll make one and post here your test result.
I hope this project was helpful to you. If you make one for yourself, it will be a great pleasure for me. Anywhere you need help, let me know. Please share this project and subscribe to my blog. Thank you.
For Professional Designs or Help:
Check this out: 5 coolest multimeters you can buy
4 Comments
Er S S RANA · 15/12/2020 at 1:54 pm
Dear Dasji
Please elaborate the addition of decimal value 48 to humidity as well as temperature. LCD functions used in the program have also not been defined. Please share link of used lcd functions.
With Regards.
Thanking you.
Mithun K. Das · 19/12/2020 at 4:38 am
+48 to convert the decimal to ASCII value. And the LCD functions are built-in functions of the compiler.
Yusuf · 15/11/2021 at 1:07 am
Could you please elaborate on how to install DHT22 lib in proteus
Lab Projects BD · 15/11/2021 at 10:27 am
Copy and paste to the installed drive location inside models / library