Compare commits
5 Commits
275c641ec8
...
875a7c0101
Author | SHA1 | Date |
---|---|---|
interfisch | 875a7c0101 | |
interfisch | 310fb73fba | |
interfisch | d45eddd707 | |
interfisch | 4a4faf68d4 | |
interfisch | da46dd1a77 |
|
@ -0,0 +1,68 @@
|
||||||
|
|
||||||
|
#include "sensor_anemometer.h"
|
||||||
|
|
||||||
|
//uses ATS177 Latched hall sensor for rotation sensing
|
||||||
|
|
||||||
|
Sensor_Anemometer::Sensor_Anemometer(int p)
|
||||||
|
{
|
||||||
|
pin=p;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Sensor_Anemometer::init() //Things to be done during setup()
|
||||||
|
{
|
||||||
|
pinMode(pin,INPUT_PULLUP);
|
||||||
|
attachInterrupt(digitalPinToInterrupt(pin),interrupt_anemometer,CHANGE); //anemometer interrupt
|
||||||
|
init_ok=true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//Also called during setup()
|
||||||
|
void Sensor_Anemometer::setSettings(float minchange, unsigned long senddelaymax, unsigned long readdelay)
|
||||||
|
{
|
||||||
|
data.minchange=minchange;
|
||||||
|
data.senddelaymax=senddelaymax;
|
||||||
|
data.readdelay=readdelay;
|
||||||
|
}
|
||||||
|
|
||||||
|
//Called during setup
|
||||||
|
void Sensor_Anemometer::advertise(HomieNode& p_sensorNode)
|
||||||
|
{
|
||||||
|
sensorNode = &p_sensorNode;
|
||||||
|
sensorNode->advertise("windspeed");
|
||||||
|
}
|
||||||
|
|
||||||
|
void Sensor_Anemometer::sensorloop()
|
||||||
|
{
|
||||||
|
if (init_ok) {
|
||||||
|
sensordata &d=data;
|
||||||
|
|
||||||
|
bool _changed=false;
|
||||||
|
if (millis() >= (d.lastreadtime+d.readdelay)) {
|
||||||
|
uint16_t _anepulsesPerMinute=anemometer_pulsecounter/((millis()-anemometer_lasttimereset)/60000.0);
|
||||||
|
d.value = _anepulsesPerMinute*SENSOR_ANEMOMETER_PPMtoMPS;
|
||||||
|
|
||||||
|
if (abs((int)d.lastsentvalue-d.value)>=d.minchange){ //int abs
|
||||||
|
_changed=true;
|
||||||
|
}
|
||||||
|
d.lastreadtime=millis();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_changed || millis() >= (d.lastsent+d.senddelaymax)) {
|
||||||
|
Serial.print("Sending windspeed. reason=");
|
||||||
|
if (_changed) Serial.println("change"); else Serial.println("time");
|
||||||
|
|
||||||
|
Homie.getLogger() << "windspeed tcs " << ": " << d.value << endl;
|
||||||
|
sensorNode->setProperty("windspeed").send(String(d.value));
|
||||||
|
|
||||||
|
//reset when sent. makes it more accurate but keeps fast response
|
||||||
|
anemometer_pulsecounter=0; //reset counter
|
||||||
|
anemometer_lasttimereset=millis();
|
||||||
|
d.lastreadtime=millis(); //also set lastread time to avoid having 1 count with a low time = high windspeed
|
||||||
|
|
||||||
|
d.lastsentvalue=d.value;
|
||||||
|
|
||||||
|
d.lastsent=millis();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,43 @@
|
||||||
|
#ifndef SENSOR_Anemometer_H
|
||||||
|
#define SENSOR_Anemometer_H
|
||||||
|
|
||||||
|
#include "sensordata.h"
|
||||||
|
#include <Homie.h>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
class Sensor_Anemometer
|
||||||
|
{
|
||||||
|
|
||||||
|
private:
|
||||||
|
HomieNode *sensorNode; //reference to HomieNode
|
||||||
|
|
||||||
|
int pin;
|
||||||
|
|
||||||
|
struct sensordata data; //struct values are changed in setup()
|
||||||
|
//value in [m/s]
|
||||||
|
|
||||||
|
bool init_ok;
|
||||||
|
|
||||||
|
unsigned long anemometer_lasttimereset=0;
|
||||||
|
|
||||||
|
|
||||||
|
#define ANEMOMETER_DEBOUNCETIME 15 //15ms between pulses is approx 85m/s windspeed
|
||||||
|
|
||||||
|
|
||||||
|
public:
|
||||||
|
Sensor_Anemometer(int p);
|
||||||
|
|
||||||
|
|
||||||
|
void init();
|
||||||
|
void setSettings(float minchange, unsigned long senddelaymax, unsigned long readdelay);
|
||||||
|
void advertise(HomieNode& p_sensorNode);
|
||||||
|
void sensorloop();
|
||||||
|
//void ICACHE_RAM_ATTR interrupt_anemometer();
|
||||||
|
|
||||||
|
uint16_t anemometer_pulsecounter=0; //counted pulses since last reset
|
||||||
|
unsigned long anemometer_lastpulse_fordebounce=0;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
|
@ -10,7 +10,6 @@
|
||||||
Sensor_HCSR501::Sensor_HCSR501(int pin)
|
Sensor_HCSR501::Sensor_HCSR501(int pin)
|
||||||
{
|
{
|
||||||
hcsr501pin=pin;
|
hcsr501pin=pin;
|
||||||
sensordata data;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sensor_HCSR501::init() //Things to be done during setup()
|
void Sensor_HCSR501::init() //Things to be done during setup()
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
Sensor_HS1101::Sensor_HS1101(int pin)
|
Sensor_HS1101::Sensor_HS1101(int pin)
|
||||||
{
|
{
|
||||||
hs1101pin=pin;
|
hs1101pin=pin;
|
||||||
struct sensordata data;
|
|
||||||
|
|
||||||
//out_humidity[] = {1000,900,800,700,600,500,400,300,200,100,0}; //*10, gets later devided by 10
|
//out_humidity[] = {1000,900,800,700,600,500,400,300,200,100,0}; //*10, gets later devided by 10
|
||||||
//in_hs1101frequency[] = {6033,6186,6330,6468,6600,6728,6853,6976,7100,7224,7351};
|
//in_hs1101frequency[] = {6033,6186,6330,6468,6600,6728,6853,6976,7100,7224,7351};
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
Sensor_LDR::Sensor_LDR(int p)
|
Sensor_LDR::Sensor_LDR(int p)
|
||||||
{
|
{
|
||||||
pin=p;
|
pin=p;
|
||||||
sensordata data;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sensor_LDR::init() //Things to be done during setup()
|
void Sensor_LDR::init() //Things to be done during setup()
|
||||||
|
|
|
@ -66,25 +66,7 @@ void Sensor_MHZ19B::setSettings(float minchange, unsigned long senddelaymax, uns
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
bool Sensor_MHZ19B::mhz19calibrationHandler(const HomieRange& range, const String& value) {
|
|
||||||
if (range.isRange) {
|
|
||||||
return false; //if range is given but index is not in allowed range
|
|
||||||
}
|
|
||||||
Homie.getLogger() << "mhz19 calibration " << ": " << value << endl;
|
|
||||||
|
|
||||||
if (value=="zero") {
|
|
||||||
mhz19->calibrateZero();
|
|
||||||
Homie.getLogger() << "mhz19 calibration " << ": " << value << endl;
|
|
||||||
#ifdef STATUSNODE
|
|
||||||
sensorNode->setProperty("status").send("MHZ19 Zero Calibration triggered");
|
|
||||||
#endif
|
|
||||||
} else {
|
|
||||||
Homie.getLogger() << "Value outside range" << endl;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
//Called during setup
|
//Called during setup
|
||||||
void Sensor_MHZ19B::advertise(HomieNode& p_sensorNode)
|
void Sensor_MHZ19B::advertise(HomieNode& p_sensorNode)
|
||||||
|
@ -92,7 +74,7 @@ void Sensor_MHZ19B::advertise(HomieNode& p_sensorNode)
|
||||||
sensorNode = &p_sensorNode;
|
sensorNode = &p_sensorNode;
|
||||||
sensorNode->advertise("co2");
|
sensorNode->advertise("co2");
|
||||||
#ifdef MHZ19CALIBRATIONTOPIC
|
#ifdef MHZ19CALIBRATIONTOPIC
|
||||||
sensorNode->advertise("mhz19calibration").settable(&Sensor_MHZ19B::mhz19calibrationHandler)); //not working!!! TODO: Fix it
|
sensorNode->advertise("mhz19calibration").settable(mhz19calibrationHandler);
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -169,4 +151,6 @@ int Sensor_MHZ19B::mhz19_readValue_reimplemented(Stream *_streamRef, MHZ19 *_mhz
|
||||||
return co2;
|
return co2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Sensor_MHZ19B::calibrateZero() {
|
||||||
|
mhz19->calibrateZero();
|
||||||
|
}
|
|
@ -33,7 +33,7 @@ private:
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//#define MHZ19CALIBRATIONTOPIC //TODO: fix it
|
#define MHZ19CALIBRATIONTOPIC
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Sensor_MHZ19B(int prx, int ptx);
|
Sensor_MHZ19B(int prx, int ptx);
|
||||||
|
@ -43,8 +43,7 @@ public:
|
||||||
void advertise(HomieNode& p_sensorNode);
|
void advertise(HomieNode& p_sensorNode);
|
||||||
void sensorloop();
|
void sensorloop();
|
||||||
|
|
||||||
bool mhz19calibrationHandler(const HomieRange& range, const String& value);
|
void calibrateZero();
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -6,7 +6,6 @@
|
||||||
Sensor_Radar::Sensor_Radar(int pin)
|
Sensor_Radar::Sensor_Radar(int pin)
|
||||||
{
|
{
|
||||||
radarpin=pin;
|
radarpin=pin;
|
||||||
sensordata data;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Sensor_Radar::init() //Things to be done during setup()
|
void Sensor_Radar::init() //Things to be done during setup()
|
||||||
|
|
|
@ -0,0 +1,81 @@
|
||||||
|
|
||||||
|
#include "sensor_raingauge.h"
|
||||||
|
|
||||||
|
//uses ATS177 Latched hall sensor for rotation sensing
|
||||||
|
|
||||||
|
Sensor_Raingauge::Sensor_Raingauge(int p)
|
||||||
|
{
|
||||||
|
pin=p;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Sensor_Raingauge::init() //Things to be done during setup()
|
||||||
|
{
|
||||||
|
init_ok=true;
|
||||||
|
|
||||||
|
pinMode(pin,INPUT_PULLUP);
|
||||||
|
attachInterrupt(digitalPinToInterrupt(pin),interrupt_raingauge,CHANGE); //anemometer interrupt
|
||||||
|
}
|
||||||
|
|
||||||
|
//Also called during setup()
|
||||||
|
void Sensor_Raingauge::setSettings(float minchange, unsigned long senddelaymax, unsigned long readdelay)
|
||||||
|
{
|
||||||
|
data.minchange=minchange;
|
||||||
|
data.senddelaymax=senddelaymax;
|
||||||
|
data.readdelay=readdelay;
|
||||||
|
}
|
||||||
|
|
||||||
|
//Called during setup
|
||||||
|
void Sensor_Raingauge::advertise(HomieNode& p_sensorNode)
|
||||||
|
{
|
||||||
|
sensorNode = &p_sensorNode;
|
||||||
|
sensorNode->advertise("rain");
|
||||||
|
}
|
||||||
|
|
||||||
|
void Sensor_Raingauge::sensorloop()
|
||||||
|
{
|
||||||
|
if (init_ok) {
|
||||||
|
sensordata &d=data;
|
||||||
|
|
||||||
|
bool _changed=false;
|
||||||
|
if (millis() >= (d.lastreadtime+d.readdelay)) {
|
||||||
|
|
||||||
|
if (millis()-raingauge_lasttimereset > d.senddelaymax) {
|
||||||
|
raingauge_idleflag=true; //raingauge didn't flip for a long time
|
||||||
|
}
|
||||||
|
if (raingauge_pulsecounter>0){ //if rg flipped
|
||||||
|
if (raingauge_idleflag) { //last flip is before reset time
|
||||||
|
d.value=raingauge_pulsecounter*RAINGAUGE_FLIPAMOUNT; //set to fixed amount if flip was exactly at that time
|
||||||
|
raingauge_idleflag=false;
|
||||||
|
}else{
|
||||||
|
d.value=3600000/(millis()-raingauge_lasttimereset)/raingauge_pulsecounter*RAINGAUGE_FLIPAMOUNT;
|
||||||
|
raingauge_idleflag=false;
|
||||||
|
}
|
||||||
|
_changed=true;
|
||||||
|
}
|
||||||
|
|
||||||
|
d.lastreadtime=millis();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_changed || millis() >= (d.lastsent+d.senddelaymax)) {
|
||||||
|
Serial.print("Sending rain. reason=");
|
||||||
|
if (_changed) Serial.println("change"); else Serial.println("time");
|
||||||
|
|
||||||
|
if (!_changed) { //no flip since a long time
|
||||||
|
d.value=0; //set to no rain
|
||||||
|
}
|
||||||
|
|
||||||
|
Homie.getLogger() << "rain " << ": " << d.value << endl;
|
||||||
|
sensorNode->setProperty("rain").send(String(d.value));
|
||||||
|
|
||||||
|
//reset when sent. makes it more accurate but keeps fast response
|
||||||
|
raingauge_pulsecounter=0; //reset counter
|
||||||
|
raingauge_lasttimereset=millis();
|
||||||
|
|
||||||
|
d.lastsentvalue=d.value;
|
||||||
|
|
||||||
|
d.lastsent=millis();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,54 @@
|
||||||
|
#ifndef SENSOR_Raingauge_H
|
||||||
|
#define SENSOR_Raingauge_H
|
||||||
|
|
||||||
|
#include "sensordata.h"
|
||||||
|
#include <Homie.h>
|
||||||
|
|
||||||
|
|
||||||
|
class Sensor_Raingauge
|
||||||
|
{
|
||||||
|
|
||||||
|
private:
|
||||||
|
HomieNode *sensorNode; //reference to HomieNode
|
||||||
|
|
||||||
|
int pin;
|
||||||
|
|
||||||
|
struct sensordata data; //struct values are changed in setup()
|
||||||
|
|
||||||
|
unsigned long raingauge_lasttimereset=0;
|
||||||
|
|
||||||
|
bool raingauge_idleflag=true;
|
||||||
|
|
||||||
|
#define RAINGAUGE_DEBOUNCETIME 1000
|
||||||
|
|
||||||
|
|
||||||
|
bool init_ok;
|
||||||
|
|
||||||
|
//value in [mm] or [L/m^2]
|
||||||
|
|
||||||
|
//#define RAINGAUGE_FLIPAMOUNT 0.38888 //how much mm rain (L/m^2) per gauge flip. mL (rain to flip) / A (opening area)
|
||||||
|
//was 0.69292 until 201702
|
||||||
|
/* Calibration:
|
||||||
|
* Test1: 1000mL -> 259 Flips
|
||||||
|
* Test2: 1000mL -> 256 in ca 10min
|
||||||
|
* -> 3,9mL per Flip, opening diameter =113mm -> A=0,010028749
|
||||||
|
*/
|
||||||
|
|
||||||
|
void updateRaingauge();
|
||||||
|
|
||||||
|
|
||||||
|
public:
|
||||||
|
Sensor_Raingauge(int p);
|
||||||
|
|
||||||
|
|
||||||
|
void init();
|
||||||
|
void setSettings(float minchange, unsigned long senddelaymax, unsigned long readdelay);
|
||||||
|
void advertise(HomieNode& p_sensorNode);
|
||||||
|
void sensorloop();
|
||||||
|
|
||||||
|
uint16_t raingauge_pulsecounter=0; //counted pulses since last reset
|
||||||
|
unsigned long raingauge_lastpulse_fordebounce=0;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
|
@ -51,17 +51,18 @@ build_flags =
|
||||||
-D SENSOR_ML8511_minchange=0.2
|
-D SENSOR_ML8511_minchange=0.2
|
||||||
|
|
||||||
-D SENSOR_ANEMOMETER
|
-D SENSOR_ANEMOMETER
|
||||||
-D ANEMOMETERPIN=D6 #Light Blue thicker cable (in distribution box)
|
-D SENSOR_Anemometer_PIN=D6 #Light Blue thicker cable (in distribution box)
|
||||||
-D dataAnemometer_minchange=0.25
|
-D SENSOR_Anemometer_minchange=0.25
|
||||||
-D dataAnemometer_readdelay=1000*30
|
-D SENSOR_Anemometer_readdelay=1000*30
|
||||||
-D dataAnemometer_senddelaymax=1000*60*5
|
-D SENSOR_Anemometer_senddelaymax=1000*60*5
|
||||||
-D ANEMOMETER_PPMtoMPS=0.0208640462
|
-D SENSOR_ANEMOMETER_PPMtoMPS=0.0208640462
|
||||||
# Cable from Anemometer: Black=GND, Blue=3v3, Brown=Signal (needs pullup (internal))
|
# Cable from Anemometer: Black=GND, Blue=3v3, Brown=Signal (needs pullup (internal))
|
||||||
|
|
||||||
-D SENSOR_RAINGAUGE
|
-D SENSOR_RAINGAUGE
|
||||||
-D RAINGAUGEPIN=D7
|
-D SENSOR_Raingauge_PIN=D7
|
||||||
-D dataRaingauge_readdelay=1000
|
-D RAINGAUGE_FLIPAMOUNT=0.38888
|
||||||
-D dataRaingauge_senddelaymax=1000*60*60 #also used for rain waiting timeout
|
-D SENSOR_Raingauge_readdelay=1000
|
||||||
|
-D SENSOR_Raingauge_senddelaymax=1000*60*60 #also used for rain waiting timeout
|
||||||
# Cable from Anemometer: Black=GND, Blue=3v3, Brown=Signal (needs pullup (internal))
|
# Cable from Anemometer: Black=GND, Blue=3v3, Brown=Signal (needs pullup (internal))
|
||||||
#Cable colors from anemometers sensor (before longer able): blue=gnd, brown=vcc, white=signal
|
#Cable colors from anemometers sensor (before longer able): blue=gnd, brown=vcc, white=signal
|
||||||
|
|
||||||
|
|
248
src/main.cpp
248
src/main.cpp
|
@ -21,6 +21,12 @@
|
||||||
|
|
||||||
#define STATUSNODE
|
#define STATUSNODE
|
||||||
|
|
||||||
|
|
||||||
|
// data/homie/config.json hochladen mit platformio run --target uploadfs
|
||||||
|
// config contains homie device name, mqtt ip and wifi credentials
|
||||||
|
|
||||||
|
HomieNode sensorNode("sensors", "Sensors","sensors"); //id, name, type
|
||||||
|
|
||||||
#include "sensordata.h"
|
#include "sensordata.h"
|
||||||
|
|
||||||
|
|
||||||
|
@ -189,9 +195,30 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_MHZ19B
|
#ifdef SENSOR_MHZ19B
|
||||||
|
bool mhz19calibrationHandler(const HomieRange& range, const String& value);
|
||||||
#include "sensor_mhz19b.cpp"
|
#include "sensor_mhz19b.cpp"
|
||||||
Sensor_MHZ19B sensor_mhz19b(SENSOR_MHZ19B_SERIAL_RX,SENSOR_MHZ19B_SERIAL_TX);
|
Sensor_MHZ19B sensor_mhz19b(SENSOR_MHZ19B_SERIAL_RX,SENSOR_MHZ19B_SERIAL_TX);
|
||||||
|
|
||||||
|
bool mhz19calibrationHandler(const HomieRange& range, const String& value) {
|
||||||
|
if (range.isRange) {
|
||||||
|
return false; //if range is given but index is not in allowed range
|
||||||
|
}
|
||||||
|
Homie.getLogger() << "mhz19 calibration " << ": " << value << endl;
|
||||||
|
|
||||||
|
if (value=="zero") {
|
||||||
|
sensor_mhz19b.calibrateZero();//mhz19->calibrateZero();
|
||||||
|
Homie.getLogger() << "mhz19 calibration " << ": " << value << endl;
|
||||||
|
#ifdef STATUSNODE
|
||||||
|
sensorNode.setProperty("status").send("MHZ19 Zero Calibration triggered");
|
||||||
|
#endif
|
||||||
|
} else {
|
||||||
|
Homie.getLogger() << "Value outside range" << endl;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
#ifndef SENSOR_MHZ19B_minchange
|
#ifndef SENSOR_MHZ19B_minchange
|
||||||
#define SENSOR_MHZ19B_minchange 10.0
|
#define SENSOR_MHZ19B_minchange 10.0
|
||||||
#endif
|
#endif
|
||||||
|
@ -265,50 +292,58 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
#ifdef SENSOR_ANEMOMETER
|
||||||
//uses ATS177 Latched hall sensor for rotation sensing
|
|
||||||
sensordata dataAnemometer;
|
|
||||||
unsigned long anemometer_lasttimereset=0;
|
|
||||||
uint16_t anemometer_pulsecounter=0; //counted pulses since last reset
|
|
||||||
|
|
||||||
#define ANEMOMETER_DEBOUNCETIME 15 //15ms between pulses is approx 85m/s windspeed
|
|
||||||
unsigned long anemometer_lastpulse_fordebounce=0;
|
|
||||||
|
|
||||||
float value_anemometer=0; // [m/s]
|
|
||||||
|
|
||||||
void ICACHE_RAM_ATTR interrupt_anemometer();
|
void ICACHE_RAM_ATTR interrupt_anemometer();
|
||||||
void updateAnemometer();
|
#include "sensor_anemometer.cpp"
|
||||||
|
//Sensor_Anemometer_Instance = new Sensor_Anemometer(SENSOR_Anemometer_PIN);
|
||||||
|
Sensor_Anemometer sensor_anemometer(SENSOR_Anemometer_PIN);
|
||||||
|
|
||||||
|
|
||||||
|
void ICACHE_RAM_ATTR interrupt_anemometer()
|
||||||
|
{
|
||||||
|
if (millis() - sensor_anemometer.anemometer_lastpulse_fordebounce >= ANEMOMETER_DEBOUNCETIME) { //ignore if pulse came too fast
|
||||||
|
sensor_anemometer.anemometer_pulsecounter++;
|
||||||
|
sensor_anemometer.anemometer_lastpulse_fordebounce=millis();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef SENSOR_Anemometer_minchange
|
||||||
|
#define SENSOR_Anemometer_minchange 0.25
|
||||||
|
#endif
|
||||||
|
#ifndef SENSOR_Anemometer_senddelaymax
|
||||||
|
#define SENSOR_Anemometer_senddelaymax 1000*60*5
|
||||||
|
#endif
|
||||||
|
#ifndef SENSOR_Anemometer_readdelay
|
||||||
|
#define SENSOR_Anemometer_readdelay 1000*30
|
||||||
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
#ifdef SENSOR_RAINGAUGE
|
||||||
//uses ATS177 Latched Hall Sensor for rauge flip sensing
|
//uses ATS177 Latched Hall Sensor for rauge flip sensing
|
||||||
sensordata dataRaingauge;
|
|
||||||
unsigned long raingauge_lasttimereset=0;
|
|
||||||
uint16_t raingauge_pulsecounter=0; //counted pulses since last reset
|
|
||||||
bool raingauge_idleflag=true;
|
|
||||||
|
|
||||||
#define RAINGAUGE_DEBOUNCETIME 1000
|
|
||||||
unsigned long raingauge_lastpulse_fordebounce=0;
|
|
||||||
|
|
||||||
float value_raingauge=0; // [mm] or [L/m^2]
|
|
||||||
|
|
||||||
#define RAINGAUGE_FLIPAMOUNT 0.38888 //how much mm rain (L/m^2) per gauge flip. mL (rain to flip) / A (opening area)
|
|
||||||
//was 0.69292 until 201702
|
|
||||||
/* Calibration:
|
|
||||||
* Test1: 1000mL -> 259 Flips
|
|
||||||
* Test2: 1000mL -> 256 in ca 10min
|
|
||||||
* -> 3,9mL per Flip, opening diameter =113mm -> A=0,010028749
|
|
||||||
*/
|
|
||||||
|
|
||||||
void ICACHE_RAM_ATTR interrupt_raingauge();
|
void ICACHE_RAM_ATTR interrupt_raingauge();
|
||||||
void updateRaingauge();
|
#include "sensor_raingauge.cpp"
|
||||||
|
|
||||||
|
Sensor_Raingauge sensor_raingauge(SENSOR_Raingauge_PIN);
|
||||||
|
|
||||||
|
void ICACHE_RAM_ATTR interrupt_raingauge()
|
||||||
|
{
|
||||||
|
if (millis() - sensor_raingauge.raingauge_lastpulse_fordebounce >= RAINGAUGE_DEBOUNCETIME) { //ignore if pulse came too fast
|
||||||
|
sensor_raingauge.raingauge_pulsecounter++;
|
||||||
|
sensor_raingauge.raingauge_lastpulse_fordebounce=millis();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifndef SENSOR_Raingauge_minchange
|
||||||
|
#define SENSOR_Raingauge_minchange 0
|
||||||
|
#endif
|
||||||
|
#ifndef SENSOR_Raingauge_senddelaymax
|
||||||
|
#define SENSOR_Raingauge_senddelaymax 1000*60*60
|
||||||
|
#endif
|
||||||
|
#ifndef SENSOR_Raingauge_readdelay
|
||||||
|
#define SENSOR_Raingauge_readdelay 1000
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// data/homie/config.json hochladen mit platformio run --target uploadfs
|
|
||||||
// config contains homie device name, mqtt ip and wifi credentials
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
HomieNode sensorNode("sensors", "Sensors","sensors"); //id, name, type
|
|
||||||
|
|
||||||
char tempstring[16]; //for dtostrf
|
char tempstring[16]; //for dtostrf
|
||||||
|
|
||||||
|
@ -401,28 +436,13 @@ void setup() {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
#ifdef SENSOR_ANEMOMETER
|
||||||
pinMode(ANEMOMETERPIN,INPUT_PULLUP);
|
sensor_anemometer.init();
|
||||||
attachInterrupt(digitalPinToInterrupt(ANEMOMETERPIN),interrupt_anemometer,CHANGE); //anemometer interrupt
|
sensor_anemometer.setSettings(SENSOR_Anemometer_minchange,SENSOR_Anemometer_senddelaymax,SENSOR_Anemometer_readdelay);
|
||||||
#ifdef dataAnemometer_minchange
|
|
||||||
dataAnemometer.minchange=dataAnemometer_minchange;
|
|
||||||
#endif
|
|
||||||
#ifdef dataAnemometer_readdelay
|
|
||||||
dataAnemometer.readdelay=dataAnemometer_readdelay;
|
|
||||||
#endif
|
|
||||||
#ifdef dataAnemometer_senddelaymax
|
|
||||||
dataAnemometer.senddelaymax=dataAnemometer_senddelaymax;
|
|
||||||
#endif
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
#ifdef SENSOR_RAINGAUGE
|
||||||
pinMode(RAINGAUGEPIN,INPUT_PULLUP);
|
sensor_raingauge.init();
|
||||||
attachInterrupt(digitalPinToInterrupt(RAINGAUGEPIN),interrupt_raingauge,CHANGE); //anemometer interrupt
|
sensor_raingauge.setSettings(SENSOR_Raingauge_minchange,SENSOR_Raingauge_senddelaymax,SENSOR_Raingauge_readdelay);
|
||||||
#ifdef dataRaingauge_senddelaymax
|
|
||||||
dataRaingauge.senddelaymax=dataRaingauge_senddelaymax;
|
|
||||||
#endif
|
|
||||||
#ifdef dataRaingauge_readdelay
|
|
||||||
dataRaingauge.readdelay=dataRaingauge_readdelay;
|
|
||||||
#endif
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
@ -493,11 +513,11 @@ void setup() {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
#ifdef SENSOR_ANEMOMETER
|
||||||
sensorNode.advertise("windspeed");
|
sensor_anemometer.advertise(sensorNode);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
#ifdef SENSOR_RAINGAUGE
|
||||||
sensorNode.advertise("rain");
|
sensor_raingauge.advertise(sensorNode);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
@ -512,91 +532,6 @@ void loop() {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
|
||||||
void loop_anemometer()
|
|
||||||
{
|
|
||||||
sensordata &d=dataAnemometer;
|
|
||||||
|
|
||||||
bool _changed=false;
|
|
||||||
if (millis() >= (d.lastreadtime+d.readdelay)) {
|
|
||||||
uint16_t _anepulsesPerMinute=anemometer_pulsecounter/((millis()-anemometer_lasttimereset)/60000.0);
|
|
||||||
value_anemometer = _anepulsesPerMinute*ANEMOMETER_PPMtoMPS;
|
|
||||||
|
|
||||||
if (abs((int)d.lastsentvalue-value_anemometer)>=d.minchange){ //int abs
|
|
||||||
_changed=true;
|
|
||||||
}
|
|
||||||
d.lastreadtime=millis();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_changed || millis() >= (d.lastsent+d.senddelaymax)) {
|
|
||||||
Serial.print("Sending windspeed. reason=");
|
|
||||||
if (_changed) Serial.println("change"); else Serial.println("time");
|
|
||||||
checkESPStatus();
|
|
||||||
|
|
||||||
Homie.getLogger() << "windspeed tcs " << ": " << value_anemometer << endl;
|
|
||||||
sensorNode.setProperty("windspeed").send(String(value_anemometer));
|
|
||||||
|
|
||||||
//reset when sent. makes it more accurate but keeps fast response
|
|
||||||
anemometer_pulsecounter=0; //reset counter
|
|
||||||
anemometer_lasttimereset=millis();
|
|
||||||
d.lastreadtime=millis(); //also set lastread time to avoid having 1 count with a low time = high windspeed
|
|
||||||
|
|
||||||
d.lastsentvalue=value_anemometer;
|
|
||||||
|
|
||||||
d.lastsent=millis();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
|
||||||
void loop_raingauge()
|
|
||||||
{
|
|
||||||
sensordata &d=dataRaingauge;
|
|
||||||
|
|
||||||
bool _changed=false;
|
|
||||||
if (millis() >= (d.lastreadtime+d.readdelay)) {
|
|
||||||
|
|
||||||
if (millis()-raingauge_lasttimereset > d.senddelaymax) {
|
|
||||||
raingauge_idleflag=true; //raingauge didn't flip for a long time
|
|
||||||
}
|
|
||||||
if (raingauge_pulsecounter>0){ //if rg flipped
|
|
||||||
if (raingauge_idleflag) { //last flip is before reset time
|
|
||||||
value_raingauge=raingauge_pulsecounter*RAINGAUGE_FLIPAMOUNT; //set to fixed amount if flip was exactly at that time
|
|
||||||
raingauge_idleflag=false;
|
|
||||||
}else{
|
|
||||||
value_raingauge=3600000/(millis()-raingauge_lasttimereset)/raingauge_pulsecounter*RAINGAUGE_FLIPAMOUNT;
|
|
||||||
raingauge_idleflag=false;
|
|
||||||
}
|
|
||||||
_changed=true;
|
|
||||||
}
|
|
||||||
|
|
||||||
d.lastreadtime=millis();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_changed || millis() >= (d.lastsent+d.senddelaymax)) {
|
|
||||||
Serial.print("Sending rain. reason=");
|
|
||||||
if (_changed) Serial.println("change"); else Serial.println("time");
|
|
||||||
checkESPStatus();
|
|
||||||
|
|
||||||
if (!_changed) { //no flip since a long time
|
|
||||||
value_raingauge=0; //set to no rain
|
|
||||||
}
|
|
||||||
|
|
||||||
Homie.getLogger() << "rain " << ": " << value_raingauge << endl;
|
|
||||||
sensorNode.setProperty("rain").send(String(value_raingauge));
|
|
||||||
|
|
||||||
//reset when sent. makes it more accurate but keeps fast response
|
|
||||||
raingauge_pulsecounter=0; //reset counter
|
|
||||||
raingauge_lasttimereset=millis();
|
|
||||||
|
|
||||||
d.lastsentvalue=value_raingauge;
|
|
||||||
|
|
||||||
d.lastsent=millis();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void loopHandler() {
|
void loopHandler() {
|
||||||
checkESPStatus();
|
checkESPStatus();
|
||||||
|
@ -654,11 +589,11 @@ void loopHandler() {
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
#ifdef SENSOR_ANEMOMETER
|
||||||
loop_anemometer();
|
sensor_anemometer.sensorloop();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
#ifdef SENSOR_RAINGAUGE
|
||||||
loop_raingauge();
|
sensor_raingauge.sensorloop();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -673,31 +608,6 @@ void checkESPStatus()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#ifdef SENSOR_ANEMOMETER
|
|
||||||
void ICACHE_RAM_ATTR interrupt_anemometer()
|
|
||||||
{
|
|
||||||
if (millis() - anemometer_lastpulse_fordebounce >= ANEMOMETER_DEBOUNCETIME) { //ignore if pulse came too fast
|
|
||||||
anemometer_pulsecounter++;
|
|
||||||
anemometer_lastpulse_fordebounce=millis();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef SENSOR_RAINGAUGE
|
|
||||||
void ICACHE_RAM_ATTR interrupt_raingauge()
|
|
||||||
{
|
|
||||||
if (millis() - raingauge_lastpulse_fordebounce >= RAINGAUGE_DEBOUNCETIME) { //ignore if pulse came too fast
|
|
||||||
raingauge_pulsecounter++;
|
|
||||||
raingauge_lastpulse_fordebounce=millis();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*##################################
|
/*##################################
|
||||||
* ######## HELPER FUNCTIONS ########
|
* ######## HELPER FUNCTIONS ########
|
||||||
*/
|
*/
|
||||||
|
|
Loading…
Reference in New Issue