It works for me. I’ve change to to have an option to turn off thermostat instead of setback. Here’s the code so far:
I also wanted to create a resume on motion to previous setting when motion happens within 20 mins of turning off.
/**
preferences {
section("On this thermostat... ") {
input "thermostat", "capability.thermostat"
}
section("When movement is detected by any of these...") {
input "motion", "capability.motionSensor", title: "Motion Sensor(s)", multiple: true, required: false
}
section("Or when any of these are open...") {
input "contact", "capability.contactSensor", title: "Contact Sensor", multiple: true, required: false
}
section("Delay the no motion event...") {
input "delayNoMotionEvent", "number", title: "Minutes", description: "60 minutes", required: false
}
section("Set thermostat to Off when no motion timed-out") {
input "noMotionOff", "boolean", title: "Yes?"
}
section("Enable motion after idle resume") {
input "motionAfterIdle", "boolean", title: "Yes?"
}
section("Resume the motion event...") {
input "resumeMotionEvent", "number", title: "Minutes", description: "20 minutes", required: false
}
section("Set motion air conditioning setting..."){
input "coolingSetpointMotion", "number", title: "Degrees?"
}
section("Set motion heat setting...") {
input "heatingSetpointMotion", "number", title: "Degrees?"
}
section("Set no motion air conditioning setting..."){
input "coolingSetpointNoMotion", "number", title: "Degrees?"
}
section("Set no motion heat setting...") {
input "heatingSetpointNoMotion", "number", title: "Degrees?"
}
}
def installed()
{
subscribe(motion, “motion”, eventHandler)
subscribe(contact, “contact”, eventHandler)
}
def updated()
{
unsubscribe()
subscribe(motion, "motion", eventHandler)
subscribe(contact, "contact", eventHandler)
}
def eventHandler(evt)
{
log.debug “device: $device, value: $evt.value, event: $evt, settings: $settings, handlerName: ${evt.handlerName}”
// set the delay, defaulting to 60 minutes
def delay = (delayNoMotionEvent != null && delayNoMotionEvent != "") ? delayNoMotionEvent * 60 : 3600
// set the resumedelay, defaulting to 20 minutes
def resumedelay = (resumeMotionEvent != null && resumeMotionEvent != "") ? resumeMotionEvent * 20 : 3600
// unschedule delay since motion is detected and set temp to active state
if (evt.value == 'active' || evt.value == 'open')
{
log.debug "unscheduling no motion temp timer"
unschedule(setTemp)
log.debug "setting motion temp"
setTemp('motion')
}
else
{
// schedule delay since no motion on any device is found
if (motion.find{it.currentState('motion').value == "active"} == null &&
contact.find{it.currentState('contact').value == "open"} == null)
{
log.debug "will set no motion temp in $delay secs"
runIn(delay, setTemp)
}
}
}
def setTemp(state)
{
if (state == "motion")
{
// thermostat.setCoolingSetpoint(coolingSetpointMotion)
// thermostat.setHeatingSetpoint(heatingSetpointMotion)
}
else
{
if (noMotionOff) {
thermostat.off()
}
else
{
thermostat.setCoolingSetpoint(coolingSetpointNoMotion)
thermostat.setHeatingSetpoint(heatingSetpointNoMotion)
}
}
}