Hello Community.
Well, In my project I want to control the temperature of my room with a NodeMCU 1.0(ESP-12E). I would like to keep the temperature between 22 to 25 degrees (i.e). The idea i had was use while to make the MCU to wait and do not keep sending the command many times. but it make the rest of the program stop. I am using others sensors in my project such as DHT22, and a CT for current. Also I am using Infrared to communication with the AC.
I have tried this code for my project:
#include "EmonLib.h" // I got this library from open from OpenEnergy Monitor website
#define BLYNK_PRINT Serial // Comment this out to disable prints and save space
#include "ESP8266WiFi.h"
#include "BlynkSimpleEsp8266.h"
#include <DHT.h>
#include <IRremoteESP8266.h>
#include <IRsend.h>
//IR Signals to cool down the temperature to 22 and to set Fan Mode
uint16_t ON22 //Raw code signal from the remote controller.
uint16_t FAN //Raw code signal from the remote controller.
IRsend irsend (4);
#define DHTPIN 5 // what digital pin the DHT22 is conected to
#define DHTTYPE DHT22 // there are multiple kinds of DHT sensors
DHT dht(DHTPIN, DHTTYPE);
// You should get Auth Token in the Blynk App.
// Go to the Project Settings (nut icon).
char auth[] = "b77d33d0befc43a0a2d5508f8e86587b";
// Your WiFi credentials.
// Set password to "" for open networks.
char ssid[] = "SSID";
char pass[] = "Password";
EnergyMonitor emon1;
// 220V is my Electrical Network voltage default.
int network = 220;
//Pin of sensor SCT
int pino_sct = A0;
void setup()
{
irsend.begin();
Serial.begin(9600);
Blynk.begin(auth, ssid, pass);
//Pin, calibration - Cur Const= Ratio/BurdenResistor. 2000/24 = 85
emon1.current(pino_sct, 85);
}
BLYNK_WRITE(V1) //I set the botton V1 as switch mode.
{
int EcoMode= param.asInt();// .
float t = dht.readTemperature(); //
if(EcoMode == 1)//
{
if (t<22){
irsend.sendRaw(FAN,349,38);// 349 is the variable size and 38 is the frequency in kHz.
while(t<22) { } //wait until temperature is over 22.
}
if(t>25) {
irsend.sendRaw(ON22,349,38);
while (t>25) { } //wait until temperature is under 25
}
Blynk.run(); // Run rest of show in-between waiting for this loop to repeat or quit.
int EcoMode = 0; // Set V1 status to 0 to quit,
Blynk.syncVirtual(V1); // ...Then force BLYNK_WRITE(V1) function check of button status to determine if repeating or done.
}
}
BLYNK_READ(V2){
double Irms = emon1.calcIrms(1480);
Blynk.virtualWrite(V2,Irms);// Current.
}
BLYNK_READ(V3){
double Irms = emon1.calcIrms(1480);
Blynk.virtualWrite(V3,Irms*network); // The consumption of energy.
}
BLYNK_READ(V4) {
float t = dht.readTemperature();
Blynk.virtualWrite(V4,t);
}
BLYNK_READ(V5) {
float h = dht.readHumidity();
Blynk.virtualWrite(V5,h);
}
void loop()
{
Blynk.run();
}
So the idea is when the botton V1 is pressed, the AC would enter in āEcoModeā so this set a temperature interval and keep turning off and On the AC Compressor to save energy. So its basically a energy monitor with automation control for energy efficiency.
I was wondering if the only solution is use BlynkTimer for solve this. If you have other suggestions to improve my code I would appreciate too.
Iāve done some experimentation with heating/cooling using my inverter aircon system and although Iāve not finalised the setup yet, my plan is to effectively override the temperature sensor in the A/C unit and use my ESP8266 attached temperature sensor instead.
If Iām using cooling mode then Iāll be setting the A/C to its lowest temperature (18 degrees) and running it until the ESP8266 temperature sensor (DHT22 in your case) says weāve earned the target temperature. At that point Iāll either switch the A/C off, or put it in fan only mode - this will ultimately depend on the type of A/C unit and how it responds to various situations.
In heating mode Iāll set the temperature to maximum 30 degrees and run it until my target temperature is reached.
The important thing with temperature control is to use Hysteresis code that builds-in a temperature tolerance that prevents the heater/cooler switching on and off every few seconds.
Say you want to use a tolerance of 0.5 degree and your target temperature is 22 degrees and youāre trying to cool your room. In this situation, you wouldnāt switch the aircon on until the temperature is 22.5 degrees and you wouldnāt turn it off until the temperature is 21.5 degrees. Youāll need to experiment with the tolerance levels as it will depend on the power of your aircon unit and the size of your room - plus your personal preference for temperature differentials.
I realise that this doesnāt answer your original question though. I think youāll want to use a timer to check your room temperature every so often. Once every 10 seconds maybe? In cooling mode, if the temperature is above 22.5 degrees then send the 18 degrees cooling command. If itās below 21.5 degrees then send the off, or fan only command.
@PeteKnight why are you sending max 30 and min 16 degrees and nothing in between? Isnāt that putting unnecessary stress on the compressor (and your wallet)? I know you are powering off when you reach your target temperature but surely thatās not the optimum way of getting there.
Well In my case just cooling mode would be necessary for my project so I believe I can save some energy setting intervals of temperature instead setting just one temperature so the AC doesnāt need to switches a lot of times to keep the target. Moreover, the temperature can still maintain the environment comfortable. In my region is very hot, something about 30 and 35 degrees (86F and 95F ) So if I keep the room temperature between 22 and 25 it could be interesting.
The code I am aiming is:
If botton āEcoModeā press
loop() {
check the temperature
If (t<22)
fan mode to raise the temperature until 25
if(t>25)
cool down until 22 degrees}
keep running the rest of program parallel with the loop
My aircon runs at the same power, regardless of the temperature you set. All Iām doing by sending an 18 degrees cooling message is to ensure that the aircon thermostat and the ESP thermostat arenāt working against each other. The aircon uses tolletrnces as well, so itās very easy to get to a situation where they are fighting against each other.
You are probably right @PeteKnight
I was just thinking that air con engineers always tell you to forget about max and min unless you own an oil well
@Victor_Caravelas_Sou the hysteresis is basically not selecting 2 numbers like your 22 and 25 because at each end of the range it can trigger on and off repeatedly.
I got it. So that is my point! I believe the time that the temperature takes to get 25 from 22 is enough to save some energy. In usual air con (not inverter) which are the majority here this could work.
I thought he explained it very good As the DHT22 has a resolution of 0.1, temperature readings between 21.6 and 22.4 will not trigger any action. I use timer to check my sensor(s) once a minute:
timer.setInterval(60000L, getSensorData); // get temp sensor every 60s
My function just updates the app:
void getSensorData() {
DS18B20.requestTemperatures();
temp = DS18B20.getTempCByIndex(0);
// If you don't have enough Blynk-Juice to afford the fancy Labeled Value ;)
float roundedValue = ceilf(temp * 100) / 100;
Blynk.virtualWrite(5, roundedValue);
}
Add some conditions in the function like if (temp > 22.5) { // Send IR cmd to start A/C } if (temp < 21.5) { // Send IR cmd to stop A/C }
Something like that will workā¦ I think.
(Pssst! If you are experimenting - RFM69 has a built in temp sensor )
Iām not keen on devices that have built-in temperature sensors as youāre almost certain to get some warming effect from the device itself. Also in a real world situation you could get some warming from the power supply, depending on how you power it.
This is why Iāve not implemented my system yet. I was waiting for some different sensors and some plastic cases to arrive, which I now have. The ESP (Iāll be using Wemos D1 Minis) willl be mounted in a small case and powered via 5v from a mains adaptor. The temperature/humidity sensor will be a BME280 (I donāt need the pressure sensor for the indoor sensors, but Iāll be using one of these in my outdoor weather station, so want to keep the same hardware throughout). The sensor will be mounted in a separate ventilated case that allows good airflow and connected via a length of wire to the Wemos, to avoid any possible heating effect.
The measured voltage has a linear relationship to the temperature as described in Table 24-2. The voltage sensitivity is approximately 1 mV/Ā°C and the accuracy of the temperature measurement is +/- 10Ā°C.
Good to know youāre working on a similar project as me. Iām using ESP-07 instead of Mini D1 or NodeMCU this time, mainly because of power consumption and external antenna connector, and I can also drill mounting holes on ESP āwhiteā board. My BMEās just arrived few days ago and this sensor is really, really good, way better than DHT family I previously experimented with. DHT reading time is 250ms on average and for this 250ms your mcu is dead, itās unusableā¦
Yes, my BMEās arrived about a week ago and Iām very impressed. The pressure reading was out by a couple of Kpa, but Iāve fixed that in the code and itās not something that Iām too worried about - Iām more interested in trends rather than absolute values but it would be nice if I could get a fairly accurate reading as Iād like to push some data to Weather Underground at some point.
Power consumption isnāt an issue for me as I wonāt be able to do deep sleep because Iām using interrupts on the wind speed and rainfall sensors.
Iām hopefully going to be able to use just one Wemos to measure:
Windspeed
Wind direction
Rainfall
Rain drop detection
Light level
Temperature
Pressure
Humidity
Iāve got the first three working together okay, and the last three working together as well. I just need to get all of the kit together in one place and see if one MCU can handle everything without losing accuracy.
I might be wrong, but I think itās like this: A reading might take ~250 ms, i.e. the first reading after start-up. The extra time is supposedly needed for the sensor to initialize correct. In the latest lib for DHT22, only 1 ms (18 ms for DHT11) is used for the wake-up call and and the data transfer takes about 5 ms. Thatās a total of 6 ms! Perhaps you just need to update your lib to make it go faster.
I have five DHT-22ās working in my home network, and the latency I got on mcu every time DHT sends itās readings is unacceptable. It might be up to library Iāve used, but now itās an old topic already, BME will be my choice in the future.
I think I found the culprit for the high latency! Since the sensors are very popular and widely used, others may find this to be of interest. If you Google DHT22, chances are youāll end up at Adafruitās homepage and consequently pick their library.
In the DHT.cpp from their library you find this:
`pinMode(_pin, INPUT_PULLUP);`
and
// Go into high impedence state to let pull-up raise data line level and
// start the reading process.
digitalWrite(_pin, HIGH);
delay(250);
This doesnāt make any sense! Itās an open drain bus and at idle it should already be HIGH, which is (normally) accomplished by using an external pull-up resistor. This is also how Adafruit wire the board on their online example. For this reason, the 250 ms delay is a complete waste of time as far as I can tell.
Also, the line should never actively be driven high when using open drain.