Skip to content

Instantly share code, notes, and snippets.

@ajesler
Created March 21, 2018 10:09
Show Gist options
  • Save ajesler/088d10418cd31bf969172a6cfa60cfb4 to your computer and use it in GitHub Desktop.
Save ajesler/088d10418cd31bf969172a6cfa60cfb4 to your computer and use it in GitHub Desktop.
/*
A Photon sketch for detecting motion.
This sketch will fire an event when motion is detected, and when it is lost.
The motion timeout is done by the PIR sensor.
*/
const int LED = D7;
const int PIR1 = D4;
const int PIR2 = D5;
const int TTL = 60; // this doesn't actually do anything, but is required.
// The minimum interval between consectutive events of the same type
const int PUBLISH_EVENT_MIN_INTERVAL = 30; // seconds
const int MOTION_DETECTED = 2;
const int MOTION_TIMEOUT = 1;
int lastPirReading = -1;
int lastPublishedAt = 0;
int lastPublishedEventType = 0;
void setup() {
pinMode(LED, OUTPUT);
pinMode(PIR1, INPUT);
pinMode(PIR2, INPUT);
Particle.function("det-reset", detectionReset);
Particle.function("det-status", detectionStatus);
Particle.function("det-trigger", detectionTrigger);
Particle.function("det-timeout", detectionTimeout);
initializeDetectionState();
}
void loop() {
int reading = pirReading();
if (reading != lastPirReading) {
if (reading == HIGH) {
motionDetected();
} else {
motionTimeout();
}
lastPirReading = reading;
}
}
/*
PIR FUNCTIONS
*/
void initializeDetectionState() {
lastPirReading = -1;
lastPublishedAt = 0;
lastPublishedEventType = 0;
}
int pirReading() {
int pir1Reading = digitalRead(PIR1);
int pir2Reading = digitalRead(PIR2);
if (pir1Reading == HIGH || pir2Reading == HIGH) {
return HIGH;
} else {
return LOW;
}
}
bool motionDetected() {
digitalWrite(LED, HIGH);
return publish(MOTION_DETECTED);
}
bool motionTimeout() {
digitalWrite(LED, LOW);
return publish(MOTION_TIMEOUT);
}
bool canPublish(int eventType) {
if (eventType != lastPublishedEventType) {
return true;
} else {
int currentTime = Time.now();
return (currentTime - lastPublishedAt) > PUBLISH_EVENT_MIN_INTERVAL;
}
}
bool publish(int eventType) {
if (canPublish(eventType)) {
String name = eventName(eventType);
bool success = Particle.publish(name, NULL, TTL, PRIVATE);
if (success) {
lastPublishedAt = Time.now();
lastPublishedEventType = eventType;
}
return success;
}
return false;
}
String eventName(int eventType) {
String name = "error";
switch (eventType) {
case MOTION_TIMEOUT:
name = "motion-timeout";
break;
case MOTION_DETECTED:
name = "motion-detected";
break;
}
return name;
}
/*
PHOTON REMOTE COMMANDS
*/
int detectionReset(String args) {
initializeDetectionState();
return 1;
}
int detectionStatus(String args) {
return lastPirReading;
}
int detectionTrigger(String args) {
return motionDetected() ? 1 : 0;
}
int detectionTimeout(String args) {
return motionTimeout() ? 1 : 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment