Multisensor PIR problem [solved]



  • Hey Folks,

    i have some problems with my battery powered arduino mini.

    When i use my sketch, the PIR doesn't signal present right. Only sometime i get a signal.

    https://github.com/n3roGit/MySensors_n3ro/tree/master/MotionSensor_DHT_light_battery_mod

    But when i use this (simple) sketch with only PIR it works like charm.

    https://github.com/n3roGit/Arduino-home-automation/tree/master/2.4Ghz (MySensors)/Arduino/PirSleepBattery

    Any ideas whats wrong?

    Regards,
    n3ro



  • " delay(dht.getMinimumSamplingPeriod());" is the problem - it delays whole sketch every run of loop()



  • PERFECT!!!!!!!!!!! It works now :):):)

    Big THX!



  • @andriej hey,

    the PIR works perfect now, but the DHT didnt update... Only the first startup of the arduino works:

    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:20.5
    ---------- Temp: 20.50
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=ok:34.6
    ---------- Humidity: 34.60
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:87
    ---------- Light: 87
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:84
    ---------- Light: 84
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:88
    ---------- Light: 88
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:83
    ---------- Light: 83
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:87
    ---------- Light: 87
    ---------- Battery: 100
    ---------- PIR: 1


  • Hero Member

    @n3ro the DHT needs a delay between polling. You are likely polling it too fast now. Rather than remove the delay command, you need to use a different method to not poll the DHT too frequently. The millis command is one option: http://www.arduino.cc/en/Tutorial/BlinkWithoutDelay

    Cheers
    Al



  • ufff. to build a multisensor sketch is really hard 😕

    thx for your info!



  • can somebody help me with my sketch? i dont understand millis 😕


  • Hero Member

    @n3ro Hard to help you with your sketch since you don't have it posted 😉





  • Hi ! I had the same problem. Seems like gw.sleep(some_number_of_mills); lets you loose the init of the dht. Just put dht.begin(); in your loop before you read the value and it should work.

    example.
    void loop ()
    {
    dht.begin();
    float temperature = dht.readTemperature();
    ......



  • @torfinn said:

    dht.begin();

    Hey torfinn,

    i get this error when compiling:
    MotionSensor_DHT_light_battery_mod.ino: In function 'void loop()':
    MotionSensor_DHT_light_battery_mod.ino:109:7: error: 'class DHT' has no member named 'begin'
    Fehler beim Kompilieren.



  • I have a idea,

    is it possible to build a second loop like this?
    But now i have one problem... the loop2 never run...

    #include <MySensor.h>
    #include <readVcc.h>
    #include <SPI.h>
    #include <DHT.h>
    
    #include <Scheduler.h>
    
    
    
    
    #define NODE_ID 11                       // ID of node
    unsigned long SLEEP_TIME = 600000;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    int oldBatteryPcnt;
    int lastLightLevel;
    unsigned long time;
    
    
    int MIN_V = 2700; // empty voltage (0%)
    int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
    
      //PIR
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode(PIR_SENSOR_DIGITAL, INPUT);      // sets the motion sensor digital pin as input
      digitalWrite(PIR_SENSOR_DIGITAL, HIGH);
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_PIR, S_MOTION);
    
      //DHT
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
    
      // Send the Sketch Version Information to the Gateway
      gw.sendSketchInfo("Humidity", "1.0");
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
    
      metric = gw.getConfig().isMetric;
    
      //LIGHT
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Light Sensor", "1.0");
    
      // Register all sensors to gateway (they will be created as child devices)
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
      
      Scheduler.startLoop(loop2);
    
    }
    
    void loop()
    {
      // Read digital motion value
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0")); // Send tripped value to gw
    
      // Sleep until interrupt comes in on motion sensor. Send update every two minute.
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    }
    void loop2()
    {
      //DHT
      //dht.begin();
      delay(dht.getMinimumSamplingPeriod());
      //delay(1000);
      //millis(dht.getMinimumSamplingPeriod());
      //Serial.print(dht.getMinimumSamplingPeriod());
    
      float temperature = dht.getTemperature();
      if (isnan(temperature)) {
        Serial.println("Failed reading temperature from DHT");
      } else if (temperature != lastTemp) {
        lastTemp = temperature;
        if (!metric) {
          temperature = dht.toFahrenheit(temperature);
        }
        gw.send(msgTemp.set(temperature, 1));
        Serial.print("---------- Temp: ");
        Serial.println(temperature);
      }
    
      float humidity = dht.getHumidity();
      if (isnan(humidity)) {
        Serial.println("Failed reading humidity from DHT");
      } else if (humidity != lastHum) {
        lastHum = humidity;
        gw.send(msgHum.set(humidity, 1));
        Serial.print("---------- Humidity: ");
        Serial.println(humidity);
      }
    
      // Light
      int lightLevel = (1023 - analogRead(LIGHT_SENSOR_ANALOG_PIN)) / 10.23;
      //Serial.println(lightLevel);
      if (lightLevel != lastLightLevel) {
        gw.send(msgLight.set(lightLevel));
        lastLightLevel = lightLevel;
        Serial.print("---------- Light: ");
        Serial.println(lightLevel);
      }
    
      // Measure battery
      float batteryV = readVcc();
      int batteryPcnt = (((batteryV - MIN_V) / (MAX_V - MIN_V)) * 100 );
      if (batteryPcnt > 100) {
        batteryPcnt = 100;
      }
    
      if (batteryPcnt != oldBatteryPcnt) {
        gw.sendBatteryLevel(batteryPcnt); // Send battery percentage
        oldBatteryPcnt = batteryPcnt;
      }
      Serial.print("---------- Battery: ");
      Serial.println(batteryPcnt);
      gw.sleep(SLEEP_TIME);
    }
    

    i have downloaded THIS

    But i get this error when compiling:

    In file included from MotionSensor_DHT_light_battery_mod.ino:6:0:
    Arduino\libraries\Scheduler/Scheduler.h:33:22: fatal error: WProgram.h: No such file or directory
    #include <WProgram.h>


  • Hero Member

    @n3ro , you can have only one loop().

    You need to merge the two logics into into a single loop. You might also want to remove the second sleep, otherwise PIR will not trigger there.



  • @rvendrame do you have an idea how to do it?


  • Hero Member

    Maybe you can start by to removing these 3 lines:

    }
    void loop2()
    {
    
    

    ... and move the 1st sleep to the end of loop (where the 2nd sleep is):

    // Sleep until interrupt comes in on motion sensor. Send update every two minute.
     gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    
    

    .... and remove the 2nd sleep:

    gw.sleep(SLEEP_TIME);
    


  • @rvendrame
    if i use this:

    #include <MySensor.h>
    #include <readVcc.h>
    #include <SPI.h>
    #include <DHT.h>
    
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 600000;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    int oldBatteryPcnt;
    int lastLightLevel;
    
    
    int MIN_V = 2700; // empty voltage (0%)
    int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
    
      //PIR
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode(PIR_SENSOR_DIGITAL, INPUT);      // sets the motion sensor digital pin as input
      digitalWrite(PIR_SENSOR_DIGITAL, HIGH);
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_PIR, S_MOTION);
      
      //DHT
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
    
      // Send the Sketch Version Information to the Gateway
      gw.sendSketchInfo("Humidity", "1.0");
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
    
      metric = gw.getConfig().isMetric;
      
      //LIGHT
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Light Sensor", "1.0");
    
      // Register all sensors to gateway (they will be created as child devices)
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    
    }
    
    void loop()
    {
    
      // Measure battery
      float batteryV = readVcc();
      int batteryPcnt = (((batteryV - MIN_V) / (MAX_V - MIN_V)) * 100 );
      if (batteryPcnt > 100) {
        batteryPcnt = 100;
      }
    
      if (batteryPcnt != oldBatteryPcnt) {
        gw.sendBatteryLevel(batteryPcnt); // Send battery percentage
        oldBatteryPcnt = batteryPcnt;
      }
      Serial.print("---------- Battery: ");
      Serial.println(batteryPcnt);
    
      // Read digital motion value
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0")); // Send tripped value to gw
    
    
      //DHT
      //delay(dht.getMinimumSamplingPeriod());
    
      float temperature = dht.getTemperature();
      if (isnan(temperature)) {
        Serial.println("Failed reading temperature from DHT");
      } else if (temperature != lastTemp) {
        lastTemp = temperature;
        if (!metric) {
          temperature = dht.toFahrenheit(temperature);
        }
        gw.send(msgTemp.set(temperature, 1));
        Serial.print("---------- Temp: ");
        Serial.println(temperature);
      }
    
      float humidity = dht.getHumidity();
      if (isnan(humidity)) {
        Serial.println("Failed reading humidity from DHT");
      } else if (humidity != lastHum) {
        lastHum = humidity;
        gw.send(msgHum.set(humidity, 1));
        Serial.print("---------- Humidity: ");
        Serial.println(humidity);
      }
      // Light
      int lightLevel = (1023 - analogRead(LIGHT_SENSOR_ANALOG_PIN)) / 10.23;
      //Serial.println(lightLevel);
      if (lightLevel != lastLightLevel) {
        gw.send(msgLight.set(lightLevel));
        lastLightLevel = lightLevel;
        Serial.print("---------- Light: ");
        Serial.println(lightLevel);
      }
      // Sleep until interrupt comes in on motion sensor. Send update every two minute.
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    }
    

    the pir works fine. but the dht doesn't work.

    when delay(dht.getMinimumSamplingPeriod()); is used the dht works and the pir fails.


  • Hero Member

    It makes sense 😉 Try this:

    create (outside the loop) a variable to count the time:

    long mytime = 0; 
    

    .. and replace the delay by :

     if ( milis() > mytime )  { 
    
       <  Put the dht stuff here > 
    
      mytime = millis() + dht.getMinimumSamplingPeriod() ; 
    
    }


  • @rvendrame

    hmm 🙂
    if is use this:

    #include <MySensor.h>
    #include <readVcc.h>
    #include <SPI.h>
    #include <DHT.h>
    
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 10000;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    int oldBatteryPcnt;
    int lastLightLevel;
    long mytime = 0;
    
    
    int MIN_V = 2700; // empty voltage (0%)
    int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
    
      //PIR
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode(PIR_SENSOR_DIGITAL, INPUT);      // sets the motion sensor digital pin as input
      digitalWrite(PIR_SENSOR_DIGITAL, HIGH);
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_PIR, S_MOTION);
    
      //DHT
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
    
      // Send the Sketch Version Information to the Gateway
      gw.sendSketchInfo("Humidity", "1.0");
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
    
      metric = gw.getConfig().isMetric;
    
      //LIGHT
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Light Sensor", "1.0");
    
      // Register all sensors to gateway (they will be created as child devices)
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    
    }
    
    void loop()
    {
    
    
    
      // Read digital motion value
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0")); // Send tripped value to gw
    
    
      if ( millis() > mytime )  {
    
        //DHT
        delay(dht.getMinimumSamplingPeriod());
    
        float temperature = dht.getTemperature();
        if (isnan(temperature)) {
          Serial.println("Failed reading temperature from DHT");
        } else if (temperature != lastTemp) {
          lastTemp = temperature;
          if (!metric) {
            temperature = dht.toFahrenheit(temperature);
          }
          gw.send(msgTemp.set(temperature, 1));
          Serial.print("---------- Temp: ");
          Serial.println(temperature);
        }
    
        float humidity = dht.getHumidity();
        if (isnan(humidity)) {
          Serial.println("Failed reading humidity from DHT");
        } else if (humidity != lastHum) {
          lastHum = humidity;
          gw.send(msgHum.set(humidity, 1));
          Serial.print("---------- Humidity: ");
          Serial.println(humidity);
        }
        // Light
        int lightLevel = (1023 - analogRead(LIGHT_SENSOR_ANALOG_PIN)) / 10.23;
        //Serial.println(lightLevel);
        if (lightLevel != lastLightLevel) {
          gw.send(msgLight.set(lightLevel));
          lastLightLevel = lightLevel;
          Serial.print("---------- Light: ");
          Serial.println(lightLevel);
        }
        // Measure battery
        float batteryV = readVcc();
        int batteryPcnt = (((batteryV - MIN_V) / (MAX_V - MIN_V)) * 100 );
        if (batteryPcnt > 100) {
          batteryPcnt = 100;
        }
    
        if (batteryPcnt != oldBatteryPcnt) {
          gw.sendBatteryLevel(batteryPcnt); // Send battery percentage
          oldBatteryPcnt = batteryPcnt;
        }
        Serial.print("---------- Battery: ");
        Serial.println(batteryPcnt);
    
        mytime = millis() + dht.getMinimumSamplingPeriod();
     
      }
         Serial.println(mytime);
      // Sleep until interrupt comes in on motion sensor. Send update every two minute.
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    }
    

    i get this output:
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    send: 10-10-255-255 s=255,c=3,t=7,pt=0,l=0,st=fail:
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=fail:41.7
    ---------- Humidity: 41.70
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=fail:38
    ---------- Light: 38
    ---------- Battery: 100
    11148
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    11148
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    11148
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    11148
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    11148
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    send: 10-10-255-255 s=255,c=3,t=7,pt=0,l=0,st=fail:
    ---------- Battery: 100
    15441
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    15441
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    15441
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    15441
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1

    the pir sends 0 and didnt sleep right 😞


  • Hero Member

    What is this number? Did you print the milis()?

    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608 <<<<<<



  • @n3ro said:

    Serial.println(mytime);

    yes 🙂
    Serial.println(mytime);


  • Hero Member

    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    

    Are you connecting both DHT and PIR at same pin 2 ? That must be the cause (DHT is triggering the interruption, I think you want only the PIR to trigger it).

    Edit: looks like your PIR is at pin 3 , and DHT on pin 2 --- Should be the inverse? The PIR should be on pin 2 (to trigger the interrupt).



  • @rvendrame Pir sensor is defined as 3

    interrupt pin is defined as INT1: 3 - 2 = 1


  • Hero Member

    So PIR must connect on PIN 1 and not PIN 3.

    Edit: Better, how did you connect DHT and PIR?



  • @rvendrame The DHT is on pin 2 and the pir on pin 3. i use the MYS PCB.

    i suspect the delay function disturb the sleep function. if i dont use the delay, the dht cant "heat up".

    far as I know the interrupt is only an internal value. right?


  • Hero Member

    Yes, it looks fine. What exactly error are you having? From your first serial monitor, it looks like your sensor woke on every 10min aprox, ( 6608 / 11148 / 15441 ).



  • @rvendrame
    if i use this:

    #include <MySensor.h>
    #include <readVcc.h>
    #include <SPI.h>
    #include <DHT.h>
    
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 600000;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    int oldBatteryPcnt;
    int lastLightLevel;
    
    
    int MIN_V = 2700; // empty voltage (0%)
    int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
    
      //PIR
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode(PIR_SENSOR_DIGITAL, INPUT);      // sets the motion sensor digital pin as input
      digitalWrite(PIR_SENSOR_DIGITAL, HIGH);
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_PIR, S_MOTION);
      
      //DHT
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
    
      // Send the Sketch Version Information to the Gateway
      gw.sendSketchInfo("Humidity", "1.0");
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
    
      metric = gw.getConfig().isMetric;
      
      //LIGHT
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Light Sensor", "1.0");
    
      // Register all sensors to gateway (they will be created as child devices)
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    
    }
    
    void loop()
    {
    
      // Measure battery
      float batteryV = readVcc();
      int batteryPcnt = (((batteryV - MIN_V) / (MAX_V - MIN_V)) * 100 );
      if (batteryPcnt > 100) {
        batteryPcnt = 100;
      }
    
      if (batteryPcnt != oldBatteryPcnt) {
        gw.sendBatteryLevel(batteryPcnt); // Send battery percentage
        oldBatteryPcnt = batteryPcnt;
      }
      Serial.print("---------- Battery: ");
      Serial.println(batteryPcnt);
    
      // Read digital motion value
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0")); // Send tripped value to gw
    
    
      //DHT
      //delay(dht.getMinimumSamplingPeriod());
    
      float temperature = dht.getTemperature();
      if (isnan(temperature)) {
        Serial.println("Failed reading temperature from DHT");
      } else if (temperature != lastTemp) {
        lastTemp = temperature;
        if (!metric) {
          temperature = dht.toFahrenheit(temperature);
        }
        gw.send(msgTemp.set(temperature, 1));
        Serial.print("---------- Temp: ");
        Serial.println(temperature);
      }
    
      float humidity = dht.getHumidity();
      if (isnan(humidity)) {
        Serial.println("Failed reading humidity from DHT");
      } else if (humidity != lastHum) {
        lastHum = humidity;
        gw.send(msgHum.set(humidity, 1));
        Serial.print("---------- Humidity: ");
        Serial.println(humidity);
      }
      // Light
      int lightLevel = (1023 - analogRead(LIGHT_SENSOR_ANALOG_PIN)) / 10.23;
      //Serial.println(lightLevel);
      if (lightLevel != lastLightLevel) {
        gw.send(msgLight.set(lightLevel));
        lastLightLevel = lightLevel;
        Serial.print("---------- Light: ");
        Serial.println(lightLevel);
      }
      // Sleep until interrupt comes in on motion sensor. Send update every two minute.
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    }
    

    i get this output after starting:
    sensor started, id 10
    send: 10-10-0-0 s=255,c=0,t=17,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=6,pt=1,l=1,st=ok:0
    read: 0-0-10 s=255,c=3,t=6,pt=0,l=1:M
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=13,st=ok:Motion Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=1,c=0,t=1,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=8,st=ok:Humidity
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=2,c=0,t=7,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=3,c=0,t=6,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=12,st=ok:Light Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=4,c=0,t=16,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=0,pt=1,l=1,st=ok:100
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:16.6
    ---------- Temp: 16.60
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=ok:43.8
    ---------- Humidity: 43.80
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:39
    ---------- Light: 39
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:37
    ---------- Light: 37
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:34
    ---------- Light: 34
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:36
    ---------- Light: 36
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:37
    ---------- Light: 37
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:38
    ---------- Light: 38

    The DHT gives only output the first start and the pir interrupt works perfect.

    When delay(dht.getMinimumSamplingPeriod()); is activated the DHT works and the pit interrupts the whole time 😞
    In this configuration the arduino never sleeps ..

    sensor started, id 10
    send: 10-10-0-0 s=255,c=0,t=17,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=6,pt=1,l=1,st=ok:0
    read: 0-0-10 s=255,c=3,t=6,pt=0,l=1:M
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=13,st=ok:Motion Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=1,c=0,t=1,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=8,st=ok:Humidity
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=2,c=0,t=7,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=3,c=0,t=6,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=12,st=ok:Light Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=4,c=0,t=16,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=0,pt=1,l=1,st=ok:100
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:16.5
    ---------- Temp: 16.50
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=ok:43.9
    ---------- Humidity: 43.90
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:38
    ---------- Light: 38
    ---------- Battery: 100
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:16.6
    ---------- Temp: 16.60
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=ok:43.8
    ---------- Humidity: 43.80
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:37
    ---------- Light: 37
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:16.5
    ---------- Temp: 16.50
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- Battery: 100
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    send: 10-10-0-0 s=4,c=1,t=23,pt=2,l=2,st=ok:38

    EDIT: i have changed the sleeptime for testing to a shorter time



  • @rvendrame When the PIR is connected to PIN3 the interrupt is INT1. Pin 1 does not have an interrupt.

    Only pin 2 and pin 3 have an interrupt.

    Pin 2 = int0
    pin 3 = int1


  • Hero Member

    if you put the delay() inside that 'if ( mills() > mytime ) ' , what happens?



  • @Sweebee is it possible to fix the problem when DHT is connected to pin 4?


  • Hero Member

    @n3ro said:

    s it possible to fix the problem when DHT is connected to pin 4?

    It worth a try ...



  • @rvendrame
    i have posted it before this post:

    "What is this number? Did you print the milis()?

    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    6608 <<<<<<"

    in the posted sketch the delay is inside millis


  • Hero Member

    I didn't find the if ( millis() > my time) in the last sketch you posted ...



  • if i use this

    #include <MySensor.h>
    #include <readVcc.h>
    #include <SPI.h>
    #include <DHT.h>
    
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 10000;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    int oldBatteryPcnt;
    int lastLightLevel;
    long mytime = 0;
    
    
    int MIN_V = 2700; // empty voltage (0%)
    int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
    
      //PIR
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Motion Sensor", "1.0");
    
      pinMode(PIR_SENSOR_DIGITAL, INPUT);      // sets the motion sensor digital pin as input
      digitalWrite(PIR_SENSOR_DIGITAL, HIGH);
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_PIR, S_MOTION);
    
      //DHT
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
    
      // Send the Sketch Version Information to the Gateway
      gw.sendSketchInfo("Humidity", "1.0");
    
      // Register all sensors to gw (they will be created as child devices)
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
    
      metric = gw.getConfig().isMetric;
    
      //LIGHT
      // Send the sketch version information to the gateway and Controller
      gw.sendSketchInfo("Light Sensor", "1.0");
    
      // Register all sensors to gateway (they will be created as child devices)
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    
    }
    
    void loop()
    {
    
    
    
      // Read digital motion value
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0")); // Send tripped value to gw
    
    
      if ( millis() > mytime )  {
    
        //DHT
        delay(dht.getMinimumSamplingPeriod());
    
        float temperature = dht.getTemperature();
        if (isnan(temperature)) {
          Serial.println("Failed reading temperature from DHT");
        } else if (temperature != lastTemp) {
          lastTemp = temperature;
          if (!metric) {
            temperature = dht.toFahrenheit(temperature);
          }
          gw.send(msgTemp.set(temperature, 1));
          Serial.print("---------- Temp: ");
          Serial.println(temperature);
        }
    
        float humidity = dht.getHumidity();
        if (isnan(humidity)) {
          Serial.println("Failed reading humidity from DHT");
        } else if (humidity != lastHum) {
          lastHum = humidity;
          gw.send(msgHum.set(humidity, 1));
          Serial.print("---------- Humidity: ");
          Serial.println(humidity);
        }
        mytime = millis() + dht.getMinimumSamplingPeriod();
    
      }
      // Sleep until interrupt comes in on motion sensor. Send update every two minute.
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME);
    }
    

    i get this output:
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=13,st=ok:Motion Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=1,c=0,t=1,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=8,st=ok:Humidity
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=2,c=0,t=7,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=3,c=0,t=6,pt=0,l=5,st=ok:1.4.1
    send: 10-10-0-0 s=255,c=3,t=11,pt=0,l=12,st=ok:Light Sensor
    send: 10-10-0-0 s=255,c=3,t=12,pt=0,l=3,st=ok:1.0
    send: 10-10-0-0 s=4,c=0,t=16,pt=0,l=5,st=ok:1.4.1
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    send: 10-10-0-0 s=3,c=1,t=0,pt=7,l=5,st=ok:17.2
    ---------- Temp: 17.20
    send: 10-10-0-0 s=2,c=1,t=1,pt=7,l=5,st=ok:43.8
    ---------- Humidity: 43.80
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 1
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:1
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0
    ---------- PIR: 0
    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=ok:0



  • This can't work well. Your interrupt is set on pin1 - 2 = int-1?

    What happens when you remove the pir and use a switch instead?



  • @Sweebee
    is #define INTERRUPT PIR_SENSOR_DIGITAL-2 wrong?

    when i use a switch it looks OK


  • Hero Member

    @n3ro , what is wrong at your last test? The PIR is reporting 0 and 1, and from time to time there is a temp/hum report as well.



  • @rvendrame in my last test the pir sends endless 0 and dont sleep


  • Hero Member

    Which arduino PIN do you use to connect the PIR?



  • @n3ro said:

    #define PIR_SENSOR_DIGITAL 3

    🙂


  • Hero Member

    Perfect. If it is working fine with a switch --- Maybe your PIN is triggering false positives? Or maybe the PIR output is floating a bit, and arduino is triggering it more than it should?



  • If a switch works than the only could be the pir itself. You have enabled the pull-up resistor so an open collector should not give floats.

    You already told that a sketch with a pir only worked fine?

    Well, i can test what happens with my dht22 and a pir tomorrow (with your sketch).




  • Contest Winner

    @n3ro

    you are sending an update on the PIR status every time the arduino wakes from a sleep, which you don't need.

    Also, and this probably isn't a problem right now, but will case a problem later, use unsigned subtraction in your millis( ) timers

    could not see where you were using the library, so I commented it out below, not having it on my computer

    I also made a few more notes in the code:

    #include <MySensor.h>
    //#include <readVcc.h> // cannot see where you are using this library yet
    #include <SPI.h>
    #include <DHT.h>
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 10000UL;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    boolean lastTripped = false;
    int oldBatteryPcnt;
    int lastLightLevel;
    unsigned long mytime;
    //int MIN_V = 2700; // empty voltage (0%)
    //int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
      gw.sendSketchInfo("Motion Sensor", "1.0"); // here you call it motion sensor
      pinMode(PIR_SENSOR_DIGITAL, INPUT_PULLUP);
      gw.present(CHILD_ID_PIR, S_MOTION);
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
      //gw.sendSketchInfo("Humidity", "1.0"); // here you call it humidity
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
      metric = gw.getConfig().isMetric;
      //gw.sendSketchInfo("Light Sensor", "1.0");// pick a name for your sketch, it will only be one
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    }
    
    void loop()
    {
      // why send this every time?  
      /*
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0"));
      */
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      if (tripped != lastTripped)  // only need to update controller on a change.
      {
        gw.send(msgPir.set(tripped? "1" : "0"));
        Serial.print("---------- PIR: ");
        Serial.println(tripped? "tripped" : " not tripped");
        lastTripped = tripped;
      }
      if ( millis() - mytime >= SLEEP_TIME )  //use UNSIGNED SUBRTACTION im your millis() timers to avoid rollover issues later on down the line
      {
        float temperature = dht.getTemperature();
        if (isnan(temperature))
        {
          Serial.println("Failed reading temperature from DHT");
        }
        else if (temperature != lastTemp)
        {
          lastTemp = temperature;
          if (!metric) 
          {
            temperature = dht.toFahrenheit(temperature);
          }
          gw.send(msgTemp.set(temperature, 1));
          Serial.print("---------- Temp: ");
          Serial.println(temperature);
        }
        float humidity = dht.getHumidity();
        if (isnan(humidity)) 
        {
          Serial.println("Failed reading humidity from DHT");
        } 
        else if (humidity != lastHum) 
        {
          lastHum = humidity;
          gw.send(msgHum.set(humidity, 1));
          Serial.print("---------- Humidity: ");
          Serial.println(humidity);
        }
        mytime = millis();
      }
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME); // Sleep until interrupt detected from motion sensor. Send update every SLEEP_TIME.
    }
    


  • @BulldogLowell

    Hey, its a good idea to send only PIR if changed!
    The unused code in the sketch is because i have reduced the used functions to the minimum to debug it better. The full sketch has LDR and battery lifetime output too.

    i have added some extra output in the modified sketch:

    #include <MySensor.h>
    //#include <readVcc.h> // cannot see where you are using this library yet
    #include <SPI.h>
    #include <DHT.h>
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 10000UL;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    boolean lastTripped = false;
    int oldBatteryPcnt;
    int lastLightLevel;
    unsigned long mytime;
    //int MIN_V = 2700; // empty voltage (0%)
    //int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
      gw.sendSketchInfo("Motion Sensor", "1.0"); // here you call it motion sensor
      pinMode(PIR_SENSOR_DIGITAL, INPUT_PULLUP);
      gw.present(CHILD_ID_PIR, S_MOTION);
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
      //gw.sendSketchInfo("Humidity", "1.0"); // here you call it humidity
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
      metric = gw.getConfig().isMetric;
      //gw.sendSketchInfo("Light Sensor", "1.0");// pick a name for your sketch, it will only be one
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    }
    
    void loop()
    {
      // why send this every time?
      /*
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0"));
      */
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      if (tripped != lastTripped)  // only need to update controller on a change.
      {
        gw.send(msgPir.set(tripped ? "1" : "0"));
        Serial.print("---------- PIR: ");
        Serial.println(tripped ? "tripped" : " not tripped");
        lastTripped = tripped;
      }
      if ( millis() - mytime >= SLEEP_TIME )  //use UNSIGNED SUBRTACTION im your millis() timers to avoid rollover issues later on down the line
      {
        delay(dht.getMinimumSamplingPeriod());
        float temperature = dht.getTemperature();
        if (isnan(temperature))
        {
          Serial.println("Failed reading temperature from DHT");
        }
        else if (temperature != lastTemp)
        {
          lastTemp = temperature;
          if (!metric)
          {
            temperature = dht.toFahrenheit(temperature);
          }
          gw.send(msgTemp.set(temperature, 1));
          Serial.print("---------- Temp: ");
          Serial.println(temperature);
        }
        float humidity = dht.getHumidity();
        if (isnan(humidity))
        {
          Serial.println("Failed reading humidity from DHT");
        }
        else if (humidity != lastHum)
        {
          lastHum = humidity;
          gw.send(msgHum.set(humidity, 1));
          Serial.print("---------- Humidity: ");
          Serial.println(humidity);
        }
        mytime = millis();
    
      }
      else
      {
        Serial.println("no millis");
      }
      Serial.println(millis());
      Serial.println(mytime);
      Serial.println(SLEEP_TIME);
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME); // Sleep until interrupt detected from motion sensor. Send update every SLEEP_TIME.
    }
    

    send: 10-10-0-0 s=1,c=1,t=16,pt=0,l=1,st=fail:0
    ---------- PIR: not tripped
    no millis
    2185
    0
    10000
    no millis
    2189
    0
    10000
    no millis
    2193
    0
    10000
    no millis
    2195
    0
    10000
    no millis
    2197
    0
    10000
    no millis
    2201
    0
    10000
    no millis
    2203
    0
    10000
    no millis
    2205
    0
    10000
    no millis
    2209
    0
    10000
    no millis
    2211
    0
    10000
    no millis

    You can see that the "if millis" will never used .:(



  • i think millis didnt work with sleep. the counter is not increasing when sleeping..


  • Contest Winner

    @n3ro said:

    delay(dht.getMinimumSamplingPeriod());

    you dont need this:

    delay(dht.getMinimumSamplingPeriod());
    

    since you are sleeping longer than the minimum sampling period

    try like this, removing the timer, just use the sleep period t update temp/humidity (untested):

    #include <MySensor.h>
    //#include <readVcc.h> // cannot see where you are using this library yet
    #include <SPI.h>
    #include <DHT.h>
    
    #define NODE_ID 10                       // ID of node
    unsigned long SLEEP_TIME = 10000UL;        // Sleep time between reports (in milliseconds)
    
    #define CHILD_ID_PIR 1                   // Id of the sensor PIR
    #define CHILD_ID_HUM 2                   // Id of the sensor HUM
    #define CHILD_ID_TEMP 3                  // Id of the sensor TEMP
    #define CHILD_ID_LIGHT 4                 // Id of the sensor LIGHT
    
    #define PIR_SENSOR_DIGITAL 3           // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define INTERRUPT PIR_SENSOR_DIGITAL-2 // Usually the interrupt = pin -2 (on uno/nano anyway)
    #define HUMIDITY_SENSOR_DIGITAL_PIN 2
    #define LIGHT_SENSOR_ANALOG_PIN 0
    
    MySensor gw;
    // Initialize Variables
    MyMessage msgPir(CHILD_ID_PIR, V_TRIPPED);
    MyMessage msgHum(CHILD_ID_HUM, V_HUM);
    MyMessage msgTemp(CHILD_ID_TEMP, V_TEMP);
    MyMessage msgLight(CHILD_ID_LIGHT, V_LIGHT_LEVEL);
    
    DHT dht;
    float lastTemp;
    float lastHum;
    boolean metric = true;
    boolean lastTripped = false;
    int oldBatteryPcnt;
    int lastLightLevel;
    //int MIN_V = 2700; // empty voltage (0%)
    //int MAX_V = 3200; // full voltage (100%)
    
    void setup()
    {
      gw.begin(NULL, NODE_ID, false);
      gw.sendSketchInfo("Motion Sensor", "1.0"); // here you call it motion sensor
      pinMode(PIR_SENSOR_DIGITAL, INPUT_PULLUP);
      gw.present(CHILD_ID_PIR, S_MOTION);
      dht.setup(HUMIDITY_SENSOR_DIGITAL_PIN);
      //gw.sendSketchInfo("Humidity", "1.0"); // here you call it humidity
      gw.present(CHILD_ID_HUM, S_HUM);
      gw.present(CHILD_ID_TEMP, S_TEMP);
      metric = gw.getConfig().isMetric;
      //gw.sendSketchInfo("Light Sensor", "1.0");// pick a name for your sketch, it will only be one
      gw.present(CHILD_ID_LIGHT, S_LIGHT_LEVEL);
    }
    
    void loop()
    {
      // why send this every time?
      /*
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      Serial.print("---------- PIR: ");
      Serial.println(tripped);
      gw.send(msgPir.set(tripped ? "1" : "0"));
      */
      boolean tripped = digitalRead(PIR_SENSOR_DIGITAL) == HIGH;
      if (tripped != lastTripped)  // only need to update controller on a change.
      {
        gw.send(msgPir.set(tripped ? "1" : "0"));
        Serial.print("---------- PIR: ");
        Serial.println(tripped ? "tripped" : " not tripped");
        lastTripped = tripped;
      }
      float temperature = dht.getTemperature();
      if (isnan(temperature))
      {
        Serial.println("Failed reading temperature from DHT");
      }
      else if (temperature != lastTemp)
      {
        lastTemp = temperature;
        if (!metric)
        {
          temperature = dht.toFahrenheit(temperature);
        }
        gw.send(msgTemp.set(temperature, 1));
        Serial.print("---------- Temp: ");
        Serial.println(temperature);
      }
      float humidity = dht.getHumidity();
      if (isnan(humidity))
      {
        Serial.println("Failed reading humidity from DHT");
      }
      else if (humidity != lastHum)
      {
        lastHum = humidity;
        gw.send(msgHum.set(humidity, 1));
        Serial.print("---------- Humidity: ");
        Serial.println(humidity);
      }
      gw.sleep(INTERRUPT, CHANGE, SLEEP_TIME); // Sleep until interrupt detected from motion sensor. Send update every SLEEP_TIME.
    }
    


  • @BulldogLowell
    when i use this sketch the PIR works but the DHT cant read:

    Failed reading temperature from DHT
    Failed reading humidity from DHT


  • Contest Winner

    check the connections



  • @BulldogLowell the wires are OK.

    In sleep the DHT cant warm-up. so the dht need 2 sec before read. when i dont use the delay i cant read it.

    i dont understand why the interrupt didnt work with the enabled delay.

    do you have tested on a arduino?




  • Hero Member

    @n3ro, i'm glad you fixed it. DHT was on PIN3 before, right? Pin 2 & Pin3 are connected to the interrupts, maybe this was the problem.



  • @rvendrame yes i think so. but now its ok 😃


  • Contest Winner

    @n3ro said:

    now its working. when i use PIN4 for DHT.:)

    👏


Log in to reply
 

Suggested Topics

66
Online

11.4k
Users

11.1k
Topics

112.7k
Posts