False triggering PIR sensor



  • Hi!

    I have a problem with integration of MySensors and well known HC-SR501.
    When i use example program, all works...
    When i change sleep to smartSleep in example, my sensor start "oscilating" 1010101010
    When i add some features like battery voltage and battery percent and use sleep(), node every "SLEEP_TIME" period trigger false 1 ... i change from 120000 to 360000 and every 6minutes i have false trigger

    /**
     * The MySensors Arduino library handles the wireless radio link and protocol
     * between your home built sensors/actuators and HA controller of choice.
     * The sensors forms a self healing radio network with optional repeaters. Each
     * repeater and gateway builds a routing tables in EEPROM which keeps track of the
     * network topology allowing messages to be routed to nodes.
     *
     * Created by Henrik Ekblad <henrik.ekblad@mysensors.org>
     * Copyright (C) 2013-2015 Sensnology AB
     * Full contributor list: https://github.com/mysensors/Arduino/graphs/contributors
     *
     * Documentation: http://www.mysensors.org
     * Support Forum: http://forum.mysensors.org
     *
     * This program is free software; you can redistribute it and/or
     * modify it under the terms of the GNU General Public License
     * version 2 as published by the Free Software Foundation.
     *
     *******************************
     *
     * REVISION HISTORY
     * Version 1.0 - Henrik Ekblad
     *
     * DESCRIPTION
     * Motion Sensor example using HC-SR501
     * http://www.mysensors.org/build/motion
     *
     */
    
    // Enable debug prints
    // #define MY_DEBUG
    #define MY_TRANSPORT_WAIT_READY_MS 3000
    #define MY_NODE_ID 113
    
    // Enable and select radio type attached
    #define MY_RF24_PA_LEVEL RF24_PA_MAX
    #define MY_RADIO_NRF24
    //#define MY_RADIO_NRF5_ESB
    //#define MY_RADIO_RFM69
    //#define MY_RADIO_RFM95
    
    #include <MySensors.h>
    
    #define MIN_V 1800
    #define MAX_V 3200
    
    uint32_t SLEEP_TIME = 360000; // Sleep time between reports (in milliseconds)
    #define DIGITAL_INPUT_SENSOR 3   // The digital input you attached your motion sensor.  (Only 2 and 3 generates interrupt!)
    #define CHILD_ID 6
    #define VOLTAGE_CHILD_ID     5
    
    #define ENABLE_VOLT 1
    #define COMPARE_VOLT 1       
    float voltThreshold = 0.05;                        
    float batteryPcntThreshold = 10;   
    
    
    
    int oldBatteryPcnt = 101;
    float oldBatteryV = 0.0;
    uint16_t sensorValue = 0;
    int batteryPcnt = 0;
    float batteryV = 0;
    float lastVoltage = -1;     
    
    // Initialize motion message
    MyMessage msg(CHILD_ID, V_TRIPPED);
    
    #if ENABLE_VOLT
    MyMessage voltageMsg(VOLTAGE_CHILD_ID, V_VOLTAGE);  // Node voltage
    #endif
    
    void setup()
    {
      sleep(20000);
    	pinMode(DIGITAL_INPUT_SENSOR, INPUT);      // sets the motion sensor digital pin as input
    }
    
    void presentation()
    {
    	// Send the sketch version information to the gateway and Controller
    	sendSketchInfo("Motion Sensor", "1.0");
    
    	// Register all sensors to gw (they will be created as child devices)
    	present(CHILD_ID, S_MOTION);
    #if ENABLE_VOLT
      present(VOLTAGE_CHILD_ID, S_MULTIMETER, "Battery " );
    #endif
    }
    
    void loop()
    {
    
        // Read digital motion value
      bool tripped = digitalRead(DIGITAL_INPUT_SENSOR) == HIGH;
    
      Serial.println(tripped);
      send(msg.set(tripped?"1":"0"));  // Send tripped value to gw
      
      sensorValue = readVcc();
      batteryPcnt = min(map(sensorValue, MIN_V, MAX_V, 0, 100), 100);
      batteryV = sensorValue/1000.000;
    #ifdef MY_DEBUG
      Serial.print(F("Battery Voltage: "));
      Serial.print(batteryV);
      Serial.println(" V");
    
      Serial.print(F("Battery percent: "));
      Serial.print(batteryPcnt);
      Serial.println(" %");
    #endif
    
    #if ENABLE_VOLT
        if (COMPARE_VOLT == 1 && abs(batteryV - lastVoltage) < voltThreshold) { 
          Serial.print(batteryV - lastVoltage);
          Serial.println(F("- Node - Voltage difference too small, so not sending the new measurement to the gateway."));
        } else {
          Serial.println(F("Node - Sending the new voltage to the gateway."));
          send(voltageMsg.set(batteryV,2));
          lastVoltage = batteryV; 
        }
    #endif 
      
    
    if ((batteryPcnt < oldBatteryPcnt) || (batteryPcnt > (oldBatteryPcnt + batteryPcntThreshold)) ) {
        sendBatteryLevel(batteryPcnt);
        oldBatteryPcnt = batteryPcnt;
      }
    
    
    	// Sleep until interrupt comes in on motion sensor. Send update every two minute.
    	sleep(digitalPinToInterrupt(DIGITAL_INPUT_SENSOR), CHANGE, SLEEP_TIME);
    }
    
    long readVcc() {
    Serial.println(F("readVcc"));
    // Read 1.1V reference against AVcc
    ADMUX = _BV(REFS0) | _BV(MUX3) | _BV(MUX2) | _BV(MUX1);
    delay(2); // Wait for Vref to settle
    ADCSRA |= _BV(ADSC); // Convert
    while (bit_is_set(ADCSRA,ADSC));
    uint8_t low  = ADCL; // must read ADCL first - it then locks ADCH  
    uint8_t high = ADCH; // unlocks both
    long result = (high<<8) | low;
    result = 1126400L / result; // Back-calculate AVcc in mV
    return result;
    }
    
    
    

    I am intrested in why smartsleep make that mess, and why in my code trigger every sleeptime period a fake alarm
    i use smartsleep in my another sensors with BME280 and BH1750 without problem.
    Thank you for help


  • Mod

    Hi @shajek, welcome to the forum!

    Which Arduino/microcontroller are you using? If you are using esp8266, false pir triggers are very common. Some people have had success shielding the pir from the esp, but in most cases changing to a different pir model has been the only reliable alternative.


  • Mod



  • Hi!

    I try it on Atmega328 (nano/promini at 8MHz RC / 8/MHz XTAL) ... Thank you for posts, but my problem is (i think) little different because when i use original MotionSensor sketch without modification code, all run perfectly ... when i change sleep to smartSleep i got triggered 1 immidietly after detecting 0. But stranger problem is, when i use sleep (which work) and add 2 messeges (which send in another node maybe one message per week because low power setup) and i got every sleep time false trigger (like last post you send me) but i have version 2.3.0
    I bypassed LDO and diode and when i measure output with mulitmeter (without connecting to arudino) i dont have triggers. Even with untouched example i dont have false trigger all day (watched in HomeAssistant)



  • It is not caused by software, but due to the power supply. When transmitting some disturbances come on the power supply, triggering the pir. So adding a big capacitor (start with 1mF and than lower values) on the power supply could help



  • My bet will be the power supply as well. i had one HC-SR501 running from battery for a few months .False triggers? every time sun comes out from a cloud! for outdoor they are crap.

    Just for you know about power supplies , last project that i build a k type thermometer(for high temperatures) on my fireplace, i feed it with a HLK-PM01 and while I didn't connect negative terminal to the fireplace steel chassis(ground) , it fluctuate a lot during readings, like 20c then 45c,25 etc.. not even with a capacitor.


 

466
Online

7.9k
Users

8.7k
Topics

93.6k
Posts