History graph weird values

Hi! I was using blynk for quite long time, and i have issue with history graph.
Im sending dht11 humidity/temperature values and trying to display them and this actually works except one thing, the values on history graph are weird:

Im not sure if this is blynk issue, or my timer is sending data when dht11 didnt get a value.

#define BLYNK_PRINT Serial    // Comment this out to disable prints and save space
#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>
#include <SimpleTimer.h>
#include "DHT.h"

#define DHTTYPE DHT11
int dhtPin = D4;
SimpleTimer blynkTimer;
SimpleTimer ventTimer;
DHT dht(dhtPin, DHTTYPE);
int ventRelayPin = D5;
WidgetLED ventLED(2);

// You should get Auth Token in the Blynk App.
// Go to the Project Settings (nut icon).
char auth[] = "mytoken";

void setup() {
  pinMode(ventRelayPin, OUTPUT);
    
  dht.begin();
  Serial.begin(9600);
  Blynk.begin(auth, "myssid", "mypass");
  blynkTimer.setInterval(3000L, sendUptime);
  ventTimer.setInterval(1000L, controlVent);
}

void controlVent() {
  if( dht.readTemperature()>=24 ){
    digitalWrite(ventRelayPin, LOW);
    ventLED.on();
  } else {
    digitalWrite(ventRelayPin, HIGH);
    ventLED.off();
  }
  Serial.println(dht.readTemperature());
}

void sendUptime() {
  //temperature/humidity:
  int h = dht.readHumidity();
  int t = dht.readTemperature();
  
  Blynk.virtualWrite(V1, h);
  Blynk.virtualWrite(V0, t);  
}
 
void loop() {
  Blynk.run();
  ventTimer.run();
  blynkTimer.run();
}

DHT may not always return correct value. I think you need to add additional checks in code like in this example.

will try, thank you!

nope, its not NaN value, it sends me enormous values.
i’ve tested it with (the code is not real, just simplified my code):

if( isnan(t) || isnan(h) ){
print("its NaN")
} else{
print("its not NaN, sending")
sendToBlynk(t, v1)
sendToBlynk(h, v2)
}

and there was no “its NaN” prints, and at the same time it sometimes send weird values.

P.S. forgot to mention that I’m using wemos d1

@kongol.ml does the history graph do this on a regular basis? If so, what frequency, every hour, every 12 hours, every few days?

Looking at the graph is it trying to indicate 1 x 10 to the power 9 as the peak? This would be 1.9 billion and way off the top of the scale compared with the actual readings of 25 degrees.

@Costas no, i can’t see any regularity.
Here are the latest values:

So you see that for the last 6 hours it happened few times (actually if temperature is less than 24, it switch the relay, and for about 20 seconds i’ve heard that it was clicking every few seconds).
And for the last hour value are perfect

Ok, i’ve just figured out that the values are extremely high when I’m detaching data cable from dht11 (so thats why it wasn’t NaN, @Dmitriy :slight_smile: ).

(these blue and red peaks are moment when i detached the data wire from dht11)

So now it’s “help me with my project” topic.

Any suggestions on how to optimise code?

Here is the final one:

#define BLYNK_PRINT Serial    // Comment this out to disable prints and save space
#include <ESP8266WiFi.h>
#include <BlynkSimpleEsp8266.h>
#include <SimpleTimer.h>
#include <TimeLib.h>
#include <WidgetRTC.h>
#include "DHT.h"

#define DHTTYPE DHT11
int dhtPin = D4;
SimpleTimer blynkTimer;
SimpleTimer ventTimer;
SimpleTimer wateringTimer;
SimpleTimer wateringLogsTimer;
DHT dht(dhtPin, DHTTYPE);
int ventRelayPin = D5;
int waterPumpRelayPin = D6;
WidgetLED ventLED(2);
WidgetRTC rtc;
BLYNK_ATTACH_WIDGET(rtc, V4);


const int soil_moist = 550; //in water
const int soil_dry = 900;
int humidityPin = A0;
WidgetTerminal terminal(V3);

// You should get Auth Token in the Blynk App.
// Go to the Project Settings (nut icon).
char auth[] = "xxxxxxxxx";

