Sunday, April 14, 2013

The Humidity Sensor

Commercial humidity sensors usually measure only the relative humidity, because it is easy to realize technically. The relative humidity however does not describe how much water is contained in the air. It only describes the relation between the partial pressure of water vapor and the saturated vapor pressure. Alternatively you can interprete the relative humidity as the relation between absolute humidity and the saturated vapor density. In the NASA note D-8401 , you can find all formulas describing the relationships between absolute humidity and relative humidity, see formula (5). The absolute humidity comes down to a formula having temperature, relative humidity and the saturated vapor pressure as variables, see formula (2) combined with (5). The saturated vapor pressure is approximately a logarithmic function with the temperature as variable. I implemented it in the code as a lookup table. Below you find the saturated vapor pressure curve I created:


The humidity sensor

On the humidity sensor which I designed, I use the sht11 from Sensirion to measure temperature and relative humidity. It contains a proprietary 2 wire interface, so connecting to I2C will not work. The processor on the humidity sensor is a atmega16 from Atmel. The code running on the processor implements Sensirion's 2 wire protocol. Also I connected the addressable switch DS2408 to the processor. This converts bit signals applied from the processor to the switch into 1-wire signals. This is how my control system communicates with the humidity sensors.

Code to calculate absolute humidity from relative humidity and temperature

here I want to show how I have implemented a C function to calculate the absolute humidity from the relative humidity and the temperature. Above I was telling that I implemented the saturated vapor pressure as a lookup table. This is how I have done it:

   static int es[] =
{63,70,76,83,90,103,117,130,144,158,198,212,226,240,255,283,297,326,354,383,401,435,474,516,
560,610,657,710,764,818,872,939,1007,1076,1145,1227,1310,1407,1504,1602,1701,1813,1940,
2068,2196,2339,2482,2641,2814,2988,3163,3366,3570,3778,4000,4236,4520,4848,5099,5399,5622,
5862,6199,6538,6879,7382,7889,8399,8750,9102,9604};

The first entry corresponds to the temperature -25 degree Celsius. The last entry correspons to 45 degree Celsius. So I can just reference the array with a Celsius value (added with 25), and I get the corresponding pressure value. The piece of code below just protects the processor from overrunning memory:

    if(T < -25.0) {
      T = -25.0;
    } else if(T > 45.0) {
    
      T = 45.0;
    }

Last but not least, the absolute humidity is calculated with the code below:

    H = es[(int)(T+ 25)]; // saturated vapor pressure, need 25 degrees for offset
    H *= U; Multiply relative humidity with saturated vapor pressure
    H /= 461.5; // divide by gas constant
    H /= (T+ 273.0); // divide by temperature in Kelvin


U is the relative humidity, T the temperature. Both values come directly from the humidity sensor sht11. 461,5 is the value of the gas constant.

Final words

There are other examples to calculate the absolute humidity, e.g. here. The method I use is simple. The sensors I have in my basement run constantly with this code for more than 2 years. The circuit I desgined with DS2408, atmega16  and sht11 runs stable and I have not noticed any problems until now.

2 comments:

  1. Very interesting article. I liked how "made" your own Humidity Sensor. Very impressive, keep up the good work :)
    reagards, Karl

    ReplyDelete
  2. Thanks Karl, I appreciate you feedback.

    ReplyDelete