I wrote a program for a night light. There are 4 modes:
- on,
- adjustable brightness,
- timer,
- off.
For input, instead of using a button, I am using a distance sensor. Once a certain distance is read (eg. when passing your hand over the distance sensor) it changes to the next mode.
For the adjustable brightness mode it reads the distance sensor and is mapped to a PWM. The output pin is connected to a MOSFET which is switching a 12 volt LED.
This seems a slow way to cycle thru the system. I would like instead, if the user waved their hand over the sensor, it would turn on or off. However, if the user waited for 3 seconds with their hand over the sensor it would enable a dimmable mode. I'm not concerned about the timer function anymore and will be removing it.
All the code is already there except I need help writing a function that will keep track of how long its been reading a certain distance. Let's say for instance if the sensor reads a distance between 1 inch to 3 inches for 3 seconds it will then go into the dimmable mode. If it's under that then it will only toggle on/off. If the hand remains longer then 3 seconds it will also trigger the dimmable mode.
//----------------------------------------------------------
// USING A DISTANCE SENSOR TO CYCLE THRU DIFFERENT MODE
// FOR AN LED NIGHT LIGHT
// vonderasche
//----------------------------------------------------------
// declares library for distance sensor
#include <NewPing.h>
// constants
#define TRIGGER_PIN 12
#define ECHO_PIN 13
#define MAX_DISTANCE 200
const unsigned long onTime = 5000;
const unsigned long onTimer = 1200000;
int state = 1;
// declares NewPing object
NewPing sonar(TRIGGER_PIN, ECHO_PIN, MAX_DISTANCE);
void setup() {
Serial.begin(9600);
}
void loop() {
delay(50);
// take distances reading
int distance = sonar.ping_in();
static enum { ON, ADJUST, TIMER } state;
// if distance range is between certain values switch the state
if (distance > 1 && distance < 3) {
switch(state) {
case ON:
{
// turns LEDs on
Serial.println("ON");
analogWrite(3, 255);
analogWrite(5, 255);
state = ADJUST;
delay(1000);
}
break;
case ADJUST:
{
// allows user to set brightness based on hand distance to sensor
Serial.println("Adjusting Brightness");
int distance2 = 0;
int mappedBrightness = 0;
unsigned long previousMillis = millis();
unsigned long currentMillis = millis();
// timer for setting brightness
while ((currentMillis - previousMillis) < onTime) {
int distance2 = sonar.ping_in();
if (distance2 >= 1 && distance2 <= 6) {
mappedBrightness = map(distance2, 0, 6, 13, 255);
analogWrite(3, mappedBrightness);
analogWrite(5, mappedBrightness);
}
currentMillis = millis();
}
Serial.print("Mapped Brightness = ");
Serial.println(mappedBrightness);
delay(1000);
state = TIMER;
}
break;
case TIMER:
{
Serial.println("TIMER - 20 MINS");
// variable declaration
unsigned long ontime = 50;
unsigned long previousMillis = millis();
unsigned long currentMillis = millis();
// dims leds to 25 percent
analogWrite(3, 64);
analogWrite(5, 64);
delay(1000);
// timer for leds
while ((currentMillis - previousMillis) < onTimer) {
int distance2 = sonar.ping_in();
//breaks timer if hand swipe
if (distance2 >= 1 && distance2 <= 4) {
break;
}
currentMillis = millis();
}
// turn off leds - either hand swipe happened or timer is up
Serial.println("Turn off LEDs.");
analogWrite(3, 0);
analogWrite(5, 0);
delay(1000);
state = ON;
}
break;
}
}
}
case ADJUST:
state or planned for another state ?