gw send, how to do in my combination of sensors
-
In my project in development, I miss the GW send for my motion detector. I tried several options but nothing works. Anyone an idea, how to?
#include <MySensor.h> #include <SPI.h> #include "Bounce2.h" #define USE_MOTION_SENSOR #define MOTION_SENSOR_PIN 3 //physical number of PIR #define LIGHT_SENSOR_ANALOG_PIN A0 //physical number of LDR #define CHILD_ID_LIGHT 6 #define RELAY_ON 0 // switch around for realy HIGH/LOW state #define RELAY_OFF 1 Bounce motionsDebouncer = Bounce(); MySensor gw; #define RADIO_ID 11 // radio Id, whatever channel you assigned to #define noRelays 5 //number of relais in use const int relayPin[] = {A1, A2, A3, A4, A5}; // switch around pins to your desire number of relais const int buttonPin[] = {4, 5, 6, 7, 8 }; // switch around pins to your desire number of buttons class Relay // relay class, store all relevant data (equivalent to struct) { public: int buttonPin; // physical pin number of button int relayPin; // physical pin number of relay byte oldValue; // last Values for key (debounce) boolean relayState; // relay status (also stored in EEPROM) }; Relay Relays[noRelays]; Bounce debouncer[noRelays]; MyMessage msgRelay[noRelays]; MyMessage msgLDR(CHILD_ID_LIGHT, V_LIGHT_LEVEL); int lastLightLevel; unsigned long SLEEP_TIME = 6000; // Sleep time between reads (in milliseconds) void setup() { gw.begin(incomingMessage, RADIO_ID, true); delay(250); gw.sendSketchInfo("Multy-Relay&button-PIR&LDR", "0.2"); delay(250); gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL); pinMode( MOTION_SENSOR_PIN, INPUT_PULLUP ); motionsDebouncer.attach(MOTION_SENSOR_PIN); motionsDebouncer.interval(50); // Initialize Relays with corresponding buttons for (int i = 0; i < noRelays; i++) { Relays[i].buttonPin = buttonPin[i]; // assign physical pins Relays[i].relayPin = relayPin[i]; msgRelay[i].sensor = i; // initialize messages msgRelay[i].type = V_LIGHT; debouncer[i] = Bounce(); // initialize debouncer debouncer[i].attach(buttonPin[i]); debouncer[i].interval(5); pinMode(Relays[i].buttonPin, INPUT_PULLUP); pinMode(Relays[i].relayPin, OUTPUT); Relays[i].relayState = gw.loadState(i); // retrieve last values from EEPROM digitalWrite(Relays[i].relayPin, Relays[i].relayState ? RELAY_ON : RELAY_OFF); // and set relays accordingly gw.send(msgRelay[i].set(Relays[i].relayState ? true : false)); // make controller aware of last status gw.present(i, S_LIGHT); // present sensor to gateway delay(250); } } void loop() { if ( motionsDebouncer.update()) { int value = motionsDebouncer.read(); Serial.println( "PIR " + (String)value ); } { gw.process(); for (byte i = 0; i < noRelays; i++) { debouncer[i].update(); byte value = debouncer[i].read(); if (value != Relays[i].oldValue && value == 0) { Relays[i].relayState = !Relays[i].relayState; digitalWrite(Relays[i].relayPin, Relays[i].relayState ? RELAY_ON : RELAY_OFF); gw.send(msgRelay[i].set(Relays[i].relayState ? true : false)); gw.saveState( i, Relays[i].relayState ); } // save sensor state in EEPROM (location == sensor number) Relays[i].oldValue = value; } int lightLevel = (1023-analogRead(LIGHT_SENSOR_ANALOG_PIN))/10.23; //Serial.println(LDR); if ((lightLevel > 1.05 * lastLightLevel)||(lightLevel < 0.95 * lastLightLevel)) //5% difference will send { gw.send(msgLDR.set(lightLevel)); lastLightLevel = lightLevel; Serial.print("LDR"); Serial.println(lightLevel); } } } // process incoming message void incomingMessage(const MyMessage &message) { if (message.type == V_LIGHT) { if (message.sensor < noRelays) // check if message is valid for relays..... previous line [[[ if (message.sensor <=noRelays){ ]]] { Relays[message.sensor].relayState = message.getBool(); digitalWrite(Relays[message.sensor].relayPin, Relays[message.sensor].relayState ? RELAY_ON : RELAY_OFF); // and set relays accordingly gw.saveState( message.sensor, Relays[message.sensor].relayState ); // save sensor state in EEPROM (location == sensor number) } } // delay( 50 ); // give the input pins some rest. Incomming messages are still being processed. gw.wait(50); }
-
@Dick I assume you are working on a version < 2.0.0. if I look at your sketch??
-
not yet, stil working with the 1.54. in the IDE serial it works all fine but the motion sensor is not visible in DOMOTICZ and probably because I do not send to GW but I am new in this area so support is welcome.
-
@Dick have you looked at the motion example? https://www.mysensors.org/build/motion
-
@mfalkvidd
Yes I did bud than I do not understand what I have now,if ( motionsDebouncer.update()) { int value = motionsDebouncer.read(); Serial.println( "PIR " + (String)value );``` only a GW send row needed or is that not right? What I saw on the https://www.mysensors.org/build/motion was clear but after implementation I got several errors during the compilation so I thought, perhaps only something with GW.send Or am I wrong?
-
@Dick added some comments in the code. And made some changes. It compiles. But I can't test it for you..
#include <MySensor.h> #include <SPI.h> #include "Bounce2.h" #define USE_MOTION_SENSOR #define MOTION_SENSOR_PIN 3 //physical number of PIR #define LIGHT_SENSOR_ANALOG_PIN A0 //physical number of LDR #define CHILD_ID_LIGHT 6 #define RELAY_ON 0 // switch around for realy HIGH/LOW state #define RELAY_OFF 1 Bounce motionsDebouncer = Bounce(); MySensor gw; #define RADIO_ID 11 // radio Id, whatever channel you assigned to #define noRelays 5 //number of relais in use const int relayPin[] = {A1, A2, A3, A4, A5}; // switch around pins to your desire number of relais const int buttonPin[] = {4, 5, 6, 7, 8 }; // switch around pins to your desire number of buttons // <-- byTheo since you don't have any methods in your class, a simple C struct made be // more resource friendly class Relay // relay class, store all relevant data (equivalent to struct) { public: int buttonPin; // physical pin number of button int relayPin; // physical pin number of relay byte oldValue; // last Values for key (debounce) boolean relayState; // relay status (also stored in EEPROM) }; Relay Relays[noRelays]; Bounce debouncer[noRelays]; MyMessage msgRelay[noRelays]; MyMessage msgLDR(CHILD_ID_LIGHT, V_LIGHT_LEVEL); #define MOTION_CHILD_ID 8 // <-- byTheo MyMessage motionMsg( MOTION_CHILD_ID, V_TRIPPED ); // <-- byTheo int lastLightLevel; unsigned long SLEEP_TIME = 6000; // Sleep time between reads (in milliseconds) void setup() { gw.begin(incomingMessage, RADIO_ID, true); // delay(250); // <-- byTheo gw.wait( 250 ); // <-- byTheo gw.sendSketchInfo("Multy-Relay&button-PIR&LDR", "0.2"); // delay(250); // <-- byTheo gw.wait( 250 ); // <-- byTheo gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL); pinMode( MOTION_SENSOR_PIN, INPUT_PULLUP ); motionsDebouncer.attach(MOTION_SENSOR_PIN); // <---- byTheo I believe PIR sensors don't need debouncing motionsDebouncer.interval(50); // <---- byTheo I believe PIR sensors don't need debouncing // Initialize Relays with corresponding buttons for (int i = 0; i < noRelays; i++) { Relays[i].buttonPin = buttonPin[i]; // assign physical pins Relays[i].relayPin = relayPin[i]; msgRelay[i].sensor = i; // initialize messages msgRelay[i].type = V_LIGHT; debouncer[i] = Bounce(); // initialize debouncer debouncer[i].attach(buttonPin[i]); debouncer[i].interval(5); pinMode(Relays[i].buttonPin, INPUT_PULLUP); pinMode(Relays[i].relayPin, OUTPUT); Relays[i].relayState = gw.loadState(i); // retrieve last values from EEPROM digitalWrite(Relays[i].relayPin, Relays[i].relayState ? RELAY_ON : RELAY_OFF); // and set relays accordingly gw.send(msgRelay[i].set(Relays[i].relayState ? true : false)); // make controller aware of last status gw.present(i, S_LIGHT); // present sensor to gateway // delay(250); // <-- byTheo gw.wait( 250 ); // <-- byTheo } gw.present( MOTION_CHILD_ID, S_MOTION, "Motion needs presentation", true ); // byTheo gw.wait( 250 ); // <-- byTheo } void loop() { if ( motionsDebouncer.update()) { int value = motionsDebouncer.read(); Serial.println( "PIR " + (String)value ); gw.send( motionMsg.set( value ), true ); // <-- byTheo : Also it might need inverted value } // { <--- byTheo gw.process(); for (byte i = 0; i < noRelays; i++) { debouncer[i].update(); byte value = debouncer[i].read(); if (value != Relays[i].oldValue && value == 0) { Relays[i].relayState = !Relays[i].relayState; digitalWrite(Relays[i].relayPin, Relays[i].relayState ? RELAY_ON : RELAY_OFF); gw.send(msgRelay[i].set(Relays[i].relayState ? true : false)); gw.saveState( i, Relays[i].relayState ); } // save sensor state in EEPROM (location == sensor number) Relays[i].oldValue = value; } int lightLevel = (1023 - analogRead(LIGHT_SENSOR_ANALOG_PIN)) / 10.23; //Serial.println(LDR); if ((lightLevel > 1.05 * lastLightLevel) || (lightLevel < 0.95 * lastLightLevel)) //5% difference will send { gw.send(msgLDR.set(lightLevel)); lastLightLevel = lightLevel; Serial.print("LDR"); Serial.println(lightLevel); } // } // <---- byTheo } // process incoming message void incomingMessage(const MyMessage &message) { if (message.type == V_LIGHT) { if (message.sensor < noRelays) // check if message is valid for relays..... previous line [[[ if (message.sensor <=noRelays){ ]]] { Relays[message.sensor].relayState = message.getBool(); digitalWrite(Relays[message.sensor].relayPin, Relays[message.sensor].relayState ? RELAY_ON : RELAY_OFF); // and set relays accordingly gw.saveState( message.sensor, Relays[message.sensor].relayState ); // save sensor state in EEPROM (location == sensor number) } } // delay( 50 ); // give the input pins some rest. Incomming messages are still being processed. // gw.wait(50); // <-- byTheo don't use delays in message handler. Message handler needs the shortest execution time is possible }
-
@TheoL
Hi Theo, the devil is playing with me, my PI stopped working and that is my Domoticz location. I read your commend, thank you for that, I am probably not able to test it this evening.
sorry for that> I inform you about the results.
-
Hello @Dick,
Don't be sorry. Just let me know if this is what you wanted after you've tested it.
-
@TheoL My Domoticz works again, I have to give it a fix ip because the IP was change and for your info, Your solution worked very well. It is now visible in Domoticz. Thanks for the support now I have to wait for other parts, I wait for my last parts for this project, an IR receiver so I can use a remote controle. After that I can use this project as a universal project, a default design in basic.
Again thanks!