Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save kacole2/9ff9629f6db114343dbd4b2e7ad83f79 to your computer and use it in GitHub Desktop.
Save kacole2/9ff9629f6db114343dbd4b2e7ad83f79 to your computer and use it in GitHub Desktop.
ST_Anything Example for Doors and Window contact sensors
//******************************************************************************************
// File: ST_Anything_Multiples_Thingshield_570Doors.ino
// Authors: Dan G Ogorchock & Daniel J Ogorchock (Father and Son)
//
// Summary: This Arduino Sketch, along with the ST_Anything library and the revised SmartThings
// library, demonstrates the ability of one Arduino + SmartThings Shield to
// implement a multi input/output custom device for integration into SmartThings.
// The ST_Anything library takes care of all of the work to schedule device updates
// as well as all communications with the SmartThings Shield.
//
// ST_Anything_Multiples implements the following ST Capabilities in multiples of 2 as a demo of what is possible with a single Arduino
// - 2 x Door Control devices (used typically for Garage Doors - input pin (contact sensor) and output pin (relay switch)
// - 2 x Contact Sensor devices (used to monitor magnetic door sensors)
// - 2 x Switch devices (used to turn on a digital output (e.g. LED, relay, etc...)
// - 2 x Water Sensor devices (using an analog input pin to measure voltage from a water detector baord)
// - 2 x Illuminance Measurement devices (using a photoresitor attached to ananlog input)
// - 2 x Voltage Measurement devices (using a photoresitor attached to ananlog input)
// - 2 x Smoke Detector devices (using simple digital input)
// - 2 x Carbon Monoxide Detector devices (using simple digital input)
// - 2 x Motion devices (used to detect motion)
// - 2 x Temperature Measurement devices (Temperature from DHT22 device)
// - 2 x Humidity Measurement devices (Humidity from DHT22 device)
// - 2 x Relay Switch devices (used to turn on a digital output for a set number of cycles And On/Off times (e.g.relay, etc...))
// - 2 x Button devices (sends "pushed" if held for less than 1 second, else sends "held"
// - 2 x Alarm devices - 1 siren only, 1 siren and strobe (using simple digital outputs)
// - 2 x Dimmer Switch devices - uses 2 digital outputs, one for on/off and one for pwm level
// - 2 x MQ-2 Smoke Detector devices (using simple analog input compared to user defined limit)
//
// During the development of this re-usable library, it became apparent that the
// Arduino UNO R3's very limited 2K of SRAM was very limiting in the number of
// devices that could be implemented simultaneously. A tremendous amount of effort
// has gone into reducing the SRAM usage, including siginificant improvements to
// the SmartThings Arduino library. The SmartThings library was also modified to
// include support for using Hardware Serial port(s) on the UNO, MEGA, and Leonardo.
// During testing, it was determined that the Hardware Serial ports provide much
// better performance and reliability versus the SoftwareSerial library. Also, the
// MEGA 2560's 8K of SRAM is well worth the few extra dollars to save your sanity
// versus always running out of SRAM on the UNO R3. The MEGA 2560 also has 4 Hardware
// serial ports (i.e. UARTS) which makes it very easy to use Hardware Serial instead
// of SoftwareSerial, while still being able to see debug data on the USB serial
// console port (pins 0 & 1).
//
// Note: We did not have a Leonardo for testing, but did fully test on UNO R3 and
// MEGA 2560 using both SoftwareSerial and Hardware Serial communications to the
// Thing Shield. This sketch, due to the number of devices implemented, requires an
// Arduino MEGA 2560 wuth ThingShield wired to "Serial3"
//
// Change History:
//
// Date Who What
// ---- --- ----
// 2015-01-03 Dan & Daniel Original Creation
// 2015-03-28 Dan Ogorchock Removed RCSwitch #include now that the libraries are split up
// 2015-03-31 Daniel O. Memory optimizations utilizing progmem
// 2015-08-23 Dan Ogorchock Added optional alarm limit argument to water sensor
// 2017-02-12 Dan Ogorchock Revised to use the new SMartThings v2.0 library
// 2017-04-22 Dan Ogorchock Added Voltage, Carbon Monoxide, and Alarm with Strobe
// 2017-04-25 Dan Ogorchock Revised for Parent/Child Composite Device Handler
// 2017-11-21 Dan Ogorchock Fixed Arduino UNO compatability (missing pinRx and pinTx definitions)
//
//******************************************************************************************
//******************************************************************************************
// SmartThings Library for Arduino Shield
//******************************************************************************************
#include <SmartThingsThingShield.h> //Library to provide API to the SmartThings ThingShield
//******************************************************************************************
// ST_Anything Library
//******************************************************************************************
#include <Constants.h> //Constants.h is designed to be modified by the end user to adjust behavior of the ST_Anything library
#include <Device.h> //Generic Device Class, inherited by Sensor and Executor classes
#include <Sensor.h> //Generic Sensor Class, typically provides data to ST Cloud (e.g. Temperature, Motion, etc...)
#include <Executor.h> //Generic Executor Class, typically receives data from ST Cloud (e.g. Switch)
#include <InterruptSensor.h> //Generic Interrupt "Sensor" Class, waits for change of state on digital input
#include <PollingSensor.h> //Generic Polling "Sensor" Class, polls Arduino pins periodically
#include <Everything.h> //Master Brain of ST_Anything library that ties everything together and performs ST Shield communications
#include <PS_Illuminance.h> //Implements a Polling Sensor (PS) to measure light levels via a photo resistor on an analog input pin
#include <PS_Voltage.h> //Implements a Polling Sensor (PS) to measure voltage on an analog input pin
#include <PS_TemperatureHumidity.h> //Implements a Polling Sensor (PS) to measure Temperature and Humidity via DHT library
#include <PS_Water.h> //Implements a Polling Sensor (PS) to measure presence of water (i.e. leak detector) on an analog input pin
#include <PS_MQ2_Smoke.h> //Implements an Polling Sensor (PS) to monitor the status of an analog input pin from a MQ2 sensor
#include <IS_Motion.h> //Implements an Interrupt Sensor (IS) to detect motion via a PIR sensor on a digital input pin
#include <IS_Contact.h> //Implements an Interrupt Sensor (IS) to monitor the status of a digital input pin
#include <IS_Smoke.h> //Implements an Interrupt Sensor (IS) to monitor the status of a digital input pin
#include <IS_CarbonMonoxide.h> //Implements an Interrupt Sensor (IS) to monitor the status of a digital input pin
#include <IS_DoorControl.h> //Implements an Interrupt Sensor (IS) and Executor to monitor the status of a digital input pin and control a digital output pin
#include <IS_Button.h> //Implements an Interrupt Sensor (IS) to monitor the status of a digital input pin for button presses
#include <EX_Switch.h> //Implements an Executor (EX) via a digital output to a relay
#include <EX_Alarm.h> //Implements Executor (EX)as an Alarm capability with Siren and Strobe via digital outputs to relays
#include <S_TimedRelay.h> //Implements a Sensor to control a digital output pin with timing/cycle repeat capabilities
#include <EX_Switch_Dim.h> //Implements an Executor (EX) for a switch (on/off) and pwm output (level) uses 2 digital output pins
//******************************************************************************************
//Define which Arduino Pins will be used for each device
// Notes: -Serial Communications Pins are defined in Constants.h (avoid pins 0,1,2,3
// for inputs and output devices below as they may be used for communications)
// -Always avoid Pin 6 as it is reserved by the SmartThings Shield
//
//******************************************************************************************
//"RESERVED" pins for SmartThings ThingShield - best to avoid
#define PIN_O_RESERVED 0 //reserved by ThingShield for Serial communications OR USB Serial Monitor
#define PIN_1_RESERVED 1 //reserved by ThingShield for Serial communications OR USB Serial Monitor
#define pinTX 2 //reserved by ThingShield for Serial communications
#define pinRX 3 //reserved by ThingShield for Serial communications
#define PIN_6_RESERVED 6 //reserved by ThingShield (possible future use?)
//House Door Pins
#define PIN_CONTACT_1 5 //PIN_CONTACT_FRONT_DOOR
#define PIN_CONTACT_2 7 //PIN_CONTACT_BACK_DOOR
#define PIN_CONTACT_3 8 //PIN_CONTACT_KITCHEN_DOOR
#define PIN_CONTACT_4 9 //PIN_CONTACT_FAMILY_ROOM_REAR_DOOR
#define PIN_CONTACT_5 10 //PIN_CONTACT_FAMILY_ROOM_PATIO_DOORS
//Window Pins
#define PIN_CONTACT_6 11 //PIN_CONTACT_BASEMENT_WINDOWS
//******************************************************************************************
//st::Everything::callOnMsgSend() optional callback routine. This is a sniffer to monitor
// data being sent to ST. This allows a user to act on data changes locally within the
// Arduino sktech.
//******************************************************************************************
void callback(const String &msg)
{
//Serial.print(F("ST_Anything Callback: Sniffed data = "));
//Serial.println(msg);
//TODO: Add local logic here to take action when a device's value/state is changed
//Masquerade as the ThingShield to send data to the Arduino, as if from the ST Cloud (uncomment and edit following line)
//st::receiveSmartString("Put your command here!"); //use same strings that the Device Handler would send
}
//******************************************************************************************
//Arduino Setup() routine
//******************************************************************************************
void setup()
{
//******************************************************************************************
//Declare each Device that is attached to the Arduino
// Notes: - For each device, there is typically a corresponding "tile" defined in your
// SmartThings Device Hanlder Groovy code, except when using new COMPOSITE Device Handler
// - For details on each device's constructor arguments below, please refer to the
// corresponding header (.h) and program (.cpp) files.
// - The name assigned to each device (1st argument below) must match the Groovy
// Device Handler names. (Note: "temphumid" below is the exception to this rule
// as the DHT sensors produce both "temperature" and "humidity". Data from that
// particular sensor is sent to the ST Hub in two separate updates, one for
// "temperature" and one for "humidity")
// - The new Composite Device Handler is comprised of a Parent DH and various Child
// DH's. The names used below MUST not be changed for the Automatic Creation of
// child devices to work properly. Simply increment the number by +1 for each duplicate
// device (e.g. contact1, contact2, contact3, etc...) You can rename the Child Devices
// to match your specific use case in the ST Phone Application.
//******************************************************************************************
//Interrupt Sensors
static st::IS_Contact sensor1(F("contact1"), PIN_CONTACT_1, LOW, true, 500); //frontDoor, PIN_CONTACT_FRONT_DOOR
static st::IS_Contact sensor2(F("contact2"), PIN_CONTACT_2, LOW, true, 500); //backDoor, PIN_CONTACT_BACK_DOOR
static st::IS_Contact sensor3(F("contact3"), PIN_CONTACT_3, LOW, true, 500); //kitchenDoor, PIN_CONTACT_KITCHEN_DOOR
static st::IS_Contact sensor4(F("contact4"), PIN_CONTACT_4, LOW, true, 500); //familyRoomRearDoor, PIN_CONTACT_FAMILY_ROOM_REAR_DOOR
static st::IS_Contact sensor5(F("contact5"), PIN_CONTACT_5, LOW, true, 500); //familyRoomPatioDoors, PIN_CONTACT_FAMILY_ROOM_PATIO_DOORS
static st::IS_Contact sensor6(F("contact6"), PIN_CONTACT_6, LOW, true, 500); //basementWindows, PIN_CONTACT_BASEMENT_WINDOWS
//*****************************************************************************
// Configure debug print output from each main class
//*****************************************************************************
st::Everything::debug=true;
st::Executor::debug=true;
st::Device::debug=true;
st::PollingSensor::debug=true;
st::InterruptSensor::debug=true;
//*****************************************************************************
//Initialize the "Everything" Class
//*****************************************************************************
//Initialize the optional local callback routine (safe to comment out if not desired)
st::Everything::callOnMsgSend = callback;
//Create the SmartThings Thingshield Communications Object based on Arduino Model
#if defined(ARDUINO_AVR_UNO) || defined(ARDUINO_AVR_NANO) || defined(ARDUINO_AVR_MINI) //Arduino UNO, NANO, MINI
st::Everything::SmartThing = new st::SmartThingsThingShield(pinRX, pinTX, st::receiveSmartString); //Use Software Serial
#elif defined(ARDUINO_AVR_LEONARDO) //Arduino Leonardo
st::Everything::SmartThing = new st::SmartThingsThingShield(&Serial1, st::receiveSmartString); //Use Hardware Serial
#elif defined(ARDUINO_AVR_MEGA) || defined(ARDUINO_AVR_MEGA2560) //Arduino MEGA 1280 or 2560
st::Everything::SmartThing = new st::SmartThingsThingShield(&Serial3, st::receiveSmartString); //Use Hardware Serial
#else
//assume user is using an UNO for the unknown case
st::Everything::SmartThing = new st::SmartThingsThingShield(pinRX, pinTX, st::receiveSmartString); //Software Serial
#endif
//Run the Everything class' init() routine which establishes communications with SmartThings
st::Everything::init();
//*****************************************************************************
//Add each sensor to the "Everything" Class
//*****************************************************************************
st::Everything::addSensor(&sensor1);
st::Everything::addSensor(&sensor2);
st::Everything::addSensor(&sensor3);
st::Everything::addSensor(&sensor4);
st::Everything::addSensor(&sensor5);
st::Everything::addSensor(&sensor6);
//*****************************************************************************
//Initialize each of the devices which were added to the Everything Class
//*****************************************************************************
st::Everything::initDevices();
}
//******************************************************************************************
//Arduino Loop() routine
//******************************************************************************************
void loop()
{
//*****************************************************************************
//Execute the Everything run method which takes care of "Everything"
//*****************************************************************************
st::Everything::run();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment