Adding Boolean for Pir Sensors

Hello

need help to add another boolean function to this code for Pir sensors.

the purpose is;
to restart ‘‘fade on’’ of led strips when motion detected.

right now;
while ledstrip is fading off, arduino disregards pir sense.

Thank you in advance!

/*
  Under the bed nightlight

  Lights up a led strip under the bed when it detects movement while its dark.

  The circuit:
  * PIR for movement. The ammout of sensors depends on the bed. 
  * LDR for light sensor
        * Transistor to drive the LED strip

*/
#define ldr_pin A5
#define led_pin 9

const int numberOfPirs = 2;              // Number of pir sensors
const int pir_pins[numberOfPirs] = {A2,A3};  // Pins of the pir sensors Example = {pin,pin,pin}

const int led_time = 10; // Time to have the leds on (no an exact timing) (in Sec)
const int on_delay = 20; // Delay to turn the leds on (in mSec)
const int off_delay = 20; // Delay to turn the leds off (in mSec)

const int ldr_value = 500; // Value to make the differene between dark and light

const int led_max = 255;  // Ledstrip max pwm value
const int led_min = 0;    // Ledstrip min pwm value (0 recommended, else it wont turn off)

boolean licht = false;   // Booelan thats true when the light is on;
boolean led = false;     // Boolean thats true when the led strip is on;
int timer = 0;           // Integer for the timer;

void setup(){

  pinMode(ldr_pin,INPUT);
  
  // Set pinmode for all pir sensors
  for (int i=0; i < numberOfPirs; i++){
    pinMode(pir_pins[i],INPUT);
  }
  
  pinMode(led_pin,OUTPUT);
}

void loop(){
  
  // Read ldr value
  int ldr = analogRead(ldr_pin);
 
  // Read all pir sensors
  boolean pir = false;    
  for (int i=0; i < numberOfPirs; i++){
      if (digitalRead(pir_pins[i]) == 1){
        pir = true;    
      }
  }

  // Check if the room hase enough light
  if (ldr > ldr_value){
    licht = false; 
  }else{
    licht = true; 
  }
 
  // If the room is dark and movement is detected the leds turn on and the timer is set to 0
  if (pir == true && licht == false){
    ledAan();
    timer = 0;
  }
  
  // if the leds are on and the room has enough light the leds go off
  if (led == true && licht == true){
    ledUit(); 
  }
  
  // if the leds are on icrement the timer
  if (led == true) timer++;
  
  // if the timer is equal to the set time turn the leds off.
  if (timer == led_time){
    ledUit(); 
  }
 
  delay(1000);
}


// function to turn the leds on
void ledAan(){
  if (led == false){
    for(int i=led_min;i<=led_max; i++){
      analogWrite(led_pin,i);
      delay(on_delay);
    }    
    led = true;
  }
}

// function to turn the leds off
void ledUit(){
  if (led == true){
    for(int i=led_max;i>=led_min; i--){
      analogWrite(led_pin,i);
      delay(off_delay);      
    }    
    led = false;
  }
}

you have a lot of blocking code like delay() and for loops with delays.

That will impair the responsiveness of your sketch.

Read the Blink Without Delay example in your IDE to try to do this without blocking code.

I did something VERY similar for a backlit mirror in a powder room… made a class to fade.

Try the modification that I did here, using my Fade class (Fade.h library)

Notes are in the code (i simplified a lot)… check your sensor and led pins

/*
  Under the bed nightlight

  Lights up a led strip under the bed when it detects movement while its dark.

  The circuit:
  * PIR for movement. The ammout of sensors depends on the bed.
  * LDR for light sensor
  * Transistor to drive the LED strip
  
  * ADDED 1/23/2016
  * activated on Motion detected on eiither PIR sensor
  * stays lit until timeout
  * non-blocking Fade.h library provides a smoothe fade
*/

#include "Fade.h"
#define ldr_pin A5
#define led_pin 9
#define TIME_OUT  15*1000UL     // 15 seconds of on time and will fade off automatically

const byte pir_pins[] = {3, 4}; // Pins of the pir sensors Example = {pin,pin,pin}
const int ldr_value = 500;      // Value to make the differene between dark and light
boolean licht = false;          // Booelan thats true when the light is BRIGHT;
unsigned long startMillis = 0;

Fade ledStrip(led_pin, 25);     // dimming pin, millis between steps  make this number larger for a slower fade...

bool lastPirState = false;

void setup()
{
  Serial.begin(9600);
  pinMode(ldr_pin, INPUT);
  for (int i = 0; i < 2 ; i++) 
  {
    pinMode(pir_pins[i], INPUT_PULLUP);
  }
  pinMode(led_pin, OUTPUT);
  ledStrip.write(0);
}

void loop()
{
  ledStrip.update();
  bool licht = (analogRead(ldr_pin) > ldr_value);
  boolean pirState = digitalRead(pir_pins[0]) || digitalRead(pir_pins[1]);
  if(pirState != lastPirState)
  {
    Serial.println(pirState? "MOTION ON" : "MOTION OFF");
    if(lastPirState == false)               // state change to MOTION
    {
      startMillis = millis();               // re-trigger timer on every motion detect 
      if(!licht)                            // if low light
      {
        ledStrip.write(255);
      }
    }
  }
  lastPirState = pirState;
  if((millis() - startMillis > TIME_OUT) && ledStrip.read() == 255)
  {
    ledStrip.write(0);
    Serial.println("Timer switched lamp off");  // this may print multiple times while taking the first increment down
  }
}

add two tabs to your project and create a Fade.h and Fade.cpp file:

