Files
SmartThingsPublic/smartapps/imbrianj/nobody-home.src/nobody-home.groovy
2015-08-04 15:49:03 -07:00

165 lines
3.8 KiB
Groovy

/**
* Nobody Home
*
* Author: brian@bevey.org
* Date: 12/19/14
*
* Monitors a set of presence detectors and triggers a mode change when everyone has left.
* When everyone has left, sets mode to a new defined mode.
* When at least one person returns home, set the mode back to a new defined mode.
* When someone is home - or upon entering the home, their mode may change dependent on sunrise / sunset.
*/
definition(
name: "Nobody Home",
namespace: "imbrianj",
author: "brian@bevey.org",
description: "When everyone leaves, change mode. If at least one person home, switch mode based on sun position.",
category: "Mode Magic",
iconUrl: "https://s3.amazonaws.com/smartapp-icons/Convenience/Cat-Convenience.png",
iconX2Url: "https://s3.amazonaws.com/smartapp-icons/Convenience/Cat-Convenience%402x.png"
)
preferences {
section("When all of these people leave home") {
input "people", "capability.presenceSensor", multiple: true
}
section("Change to this mode to...") {
input "newAwayMode", "mode", title: "Everyone is away"
input "newSunsetMode", "mode", title: "At least one person home and nightfall"
input "newSunriseMode", "mode", title: "At least one person home and sunrise"
}
section("Away threshold (defaults to 10 min)") {
input "awayThreshold", "decimal", title: "Number of minutes", required: false
}
section("Notifications") {
input "sendPushMessage", "enum", title: "Send a push notification?", metadata:[values:["Yes","No"]], required:false
}
}
def installed() {
init()
}
def updated() {
unsubscribe()
init()
}
def init() {
subscribe(people, "presence", presence)
subscribe(location, "sunrise", setSunrise)
subscribe(location, "sunset", setSunset)
state.sunMode = location.mode
}
def setSunrise(evt) {
changeSunMode(newSunriseMode)
}
def setSunset(evt) {
changeSunMode(newSunsetMode)
}
def changeSunMode(newMode) {
state.sunMode = newMode
if(everyoneIsAway() && (location.mode == newAwayMode)) {
log.debug("Mode is away, not evaluating")
}
else if(location.mode != newMode) {
def message = "${app.label} changed your mode to '${newMode}'"
send(message)
setLocationMode(newMode)
}
else {
log.debug("Mode is the same, not evaluating")
}
}
def presence(evt) {
if(evt.value == "not present") {
log.debug("Checking if everyone is away")
if(everyoneIsAway()) {
log.info("Starting ${newAwayMode} sequence")
def delay = (awayThreshold != null && awayThreshold != "") ? awayThreshold * 60 : 10 * 60
runIn(delay, "setAway")
}
}
else {
if(location.mode != state.sunMode) {
log.debug("Checking if anyone is home")
if(anyoneIsHome()) {
log.info("Starting ${state.sunMode} sequence")
changeSunMode(state.sunMode)
}
}
else {
log.debug("Mode is the same, not evaluating")
}
}
}
def setAway() {
if(everyoneIsAway()) {
if(location.mode != newAwayMode) {
def message = "${app.label} changed your mode to '${newAwayMode}' because everyone left home"
log.info(message)
send(message)
setLocationMode(newAwayMode)
}
else {
log.debug("Mode is the same, not evaluating")
}
}
else {
log.info("Somebody returned home before we set to '${newAwayMode}'")
}
}
private everyoneIsAway() {
def result = true
if(people.findAll { it?.currentPresence == "present" }) {
result = false
}
log.debug("everyoneIsAway: ${result}")
return result
}
private anyoneIsHome() {
def result = false
if(people.findAll { it?.currentPresence == "present" }) {
result = true
}
log.debug("anyoneIsHome: ${result}")
return result
}
private send(msg) {
if(sendPushMessage != "No") {
log.debug("Sending push message")
sendPush(msg)
}
log.debug(msg)
}