Created
March 26, 2016 23:35
-
-
Save technobly/f040eb7fa751600c4e93 to your computer and use it in GitHub Desktop.
Particle Asset Tracker Wake on Accelerometer bump, sleep after 10 seconds of no motion
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Uncomment for BUILD IDE | |
// #pragma SPARK_NO_PREPROCESSOR | |
#include <math.h> | |
#include "math.h" | |
#include <ctype.h> | |
// Particle application functions | |
#include "application.h" | |
// If compiling locally, need Adafruit_LIS3DH.cpp/.h and Adafruit_Sensor.h | |
#include "Adafruit_LIS3DH.h" | |
Adafruit_LIS3DH accel = Adafruit_LIS3DH(A2, A5, A4, A3); | |
// Configure where DEBUG_D() calls go to | |
Serial1DebugOutput debugOutput; // Serial1 | |
// SerialDebugOutput debugOutput; // Serial USB | |
SYSTEM_MODE(MANUAL); | |
// lets wakeup every 6 hours and check in (seconds) | |
#define HOW_LONG_SHOULD_WE_SLEEP (6 * 60 * 60) | |
unsigned long lastUpdate = 0; | |
#define UPDATE_INTERVAL_MS (10) | |
unsigned long noMotionCounter = 0; | |
#define SLEEP_AFTER_10S_NO_MOTION (10 * 1000) | |
#define now millis() | |
bool timeToSleep = false; | |
void initAccel() { | |
// for blinking. | |
pinMode(D7, OUTPUT); | |
digitalWrite(D7, LOW); | |
accel.begin(LIS3DH_DEFAULT_ADDRESS); | |
// Default to 5kHz low-power sampling | |
accel.setDataRate(LIS3DH_DATARATE_LOWPOWER_5KHZ); | |
accel.writeRegister8(LIS3DH_REG_CTRL2, 0xC9); // Enable HP Filter with AUTORESET on interrupt | |
accel.writeRegister8(LIS3DH_REG_CTRL3, 0x40); // Enable AOI interrupt | |
// Set 2g range | |
accel.setRange(LIS3DH_RANGE_2_G); | |
accel.writeRegister8(LIS3DH_REG_CTRL5, 0x08); // latch interrupt so we can read when ready if blocked | |
accel.writeRegister8(LIS3DH_REG_INT1THS, 0x08); // Set threshold to 8 (relatively low?) | |
accel.writeRegister8(LIS3DH_REG_INT1DUR, 0x01); // Set duration to 1 cycle | |
accel.writeRegister8(LIS3DH_REG_INT1CFG, 0x2A); // Enable X,Y,Z interrupt generation | |
// Reset HP Filter | |
accel.readRegister8(LIS3DH_REG_INT1SRC); | |
accel.readRegister8(LIS3DH_REG_CTRL2); | |
} | |
void button_clicked(system_event_t event, int param) | |
{ | |
int times = system_button_clicks(param); | |
DEBUG_D("Button %d pressed %d times...\r\n", times, param); | |
if(times == 3) { | |
timeToSleep = true; | |
} else { | |
DEBUG_D("Mode button %d clicks is unknown! Maybe this is a system handled number?\r\n", event); | |
} | |
} | |
void setup() { | |
initAccel(); | |
// Setup manual sleep button clicks | |
System.on(button_final_click, button_clicked); | |
} | |
bool hasMotion() { | |
bool motion = digitalRead(WKP); | |
digitalWrite(D7, (motion) ? HIGH : LOW); | |
// Reset accelerometer interrupt (latched) | |
accel.readRegister8(LIS3DH_REG_INT1SRC); | |
return motion; | |
} | |
void checkMotion() { | |
if(hasMotion()) { | |
noMotionCounter = 0; | |
DEBUG_D("BUMP! "); | |
} | |
else { | |
noMotionCounter += UPDATE_INTERVAL_MS; | |
} | |
} | |
void sleepNow() { | |
System.sleep(SLEEP_MODE_DEEP, HOW_LONG_SHOULD_WE_SLEEP); | |
} | |
void checkSleep() { | |
if (timeToSleep) { | |
DEBUG_D("\r\nManually deep sleeping for %ds but will wake up for motion...\r\n", HOW_LONG_SHOULD_WE_SLEEP); | |
delay(100); | |
sleepNow(); | |
} | |
} | |
void loop() { | |
if (now - lastUpdate > UPDATE_INTERVAL_MS) { | |
lastUpdate = now; | |
checkMotion(); | |
checkSleep(); | |
} | |
if (noMotionCounter > SLEEP_AFTER_10S_NO_MOTION) { | |
DEBUG_D("\r\nNo motion for %ds, sleeping for %ds but will wake up for motion...\r\n", SLEEP_AFTER_10S_NO_MOTION/1000, HOW_LONG_SHOULD_WE_SLEEP); | |
delay(100); | |
sleepNow(); | |
} | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment