Its function is simple: IF time is between 20PM and 6AM AND Infrared sensor detects movement THEN light up LED strip.
And it works great - for like 40 minutes. After that it stops working until I press the reset button on the Arduino. At which point it works again! I ruled out the electronics because I rebuilt it on a breadboard with a different Arduino.
That makes me believe the issue is the code. It feels like a memory leak to me. I can't spot one though. Does anyone maybe see one?
#include <FastLED.h>
#include <Wire.h>
#include <RTClib.h>
RTC_DS3231 rtc;
#define LED_PIN 8
#define NUM_LEDS 60
int pirPin = 2; // Input for HC-S501
CRGB leds[NUM_LEDS];
int pirValue; // Place to store read PIR Value
void setup() {
Serial.begin(9600);
pinMode(pirPin, INPUT);
FastLED.addLeds<WS2812, LED_PIN, GRB>(leds, NUM_LEDS);
rtc.begin();
rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));//auto update from computer time
}
void loop() {
pirValue = digitalRead(pirPin);
DateTime nowTime = rtc.now();
Serial.print(nowTime.hour());
Serial.print("pir:/");
Serial.print(pirValue);
if (pirValue != 0) {
if (nowTime.hour() >= 20 || nowTime.hour() <= 6) {
for (int i = 0; i < NUM_LEDS; i++) {
leds[i] = CRGB(127, 73, 20);
}
FastLED.show();
delay(15000);
}
} else {
FastLED.clear();
FastLED.show();
}
}
I'm not following your question about the signal from the PIR. I do not have a pull up or pull down resistor. The component is an HC-SR501 if that helps.
I've now added an image of the schematic. I can't provide photos of the physical components themselves at this moment however, but I had recreated everything from scratch following the schematic with the same results.
I can see how that would help reduce its workload, but do you believe that would solve the issue?
If it's a memory leak it would definitely make the issue appear a lot more slowly I suppose.
The only indication I have is its behaviour, but I'll be clear in that I don't know if it's a memory leak.
It functions for a period of time, and then stops until it's reset. The period of time in which it functions is consistent.
I don't know how else to ask it more clearly, what does the PIR output? Is it a relay contact? A transistor? MOSFET? Open collector / drain? What exactly? What does the datasheet say?
The PIR gives a digital pulse - high 3.3v when triggered and low 0v when idle.
I'm trying to wrap my head around what is meant by output in this context as I'm new to electronics, so thanks for bearing with me.
When I read the value through the following I'll just get a 0/1 based on state.
Also set the Trigger to H to keep the PIR Output HIGH until 15sec. after the LAST detection of movement.
Or set the Trigger to L to keep PIR Output HIGH for 15sec. after the FIRST detection of movement.
FastLED.clear(); is not doing what you think. Turn off the LED's the same way you turned them on:
for (int i = 0; i < NUM_LEDS; i++) {
leds[i] = CRGB(0, 0, 0); // turn off LED's
}
Full code w/ changes:
#include <FastLED.h>
#include <Wire.h>
#include <RTClib.h>
RTC_DS3231 rtc;
#define LED_PIN 8
#define NUM_LEDS 60
int pirPin = 2; // Input for HC-S501
CRGB leds[NUM_LEDS];
int pirValue; // Place to store read PIR Value
int nowHour; // store Hour;
void setup() {
Serial.begin(9600);
pinMode(pirPin, INPUT);
FastLED.addLeds<WS2812, LED_PIN, GRB>(leds, NUM_LEDS);
rtc.begin();
rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));//auto update from computer time
}
void loop() {
DateTime nowTime = rtc.now();
nowHour = nowTime.hour();
pirValue = digitalRead(pirPin);
Serial.print(nowHour);
Serial.print("pir:/");
Serial.print(pirValue);
if (pirValue != 0) {
if (nowHour >= 20 || nowHour <= 6) {
for (int i = 0; i < NUM_LEDS; i++) {
leds[i] = CRGB(127, 73, 20);
}
FastLED.show();
// delay(15000); // This delay is not needed because the PIR sensor can take care of this for us
}
} else {
for (int i = 0; i < NUM_LEDS; i++) {
leds[i] = CRGB(0, 0, 0); // turn off LED's
}
FastLED.show();
}
}
OK, thanks.
The only thing I can see from what you've showed is there should be a capacitor across the power of the LED strip close to where it's powered. Maybe 470μF or something, exact value not important. The layout and quality of the wiring might have an effect, which is why I want the photos. I can't see anything wrong with the code but there are other people helping you who are better than me at spotting code problems.
@gfvalvo asked what happens when it stops working, that might be useful information.
What do the serial prints show when it stops working?
Just checking here ... do you realize that comment is incorrect? The statement does not do that. Rather, every time your Arduino board is powered up or reset, it sets the RTC to the time when your program was compiled. Not the current time and it involves no data transfer with the PC.
So I'll ask again, what do the Serial.print() statements of your variables show when the program "stops working"?
Wasn’t aware of that, hadn’t seen mention of it in the strip‘s manuals but I’ll add one. Thanks.
That is very good to know, and that explains a different behavior I experienced once, thanks for the good spot.
I’ll be monitoring that when I get back to the project, at the time of writing this post I didn’t have a device I could use to monitor the output at the location.