Pages: [1]   Go Down
Author Topic: home automation door switch timer problem  (Read 754 times)
0 Members and 1 Guest are viewing this topic.
Germany
Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Hello friends,
I need a little help with my home automation project. I would like to activate my light by opening the front door and to keep it on for a predetermined time. That would be fairly easy to accomplish with the delay function but I don't want to stop the entire sketch for, say, 20 seconds because I have more sensors and lights to control. What I need, and can't build myself, is a timer that starts when the door gets closed.
So it should work like: door open - lights go on (stay on), door closed - timer starts (light stays on until end of predetermined time).
I use servos to push the  wall switches, and right now it only activates on door opening and outside lightlevel.
With delay the door part looks like this:
Code:
#include <Servo.h>

Servo myservo3;
int doorpin = 8;                     //door open switch
int lightstate = LOW;
int intervaltime = 10000;
int ldrpin = 0;                     //light dependent resistor

void setup(){
  myservo3.attach(5);
  pinMode(doorpin, INPUT);
  pinMode(ldrpin, INPUT);
}

void loop()
{
  if(analogRead(ldrpin) > 900)          //over 900 means it's dark outside
  {
    if(digitalRead(doorpin) == LOW)     //door open
    {
      if(lightstate == LOW)              //light off
      {
        myservo3.write(126);            //servo pushes lightswitch on
        delay(500);
        myservo3.write(90);             //servo moves back to ready position
        delay(500);
        lightstate = HIGH;              //light is on

        delay(intervaltime);            //waits specified interval

        myservo3.write(59);             //servo pushes lightswitch off
        delay(500);
        myservo3.write(90);             //servo moves back to ready position
        delay(500);
        lightstate = LOW;               //light is off
      }
    }
  }
}

I tried different ideas but I probably have the wrong approach.
One of the not working idea I had looks like this:
Code:
#include <Servo.h>

Servo myservo3;
int doorpin = 8;
unsigned long currentdoortime;
unsigned long olddoortime = 0   ;
int doortimer = 5000;
int lightstate = LOW;

void setup(){
  myservo3.attach(5);
  pinMode(doorpin, INPUT);
}

void loop()
{
  if(digitalRead(doorpin) == LOW)     //door open
  {
    if(lightstate == LOW)              //light off
    {
      myservo3.write(126);            //servo pushes lightswitch on
      delay(500);
      myservo3.write(90);             //servo moves back to ready position
      delay(500);
      lightstate = HIGH;              //light on
    }
    else
    {
      if(lightstate == HIGH) 
        currentdoortime = millis();                      //some not working timer idea,
      if(currentdoortime - olddoortime > doortimer)      //probably wrong approach
      {                                             
        olddoortime = currentdoortime;
        myservo3.write(59);                             //servo pushes lightswitch off
        delay(500);
        myservo3.write(90);                             //servo moves back to ready position
        delay(500);
        lightstate = LOW;                               //light off
      }
    }
  }
}

But as you can see I try more and more confusing things that won't work.
It would be nice if you could point me in the right direction.
Thanks
Logged

UK
Offline Offline
Shannon Member
****
Karma: 184
Posts: 11173
-
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

You're using lightstate to detect changes in the door position but that doesn't work because lightstate doesn't reflect the previous state of the door.

I suggest you detect door changes by explicitly comparing the current state of the door sensor with the previous state.

If the door is opening, turn the light on.

If the door is closing, note the time that the door closed and leave the light on.

If the light is on and the door is closed, compare the current time with the time the door closed to see whether it is time to turn the light off.

Your state variables will be:

A flag recording whether the light is on.
A flag recording whether the door is currently open.
The time at which the door was closed.
Logged

I only provide help via the forum - please do not contact me for private consultancy.

Topsham, Vermont USA
Offline Offline
Edison Member
*
Karma: 23
Posts: 1759
... in The Woods In Vermont
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Hi, To do many things while "delaying" you need to use the techniques shown in "Blink Without Delay" which is in your Arduino IDE "Examples" folder. 
Logged

Regards, Terry King terry@yourduino.com  - Check great prices, devices and Arduino-related boards at http://YourDuino.com
HOW-TO: http://ArduinoInfo.Info

Offline Offline
Newbie
*
Karma: 0
Posts: 16
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Code:
#include <Servo.h>

Servo myservo3;
int doorpin = 8;

unsigned long doortimer = 0;
unsigned long time;
unsigned long current_time;
int lightstate = LOW;

void setup(){
  myservo3.attach(5);
  pinMode(doorpin, INPUT);
}

void loop()
{

  if(digitalRead(doorpin) == LOW)     //door open
  {

    if(lightstate == LOW)              //light off
    {
      myservo3.write(126);            //servo pushes lightswitch on
      delay(500);
      myservo3.write(90);             //servo moves back to ready position
      delay(500);
      lightstate = HIGH;
     
      doortimer=5000;              //set doortimer to 5000 millisec
      time=millis();                    //get time since board started
      current_time=time;              //set current time to the same

                     
    }

  }


  if((current_time-time>doortimer)&&doortimer>0){
     myservo3.write(59);             //servo pushes lightswitch off
        delay(500);
        myservo3.write(90);             //servo moves back to ready position
        delay(500);
        lightstate = LOW;               //light is off
   
    doortimer=0;                       // reset

  }
 else if(doortimer>0){
  current_time=millis();         //update current time
 
  }

}




You just have to make it start after the door is closed.
« Last Edit: August 18, 2012, 09:20:38 am by Tentationem » Logged

Germany
Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Thank you all very much.

Tentationem, your sketch is a big help and terryking228 is of course right that I have to use the blink without delay way. But I just started using the Arduino and programing about two weeks ago and the millis() are still quiet confusing for me. Although I understand the general idea it is difficult for me to adapt it to different problems.

You helped me a lot! Thank you.
Logged

Offline Offline
God Member
*****
Karma: 7
Posts: 647
"In this house, we obey the Laws of Thermodynamics" Homer J. Simpson
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

You seem to be using a servo to physically push a normal switch. Would you not be better using a relay to switch the power to the light?
Logged

Germany
Offline Offline
Newbie
*
Karma: 0
Posts: 5
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Yes radman,

a relay would probably be the most professional approach, but since I only rent I don't wanna mess to much with the wiring of the house. And this way I don't have to worry about high currents. I recently read about different relay shields and they look very interesting but not for this project. I thought about using a relay to transfer my doorbell incoming signal to the arduino.
But lights first.
The above code works great, I just had to change one of the curly brackets to make the timer start when the door closes. 

p.s.: I love your Simpsons quote it's one of the best, especially since the perpetual motion machine Lisa built gets faster and faster,           hilarious. And I don't think it's optional to obey the laws of thermodynamics.
Logged

Offline Offline
God Member
*****
Karma: 7
Posts: 647
"In this house, we obey the Laws of Thermodynamics" Homer J. Simpson
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
I love your Simpsons quote it's one of the best
Homer is just too close to the truth sometimes. There are some really good perpetual motion machines on youtube. Somebody else has a good line about Ohms Law, but I cannot remember it just now.
Logged

Pages: [1]   Go Up
Jump to: