Skip to content

Async #97

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
124 changes: 63 additions & 61 deletions DHT.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -33,32 +33,11 @@ void DHT::begin(void) {

//boolean S == Scale. True == Fahrenheit; False == Celcius
float DHT::readTemperature(bool S, bool force) {
float f = NAN;

if (read(force)) {
switch (_type) {
case DHT11:
f = data[2];
if(S) {
f = convertCtoF(f);
}
break;
case DHT22:
case DHT21:
f = data[2] & 0x7F;
f *= 256;
f += data[3];
f *= 0.1;
if (data[2] & 0x80) {
f *= -1;
}
if(S) {
f = convertCtoF(f);
}
break;
}
}
return f;
//Argument <<force>> is kept only for back-compatibility
if(S)
return this->convertCtoF(this->_temperature);
else
return this->_temperature;
}

float DHT::convertCtoF(float c) {
Expand All @@ -70,22 +49,8 @@ float DHT::convertFtoC(float f) {
}

float DHT::readHumidity(bool force) {
float f = NAN;
if (read()) {
switch (_type) {
case DHT11:
f = data[0];
break;
case DHT22:
case DHT21:
f = data[0];
f *= 256;
f += data[1];
f *= 0.1;
break;
}
}
return f;
//Argument <<force>> is kept only for back-compatibility
return this->_humidity;
}

//boolean isFahrenheit: True == Fahrenheit; False == Celcius
Expand Down Expand Up @@ -120,30 +85,53 @@ float DHT::computeHeatIndex(float temperature, float percentHumidity, bool isFah
return isFahrenheit ? hi : convertFtoC(hi);
}

boolean DHT::read(bool force) {
// Check if sensor was read less than two seconds ago and return early
// to use last reading.

void DHT::loop(){
uint32_t currenttime = millis();
if (!force && ((currenttime - _lastreadtime) < 2000)) {
return _lastresult; // return last correct measurement
}
_lastreadtime = currenttime;
switch(this->state){
case IDLE:
// Check if sensor was read less than two seconds ago and return early
// to use last reading.
if((currenttime - _lastreadtime) < 2000)
return;
this->_lastreadtime = currenttime;
this->state = WAITING;

// Reset 40 bits of received data to zero.
data[0] = data[1] = data[2] = data[3] = data[4] = 0;

// Send start signal. See DHT datasheet for full signal diagram:
// http://www.adafruit.com/datasheets/Digital%20humidity%20and%20temperature%20sensor%20AM2302.pdf
// Go into high impedence state to let pull-up raise data line level and
// start the reading process.
digitalWrite(_pin, HIGH);
break;

case WAITING:
if((currenttime-_lastreadtime) < 250)
return;
// First set data line low for 20 milliseconds.
pinMode(_pin, OUTPUT);
digitalWrite(_pin, LOW);

// Reset 40 bits of received data to zero.
data[0] = data[1] = data[2] = data[3] = data[4] = 0;
this->_lastreadtime = currenttime;
this->state = READING;
break;

// Send start signal. See DHT datasheet for full signal diagram:
// http://www.adafruit.com/datasheets/Digital%20humidity%20and%20temperature%20sensor%20AM2302.pdf
case READING:
if((currenttime-_lastreadtime) < 20)
return;
this->read();
this->state = IDLE;

}
}

// Go into high impedence state to let pull-up raise data line level and
// start the reading process.
digitalWrite(_pin, HIGH);
delay(250);
boolean DHT::isValid(){
return this->_lastresult;
}

// First set data line low for 20 milliseconds.
pinMode(_pin, OUTPUT);
digitalWrite(_pin, LOW);
delay(20);
boolean DHT::read() {

uint32_t cycles[80];
{
Expand Down Expand Up @@ -217,6 +205,20 @@ boolean DHT::read(bool force) {

// Check we read 40 bits and that the checksum matches.
if (data[4] == ((data[0] + data[1] + data[2] + data[3]) & 0xFF)) {
float t,h;
switch (_type) {
case DHT11:
this->_temperature = data[2];
this->_humidity = data[0];
break;
case DHT22:
case DHT21:
t = (data[2] & 0x7F) * 256 + data[3];
this->_temperature = t * 0.1 * ((data[2] & 0x80) ? -1 : 1);
h = data[0] * 256 + data[1];
this->_humidity = h * 0.1;
break;
}
_lastresult = true;
return _lastresult;
}
Expand Down
14 changes: 13 additions & 1 deletion DHT.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,9 @@ class DHT {
float convertFtoC(float);
float computeHeatIndex(float temperature, float percentHumidity, bool isFahrenheit=true);
float readHumidity(bool force=false);
boolean read(bool force=false);
boolean read();
boolean isValid();
void loop();

private:
uint8_t data[5];
Expand All @@ -57,7 +59,17 @@ class DHT {
uint32_t _lastreadtime, _maxcycles;
bool _lastresult;

float _temperature, _humidity;

enum readingStatus{
IDLE,
WAITING,
READING
};

uint32_t expectPulse(bool level);

readingStatus state = IDLE;

};

Expand Down
48 changes: 26 additions & 22 deletions examples/DHT_Unified_Sensor/DHT_Unified_Sensor.ino
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

// Depends on the following Arduino libraries:
// - Adafruit Unified Sensor Library: https://github.com/adafruit/Adafruit_Sensor
// - DHT Sensor Library: https://github.com/adafruit/DHT-sensor-library
// - DHT Sensor Library: https://github.com/nos86/DHT-sensor-library#async

#include <Adafruit_Sensor.h>
#include <DHT.h>
Expand All @@ -24,6 +24,7 @@
DHT_Unified dht(DHTPIN, DHTTYPE);

uint32_t delayMS;
float lastReading = 0;

void setup() {
Serial.begin(9600);
Expand Down Expand Up @@ -58,27 +59,30 @@ void setup() {
}

void loop() {
dht.loop();
// Delay between measurements.
delay(delayMS);
// Get temperature event and print its value.
sensors_event_t event;
dht.temperature().getEvent(&event);
if (isnan(event.temperature)) {
Serial.println("Error reading temperature!");
}
else {
Serial.print("Temperature: ");
Serial.print(event.temperature);
Serial.println(" *C");
}
// Get humidity event and print its value.
dht.humidity().getEvent(&event);
if (isnan(event.relative_humidity)) {
Serial.println("Error reading humidity!");
}
else {
Serial.print("Humidity: ");
Serial.print(event.relative_humidity);
Serial.println("%");
if(mills()-lastReading>delayMS){
lastReading = millis();
// Get temperature event and print its value.
sensors_event_t event;
dht.temperature().getEvent(&event);
if (isnan(event.temperature)) {
Serial.println("Error reading temperature!");
}
else {
Serial.print("Temperature: ");
Serial.print(event.temperature);
Serial.println(" *C");
}
// Get humidity event and print its value.
dht.humidity().getEvent(&event);
if (isnan(event.relative_humidity)) {
Serial.println("Error reading humidity!");
}
else {
Serial.print("Humidity: ");
Serial.print(event.relative_humidity);
Serial.println("%");
}
}
}
71 changes: 37 additions & 34 deletions examples/DHTtester/DHTtester.ino
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
// Example testing sketch for various DHT humidity/temperature sensors
// Written by ladyada, public domain
// Written by nos86, public domain

#include "DHT.h"

Expand All @@ -22,6 +22,7 @@
// tweak the timings for faster processors. This parameter is no longer needed
// as the current DHT reading algorithm adjusts itself to work on faster procs.
DHT dht(DHTPIN, DHTTYPE);
float lastReading = 0;

void setup() {
Serial.begin(9600);
Expand All @@ -32,38 +33,40 @@ void setup() {

void loop() {
// Wait a few seconds between measurements.
delay(2000);

// Reading temperature or humidity takes about 250 milliseconds!
// Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
float h = dht.readHumidity();
// Read temperature as Celsius (the default)
float t = dht.readTemperature();
// Read temperature as Fahrenheit (isFahrenheit = true)
float f = dht.readTemperature(true);

// Check if any reads failed and exit early (to try again).
if (isnan(h) || isnan(t) || isnan(f)) {
Serial.println("Failed to read from DHT sensor!");
return;
dht.loop();
if(millis()-lastReading>2000){
lastReading = millis();
// Reading temperature or humidity takes about 250 milliseconds!
// Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
float h = dht.readHumidity();
// Read temperature as Celsius (the default)
float t = dht.readTemperature();
// Read temperature as Fahrenheit (isFahrenheit = true)
float f = dht.readTemperature(true);

// Check if any reads failed and exit early (to try again).
if (isnan(h) || isnan(t) || isnan(f)) {
Serial.println("Failed to read from DHT sensor!");
return;
}

// Compute heat index in Fahrenheit (the default)
float hif = dht.computeHeatIndex(f, h);
// Compute heat index in Celsius (isFahreheit = false)
float hic = dht.computeHeatIndex(t, h, false);

Serial.print("Humidity: ");
Serial.print(h);
Serial.print(" %\t");
Serial.print("Temperature: ");
Serial.print(t);
Serial.print(" *C ");
Serial.print(f);
Serial.print(" *F\t");
Serial.print("Heat index: ");
Serial.print(hic);
Serial.print(" *C ");
Serial.print(hif);
Serial.println(" *F");
}

// Compute heat index in Fahrenheit (the default)
float hif = dht.computeHeatIndex(f, h);
// Compute heat index in Celsius (isFahreheit = false)
float hic = dht.computeHeatIndex(t, h, false);

Serial.print("Humidity: ");
Serial.print(h);
Serial.print(" %\t");
Serial.print("Temperature: ");
Serial.print(t);
Serial.print(" *C ");
Serial.print(f);
Serial.print(" *F\t");
Serial.print("Heat index: ");
Serial.print(hic);
Serial.print(" *C ");
Serial.print(hif);
Serial.println(" *F");
}
3 changes: 2 additions & 1 deletion keywords.txt
Original file line number Diff line number Diff line change
Expand Up @@ -19,4 +19,5 @@ convertFtoC KEYWORD2
computeHeatIndex KEYWORD2
readHumidity KEYWORD2
read KEYWORD2

loop KEYWORD2
isValid KEYWORD2