From 8533623b1590dd71014745320349db7ef57d5856 Mon Sep 17 00:00:00 2001 From: larry tavano Date: Sat, 5 Aug 2017 22:59:02 -0700 Subject: [PATCH] MSA-2146: samsung --- .../button-controller.groovy | 688 +++++++++--------- 1 file changed, 344 insertions(+), 344 deletions(-) diff --git a/smartapps/smartthings/button-controller.src/button-controller.groovy b/smartapps/smartthings/button-controller.src/button-controller.groovy index 52e3e79..77cdae9 100644 --- a/smartapps/smartthings/button-controller.src/button-controller.groovy +++ b/smartapps/smartthings/button-controller.src/button-controller.groovy @@ -1,344 +1,344 @@ -/** - * Copyright 2015 SmartThings - * - * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except - * in compliance with the License. You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed - * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License - * for the specific language governing permissions and limitations under the License. - * - * Button Controller - * - * Author: SmartThings - * Date: 2014-5-21 - */ -definition( - name: "Button Controller", - namespace: "smartthings", - author: "SmartThings", - description: "Control devices with buttons like the Aeon Labs Minimote", - category: "Convenience", - iconUrl: "https://s3.amazonaws.com/smartapp-icons/MyApps/Cat-MyApps.png", - iconX2Url: "https://s3.amazonaws.com/smartapp-icons/MyApps/Cat-MyApps@2x.png" -) - -preferences { - page(name: "selectButton") - for (def i=1; i<=8; i++) { - page(name: "configureButton$i") - } - - page(name: "timeIntervalInput", title: "Only during a certain time") { - section { - input "starting", "time", title: "Starting", required: false - input "ending", "time", title: "Ending", required: false - } - } -} - -def selectButton() { - dynamicPage(name: "selectButton", title: "First, select your button device", nextPage: "configureButton1", uninstall: configured()) { - section { - input "buttonDevice", "capability.button", title: "Button", multiple: false, required: true - } - - section(title: "More options", hidden: hideOptionsSection(), hideable: true) { - - def timeLabel = timeIntervalLabel() - - href "timeIntervalInput", title: "Only during a certain time", description: timeLabel ?: "Tap to set", state: timeLabel ? "complete" : null - - input "days", "enum", title: "Only on certain days of the week", multiple: true, required: false, - options: ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"] - - input "modes", "mode", title: "Only when mode is", multiple: true, required: false - } - } -} - -def createPage(pageNum) { - if ((state.numButton == pageNum) || (pageNum == 8)) - state.installCondition = true - dynamicPage(name: "configureButton$pageNum", title: "Set up button $pageNum here", - nextPage: "configureButton${pageNum+1}", install: state.installCondition, uninstall: configured(), getButtonSections(pageNum)) -} - -def configureButton1() { - state.numButton = buttonDevice.currentState("numberOfButtons")?.longValue ?: 4 - log.debug "state variable numButton: ${state.numButton}" - state.installCondition = false - createPage(1) -} -def configureButton2() { - createPage(2) -} - -def configureButton3() { - createPage(3) -} - -def configureButton4() { - createPage(4) -} - -def configureButton5() { - createPage(5) -} - -def configureButton6() { - createPage(6) -} - -def configureButton7() { - createPage(7) -} - -def configureButton8() { - createPage(8) -} - -def getButtonSections(buttonNumber) { - return { - section("Lights") { - input "lights_${buttonNumber}_pushed", "capability.switch", title: "Pushed", multiple: true, required: false - input "lights_${buttonNumber}_held", "capability.switch", title: "Held", multiple: true, required: false - } - section("Locks") { - input "locks_${buttonNumber}_pushed", "capability.lock", title: "Pushed", multiple: true, required: false - input "locks_${buttonNumber}_held", "capability.lock", title: "Held", multiple: true, required: false - } - section("Sonos") { - input "sonos_${buttonNumber}_pushed", "capability.musicPlayer", title: "Pushed", multiple: true, required: false - input "sonos_${buttonNumber}_held", "capability.musicPlayer", title: "Held", multiple: true, required: false - } - section("Modes") { - input "mode_${buttonNumber}_pushed", "mode", title: "Pushed", required: false - input "mode_${buttonNumber}_held", "mode", title: "Held", required: false - } - def phrases = location.helloHome?.getPhrases()*.label - if (phrases) { - section("Hello Home Actions") { - log.trace phrases - input "phrase_${buttonNumber}_pushed", "enum", title: "Pushed", required: false, options: phrases - input "phrase_${buttonNumber}_held", "enum", title: "Held", required: false, options: phrases - } - } - section("Sirens") { - input "sirens_${buttonNumber}_pushed","capability.alarm" ,title: "Pushed", multiple: true, required: false - input "sirens_${buttonNumber}_held", "capability.alarm", title: "Held", multiple: true, required: false - } - - section("Custom Message") { - input "textMessage_${buttonNumber}", "text", title: "Message", required: false - } - - section("Push Notifications") { - input "notifications_${buttonNumber}_pushed","bool" ,title: "Pushed", required: false, defaultValue: false - input "notifications_${buttonNumber}_held", "bool", title: "Held", required: false, defaultValue: false - } - - section("Sms Notifications") { - input "phone_${buttonNumber}_pushed","phone" ,title: "Pushed", required: false - input "phone_${buttonNumber}_held", "phone", title: "Held", required: false - } - } -} - -def installed() { - initialize() -} - -def updated() { - unsubscribe() - initialize() -} - -def initialize() { - subscribe(buttonDevice, "button", buttonEvent) -} - -def configured() { - return buttonDevice || buttonConfigured(1) || buttonConfigured(2) || buttonConfigured(3) || buttonConfigured(4) -} - -def buttonConfigured(idx) { - return settings["lights_$idx_pushed"] || - settings["locks_$idx_pushed"] || - settings["sonos_$idx_pushed"] || - settings["mode_$idx_pushed"] || - settings["notifications_$idx_pushed"] || - settings["sirens_$idx_pushed"] || - settings["notifications_$idx_pushed"] || - settings["phone_$idx_pushed"] -} - -def buttonEvent(evt){ - if(allOk) { - def buttonNumber = evt.data // why doesn't jsonData work? always returning [:] - def value = evt.value - log.debug "buttonEvent: $evt.name = $evt.value ($evt.data)" - log.debug "button: $buttonNumber, value: $value" - - def recentEvents = buttonDevice.eventsSince(new Date(now() - 3000)).findAll{it.value == evt.value && it.data == evt.data} - log.debug "Found ${recentEvents.size()?:0} events in past 3 seconds" - - if(recentEvents.size <= 1){ - switch(buttonNumber) { - case ~/.*1.*/: - executeHandlers(1, value) - break - case ~/.*2.*/: - executeHandlers(2, value) - break - case ~/.*3.*/: - executeHandlers(3, value) - break - case ~/.*4.*/: - executeHandlers(4, value) - break - } - } else { - log.debug "Found recent button press events for $buttonNumber with value $value" - } - } -} - -def executeHandlers(buttonNumber, value) { - log.debug "executeHandlers: $buttonNumber - $value" - - def lights = find('lights', buttonNumber, value) - if (lights != null) toggle(lights) - - def locks = find('locks', buttonNumber, value) - if (locks != null) toggle(locks) - - def sonos = find('sonos', buttonNumber, value) - if (sonos != null) toggle(sonos) - - def mode = find('mode', buttonNumber, value) - if (mode != null) changeMode(mode) - - def phrase = find('phrase', buttonNumber, value) - if (phrase != null) location.helloHome.execute(phrase) - - def textMessage = findMsg('textMessage', buttonNumber) - - def notifications = find('notifications', buttonNumber, value) - if (notifications?.toBoolean()) sendPush(textMessage ?: "Button $buttonNumber was pressed" ) - - def phone = find('phone', buttonNumber, value) - if (phone != null) sendSms(phone, textMessage ?:"Button $buttonNumber was pressed") - - def sirens = find('sirens', buttonNumber, value) - if (sirens != null) toggle(sirens) -} - -def find(type, buttonNumber, value) { - def preferenceName = type + "_" + buttonNumber + "_" + value - def pref = settings[preferenceName] - if(pref != null) { - log.debug "Found: $pref for $preferenceName" - } - - return pref -} - -def findMsg(type, buttonNumber) { - def preferenceName = type + "_" + buttonNumber - def pref = settings[preferenceName] - if(pref != null) { - log.debug "Found: $pref for $preferenceName" - } - - return pref -} - -def toggle(devices) { - log.debug "toggle: $devices = ${devices*.currentValue('switch')}" - - if (devices*.currentValue('switch').contains('on')) { - devices.off() - } - else if (devices*.currentValue('switch').contains('off')) { - devices.on() - } - else if (devices*.currentValue('lock').contains('locked')) { - devices.unlock() - } - else if (devices*.currentValue('lock').contains('unlocked')) { - devices.lock() - } - else if (devices*.currentValue('alarm').contains('off')) { - devices.siren() - } - else { - devices.on() - } -} - -def changeMode(mode) { - log.debug "changeMode: $mode, location.mode = $location.mode, location.modes = $location.modes" - - if (location.mode != mode && location.modes?.find { it.name == mode }) { - setLocationMode(mode) - } -} - -// execution filter methods -private getAllOk() { - modeOk && daysOk && timeOk -} - -private getModeOk() { - def result = !modes || modes.contains(location.mode) - log.trace "modeOk = $result" - result -} - -private getDaysOk() { - def result = true - if (days) { - def df = new java.text.SimpleDateFormat("EEEE") - if (location.timeZone) { - df.setTimeZone(location.timeZone) - } - else { - df.setTimeZone(TimeZone.getTimeZone("America/New_York")) - } - def day = df.format(new Date()) - result = days.contains(day) - } - log.trace "daysOk = $result" - result -} - -private getTimeOk() { - def result = true - if (starting && ending) { - def currTime = now() - def start = timeToday(starting, location.timeZone).time - def stop = timeToday(ending, location.timeZone).time - result = start < stop ? currTime >= start && currTime <= stop : currTime <= stop || currTime >= start - } - log.trace "timeOk = $result" - result -} - -private hhmm(time, fmt = "h:mm a") -{ - def t = timeToday(time, location.timeZone) - def f = new java.text.SimpleDateFormat(fmt) - f.setTimeZone(location.timeZone ?: timeZone(time)) - f.format(t) -} - -private hideOptionsSection() { - (starting || ending || days || modes) ? false : true -} - -private timeIntervalLabel() { - (starting && ending) ? hhmm(starting) + "-" + hhmm(ending, "h:mm a z") : "" -} +/** + * Copyright 2015 SmartThings + * + * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except + * in compliance with the License. You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed + * on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License + * for the specific language governing permissions and limitations under the License. + * + * Button Controller + * + * Author: SmartThings + * Date: 2014-5-21 + */ +definition( + name: "Button Controller", + namespace: "smartthings", + author: "SmartThings", + description: "Control devices with buttons like the Aeon Labs Minimote", + category: "Convenience", + iconUrl: "https://s3.amazonaws.com/smartapp-icons/MyApps/Cat-MyApps.png", + iconX2Url: "https://s3.amazonaws.com/smartapp-icons/MyApps/Cat-MyApps@2x.png" +) + +preferences { + page(name: "selectButton") + for (def i=1; i<=8; i++) { + page(name: "configureButton$i") + } + + page(name: "timeIntervalInput", title: "Only during a certain time") { + section { + input "starting", "time", title: "Starting", required: false + input "ending", "time", title: "Ending", required: false + } + } +} + +def selectButton() { + dynamicPage(name: "selectButton", title: "First, select your button device", nextPage: "configureButton1", uninstall: configured()) { + section { + input "buttonDevice", "capability.button", title: "Button", multiple: false, required: true + } + + section(title: "More options", hidden: hideOptionsSection(), hideable: true) { + + def timeLabel = timeIntervalLabel() + + href "timeIntervalInput", title: "Only during a certain time", description: timeLabel ?: "Tap to set", state: timeLabel ? "complete" : null + + input "days", "enum", title: "Only on certain days of the week", multiple: true, required: false, + options: ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"] + + input "modes", "mode", title: "Only when mode is", multiple: true, required: false + } + } +} + +def createPage(pageNum) { + if ((state.numButton == pageNum) || (pageNum == 8)) + state.installCondition = true + dynamicPage(name: "configureButton$pageNum", title: "Set up button $pageNum here", + nextPage: "configureButton${pageNum+1}", install: state.installCondition, uninstall: configured(), getButtonSections(pageNum)) +} + +def configureButton1() { + state.numButton = buttonDevice.currentState("numberOfButtons")?.longValue ?: 4 + log.debug "state variable numButton: ${state.numButton}" + state.installCondition = false + createPage(1) +} +def configureButton2() { + createPage(2) +} + +def configureButton3() { + createPage(3) +} + +def configureButton4() { + createPage(4) +} + +def configureButton5() { + createPage(5) +} + +def configureButton6() { + createPage(6) +} + +def configureButton7() { + createPage(7) +} + +def configureButton8() { + createPage(8) +} + +def getButtonSections(buttonNumber) { + return { + section("Lights") { + input "lights_${buttonNumber}_pushed", "capability.switch", title: "Pushed", multiple: true, required: false + input "lights_${buttonNumber}_held", "capability.switch", title: "Held", multiple: true, required: false + } + section("Locks") { + input "locks_${buttonNumber}_pushed", "capability.lock", title: "Pushed", multiple: true, required: false + input "locks_${buttonNumber}_held", "capability.lock", title: "Held", multiple: true, required: false + } + section("Sonos") { + input "sonos_${buttonNumber}_pushed", "capability.musicPlayer", title: "Pushed", multiple: true, required: false + input "sonos_${buttonNumber}_held", "capability.musicPlayer", title: "Held", multiple: true, required: false + } + section("Modes") { + input "mode_${buttonNumber}_pushed", "mode", title: "Pushed", required: false + input "mode_${buttonNumber}_held", "mode", title: "Held", required: false + } + def phrases = location.helloHome?.getPhrases()*.label + if (phrases) { + section("Hello Home Actions") { + log.trace phrases + input "phrase_${buttonNumber}_pushed", "enum", title: "Pushed", required: false, options: phrases + input "phrase_${buttonNumber}_held", "enum", title: "Held", required: false, options: phrases + } + } + section("Sirens") { + input "sirens_${buttonNumber}_pushed","capability.alarm" ,title: "Pushed", multiple: true, required: false + input "sirens_${buttonNumber}_held", "capability.alarm", title: "Held", multiple: true, required: false + } + + section("Custom Message") { + input "textMessage_${buttonNumber}", "text", title: "Message", required: false + } + + section("Push Notifications") { + input "notifications_${buttonNumber}_pushed","bool" ,title: "Pushed", required: false, defaultValue: false + input "notifications_${buttonNumber}_held", "bool", title: "Held", required: false, defaultValue: false + } + + section("Sms Notifications") { + input "phone_${buttonNumber}_pushed","phone" ,title: "Pushed", required: false + input "phone_${buttonNumber}_held", "phone", title: "Held", required: false + } + } +} + +def installed() { + initialize() +} + +def updated() { + unsubscribe() + initialize() +} + +def initialize() { + subscribe(buttonDevice, "button", buttonEvent) +} + +def configured() { + return buttonDevice || buttonConfigured(1) || buttonConfigured(2) || buttonConfigured(3) || buttonConfigured(4) +} + +def buttonConfigured(idx) { + return settings["lights_$idx_pushed"] || + settings["locks_$idx_pushed"] || + settings["sonos_$idx_pushed"] || + settings["mode_$idx_pushed"] || + settings["notifications_$idx_pushed"] || + settings["sirens_$idx_pushed"] || + settings["notifications_$idx_pushed"] || + settings["phone_$idx_pushed"] +} + +def buttonEvent(evt){ + if(allOk) { + def buttonNumber = evt.data // why doesn't jsonData work? always returning [:] + def value = evt.value + log.debug "buttonEvent: $evt.name = $evt.value ($evt.data)" + log.debug "button: $buttonNumber, value: $value" + + def recentEvents = buttonDevice.eventsSince(new Date(now() - 3000)).findAll{it.value == evt.value && it.data == evt.data} + log.debug "Found ${recentEvents.size()?:0} events in past 3 seconds" + + if(recentEvents.size <= 1){ + switch(buttonNumber) { + case ~/.*1.*/: + executeHandlers(1, value) + break + case ~/.*2.*/: + executeHandlers(2, value) + break + case ~/.*3.*/: + executeHandlers(3, value) + break + case ~/.*4.*/: + executeHandlers(4, value) + break + } + } else { + log.debug "Found recent button press events for $buttonNumber with value $value" + } + } +} + +def executeHandlers(buttonNumber, value) { + log.debug "executeHandlers: $buttonNumber - $value" + + def lights = find('lights', buttonNumber, value) + if (lights != null) toggle(lights) + + def locks = find('locks', buttonNumber, value) + if (locks != null) toggle(locks) + + def sonos = find('sonos', buttonNumber, value) + if (sonos != null) toggle(sonos) + + def mode = find('mode', buttonNumber, value) + if (mode != null) changeMode(mode) + + def phrase = find('phrase', buttonNumber, value) + if (phrase != null) location.helloHome.execute(phrase) + + def textMessage = findMsg('textMessage', buttonNumber) + + def notifications = find('notifications', buttonNumber, value) + if (notifications?.toBoolean()) sendPush(textMessage ?: "Button $buttonNumber was pressed" ) + + def phone = find('phone', buttonNumber, value) + if (phone != null) sendSms(phone, textMessage ?:"Button $buttonNumber was pressed") + + def sirens = find('sirens', buttonNumber, value) + if (sirens != null) toggle(sirens) +} + +def find(type, buttonNumber, value) { + def preferenceName = type + "_" + buttonNumber + "_" + value + def pref = settings[preferenceName] + if(pref != null) { + log.debug "Found: $pref for $preferenceName" + } + + return pref +} + +def findMsg(type, buttonNumber) { + def preferenceName = type + "_" + buttonNumber + def pref = settings[preferenceName] + if(pref != null) { + log.debug "Found: $pref for $preferenceName" + } + + return pref +} + +def toggle(devices) { + log.debug "toggle: $devices = ${devices*.currentValue('switch')}" + + if (devices*.currentValue('switch').contains('on')) { + devices.off() + } + else if (devices*.currentValue('switch').contains('off')) { + devices.on() + } + else if (devices*.currentValue('lock').contains('locked')) { + devices.unlock() + } + else if (devices*.currentValue('lock').contains('unlocked')) { + devices.lock() + } + else if (devices*.currentValue('alarm').contains('off')) { + devices.siren() + } + else { + devices.on() + } +} + +def changeMode(mode) { + log.debug "changeMode: $mode, location.mode = $location.mode, location.modes = $location.modes" + + if (location.mode != mode && location.modes?.find { it.name == mode }) { + setLocationMode(mode) + } +} + +// execution filter methods +private getAllOk() { + modeOk && daysOk && timeOk +} + +private getModeOk() { + def result = !modes || modes.contains(location.mode) + log.trace "modeOk = $result" + result +} + +private getDaysOk() { + def result = true + if (days) { + def df = new java.text.SimpleDateFormat("EEEE") + if (location.timeZone) { + df.setTimeZone(location.timeZone) + } + else { + df.setTimeZone(TimeZone.getTimeZone("America/New_York")) + } + def day = df.format(new Date()) + result = days.contains(day) + } + log.trace "daysOk = $result" + result +} + +private getTimeOk() { + def result = true + if (starting && ending) { + def currTime = now() + def start = timeToday(starting, location.timeZone).time + def stop = timeToday(ending, location.timeZone).time + result = start < stop ? currTime >= start && currTime <= stop : currTime <= stop || currTime >= start + } + log.trace "timeOk = $result" + result +} + +private hhmm(time, fmt = "h:mm a") +{ + def t = timeToday(time, location.timeZone) + def f = new java.text.SimpleDateFormat(fmt) + f.setTimeZone(location.timeZone ?: timeZone(time)) + f.format(t) +} + +private hideOptionsSection() { + (starting || ending || days || modes) ? false : true +} + +private timeIntervalLabel() { + (starting && ending) ? hhmm(starting) + "-" + hhmm(ending, "h:mm a z") : "" +} \ No newline at end of file