Fade.h

#ifndef Fade_h
#define Fade_h

#include "Arduino.h"

class Fade
{
  public:
    Fade() {};
    Fade(int pin, uint32_t timeStep = 15, uint8_t min = 0, uint8_t max = 255);
    void write(int to);
    void update();
    void update(uint32_t time);
    uint8_t setPoint();
    uint8_t read();
    uint32_t readSpeed();
    uint32_t writeSpeed(uint32_t time);
  private:
    uint8_t _min;
    uint8_t _max;
    uint8_t _targetFade;
    uint8_t _pwmRate;
    uint32_t _time;
    uint32_t _last;
    int _pin;
};

#endif

Fade.cpp

#include "Arduino.h"
#include "Fade.h"

Fade::Fade ( int pin, uint32_t timeStep, uint8_t min, uint8_t max)
{
  _pin = pin;
  _time = timeStep;
  _min = min;
  _max = max;
  pinMode(_pin, OUTPUT);
  analogWrite(_pin, _min);
  _pwmRate = _min;
}

void Fade::write(int to)
{
  _targetFade = (uint8_t) constrain(to, _min, _max);

  this->update();
}

uint8_t Fade::setPoint()
{
  return _targetFade;
}

void Fade::update()
{
  this->update(millis());
}

void Fade::update(uint32_t time)
{
  if (time - _time > _last)
  {
    _last = time;
    if (_pwmRate > _targetFade) analogWrite(_pin, --_pwmRate);
    if (_pwmRate < _targetFade) analogWrite(_pin, ++_pwmRate);
  }
}

uint8_t Fade::read()
{
  return _pwmRate;
}

uint32_t Fade::readSpeed()
{
  return _time;
}

uint32_t Fade::writeSpeed(uint32_t time)
{
  _time = time;
}

I didn’t test with two PIR sensors but I did test it.

Thank you soo much Sir! Really apreciated. May god give you what you are wishing for...

PHOTOGUY:
Thank you soo much Sir! Really apreciated. May god give you what you are wishing for…

:-[

so, I made a little change (.ino file only) because I thought it should stay lit as long as it detects motion…

****also check out the notes in the code regarding maximum brightness!!

/*
  Under the bed nightlight

  Lights up a led strip under the bed when it detects movement while its dark.

  The circuit:
  * PIR for movement. The ammout of sensors depends on the bed.
  * LDR for light sensor
  * Transistor to drive the LED strip
  
  * ADDED 1/23/2016
  * activated on Motion detected on eiither PIR sensor
  * stays lit until timeout
  * non-blocking Fade.h library provides a smoothe fade
*/

#include "Fade.h"
#define ldr_pin A5
#define led_pin 9
#define TIME_OUT  15*1000UL     // 15 seconds of on time and will fade off automatically

const byte pir_pins[] = {3, 4}; // Pins of the pir sensors Example = {pin,pin,pin}
const int ldr_value = 500;      // Value to make the differene between dark and light
boolean licht = false;          // Booelan thats true when the light is BRIGHT;
unsigned long startMillis = 0;

Fade ledStrip(led_pin, 25);     // dimming pin, millis between steps  make this number larger for a slower fade...

bool lastPirState = false;

void setup()
{
  Serial.begin(9600);
  pinMode(ldr_pin, INPUT);
  for (int i = 0; i < sizeof(pir_pins); i++) 
  {
    pinMode(pir_pins[i], INPUT);
  }
  pinMode(led_pin, OUTPUT);
  ledStrip.write(0);
}

void loop()
{
  ledStrip.update();
  bool licht = (analogRead(ldr_pin) > ldr_value);
  boolean pirState = digitalRead(pir_pins[0]) || digitalRead(pir_pins[1]);
  if(pirState != lastPirState)
  {
    Serial.println(pirState? "MOTION ON" : "MOTION OFF");
    if(lastPirState == false)               // state change to MOTION
    {
      startMillis = millis();               // re-trigger timer on every motion detect 
      if(!licht)                            // if low light
      {
        ledStrip.write(255);  //<<<<<<<<<<  Note you can change this to a lower number for the max briteness!!!!
      }
    }
  }
  else if (pirState)   // constantly restarting timer if motion active
  {
    startMillis = millis();
  }
  lastPirState = pirState;
  if((millis() - startMillis > TIME_OUT) && ledStrip.setPoint())  // modified this to allow of above 
  {
    ledStrip.write(0);
    Serial.println("Timer switched lamp off");  // this may print multiple times while taking the first increment down
  }
}

Hello,

Today I have tested the code. However i am doing something wrong. Could you tell me which part needs to be corrected?

  • The code can be uploaded to arduino UNO without any problem.
  • Serial Monitor shows PIR state, Pirs working
  • Led is not lighting. Used different leds no change…
  • There are 3 tabs created as advised (screen print attached)

thank you

fade.png

are you sure that it is all wired up and the pin numbers are correct?

Check the photoresistor as well

Hello Mr James

i have checked all the connections even changed board but the led does not even blink.

searched all your post over the web in order not to take your precious time but could not find a way out. :slightly_frowning_face:

after long hours of examining i have realised that changing below value makes difference. At last the led blink!

const int ldr_value = 600;      // Value to make the differene between dark and light

after this changed polarity of LDR and it worked!!!

A5 <<<<<<<<<< 100ohm resistor <<<<<<<<<< neutral
A5 <<<<<<<<<< LDR <<<<<<<<<< positive

thank you Mr James!

GREAT!!

Share a photo or YouTube when you get a chance.

(try the backlit mirror too!!)