void setup() {
  pinMode(ventRelayPin, OUTPUT);
  pinMode(waterPumpRelayPin, OUTPUT);
  dht.begin();
  Serial.begin(9600);
  
  Blynk.begin(auth, "xxxxxxxx", "xxxxxxxx");
  while (Blynk.connect() == false) {
    // Wait until connected
  }
  rtc.begin();
  blynkTimer.setInterval(3000L, sendUptime);
  ventTimer.setInterval(1000L, controlVent);
  wateringTimer.setInterval(1000L, waterFlower);
  wateringLogsTimer.setInterval(2*1000L, sendWateringLogs);
};

void controlVent() {
  if( dht.readTemperature()>=24 ){
    digitalWrite(ventRelayPin, LOW);
    ventLED.on();
    Serial.println("Vent is on;");
  } else {
    digitalWrite(ventRelayPin, HIGH);
    ventLED.off();
    Serial.println("Vent is off;");
  }
  Serial.print("DHT11 temperature: ");
  Serial.print(dht.readTemperature());
  Serial.println(";");
  Serial.println("-----------------------");
};


void printDigits(int digits) {
  Serial.print(":");
  if (digits < 10) {
    Serial.print('0');
  }
  Serial.print(digits);
};




void sendWateringLogs(){
  int soilHumidity = analogRead(humidityPin);
  String currentTime = String(hour()) + ":" + minute() + ":" + second();
  String currentDate = String(day()) + "/" + month() + "/" + year();
  Blynk.virtualWrite(V4, currentTime);
  
  if( soilHumidity>soil_dry ){
    //water it:
    terminal.print(currentTime);
    terminal.print(": Soil humidity is ");
    terminal.print(soilHumidity);
    terminal.println(". Watering now.");
    terminal.flush();

    Serial.println("Watering soil.");
    Serial.println("-----------------------");
  } else if( soilHumidity<=soil_moist ){
    terminal.print(currentTime);
    terminal.print(": TOO MANY WATER! (");
    terminal.print(soilHumidity);
    terminal.println(").");
    terminal.flush();

    Serial.print("TOO MANY WATER! (");
    Serial.print(soilHumidity);
    Serial.println(");");
    Serial.println("-----------------------");
  } else if( soilHumidity<soil_dry && soilHumidity>soil_moist ) {
    //moist enough:
    terminal.print(currentTime);
    terminal.print(": Soil humidity is ");
    terminal.print(soilHumidity);
    terminal.println("; All good.");
    terminal.flush();

    Serial.println("Soil humidity - all good.");
    Serial.println("-----------------------");
  }
  
  Serial.print("Soil humidity: ");
  Serial.print(soilHumidity);
  Serial.println(";");
  Serial.println("-----------------------");
};

void waterFlower(){
  int soilHumidity = analogRead(humidityPin);
  if( soilHumidity>soil_dry ){
    //water it:
    digitalWrite(waterPumpRelayPin, LOW);
  } else if( soilHumidity<=soil_moist ){
    digitalWrite(waterPumpRelayPin, HIGH);
  } else if( soilHumidity<soil_dry && soilHumidity>soil_moist ) {
    //moist enough:
    digitalWrite(waterPumpRelayPin, HIGH);
  }
};

void sendUptime() {
  //temperature/humidity:
  int h = dht.readHumidity();
  int t = dht.readTemperature();

  if( isnan(h) || isnan(t) ){
    Serial.print("should return");
    return; 
  } else {
    Serial.print("should send");
    Blynk.virtualWrite(V1, h);
    Blynk.virtualWrite(V0, t);  
  }
};
 
void loop() {
  Blynk.run();
  ventTimer.run();
  blynkTimer.run();
  wateringTimer.run();
  wateringLogsTimer.run();
}

Lol.

Code seems fine for me. Something wrong with it?

@Dmitriy, yes, it’s still sending weirdly big values (like if wire is disconnected, which is not)

SimpleTimer allows up to 10 timers per instance.

I would reduce your 4 instances to 1.

After changing a code, so that temperature form dht11 is reading once in a 2 seconds and humidity once in 4 seconds everything become fine.

DHT’s need a lot of time to settle. I myself always use 10s since it’s not very time critical anyway :slight_smile:

yes, you should give as much time as you can to dht11, as its too slow, but in my case it controls the ventilation, so its should be as fast as possible :slight_smile:

ALSO! dht11 values should be float, not int