Created
February 4, 2018 06:53
-
-
Save enishoca/a46ec09c9445dc93bb7231cd93586402 to your computer and use it in GitHub Desktop.
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
metadata { | |
definition(name: "Virtual Thermostat Device", namespace: "piratemedia/smartthings", author: "Eliot S.") { | |
capability "Actuator" | |
capability "Refresh" | |
capability "Sensor" | |
capability "Thermostat" | |
//capability "Thermostat Heating Setpoint" | |
capability "Thermostat Mode" | |
capability "Thermostat Operating State" | |
//capability "Thermostat Setpoint" | |
capability "Temperature Measurement" | |
capability "Health Check" | |
command "refresh" | |
command "poll" | |
command "offbtn" | |
command "heatbtn" | |
command "setThermostatMode", ["string"] | |
command "levelUpDown" | |
command "levelUp" | |
command "levelDown" | |
command "heatingSetpointUp" | |
command "heatingSetpointDown" | |
command "log" | |
command "changeMode" | |
command "setVirtualTemperature", ["number"] | |
command "setHeatingStatus", ["boolean"] | |
command "setEmergencyMode", ["boolean"] | |
command "setHeatingOff", ["boolean"] | |
attribute "temperatureUnit", "string" | |
attribute "targetTemp", "string" | |
attribute "debugOn", "string" | |
attribute "safetyTempMin", "string" | |
attribute "safetyTempMax", "string" | |
attribute "safetyTempExceeded", "string" | |
} | |
simulator { | |
// TODO: define status and reply messages here | |
} | |
tiles(scale: 2) { | |
multiAttributeTile(name: "temperature", type: "thermostat", width: 6, height: 4, canChangeIcon: true) { | |
tileAttribute("device.temperature", key: "PRIMARY_CONTROL") { | |
attributeState("default", label: '${currentValue}°', unit: '°C') | |
} | |
tileAttribute("device.thermostatSetpoint", key: "VALUE_CONTROL") { | |
attributeState("default", action: "levelUpDown") | |
attributeState("VALUE_UP", action: "levelUp") | |
attributeState("VALUE_DOWN", action: "levelDown") | |
} | |
tileAttribute("device.thermostatOperatingState", key: "OPERATING_STATE") { | |
attributeState("idle", backgroundColor: "#44B621") | |
attributeState("heating", backgroundColor: "#FFA81E") | |
attributeState("off", backgroundColor: "#ddcccc") | |
attributeState("emergency", backgroundColor: "#e60000") | |
} | |
tileAttribute("device.thermostatMode", key: "THERMOSTAT_MODE") { | |
attributeState("off", label: 'off') | |
attributeState("heat", label: 'heat') | |
} | |
tileAttribute("device.thermostatSetpoint", key: "HEATING_SETPOINT") { | |
attributeState("default", label: '${currentValue}') | |
} | |
} | |
valueTile("temp2", "device.temperature", width: 2, height: 2, decoration: "flat") { | |
state("default", label: '${currentValue}°', icon: "https://raw.githubusercontent.com/eliotstocker/SmartThings-VirtualThermostat-WithDTH/master/device.png", | |
backgroundColors: getTempColors(), canChangeIcon: true) | |
} | |
standardTile("thermostatMode", "device.thermostatMode", width: 2, height: 2, decoration: "flat") { | |
state("off", action: "changeMode", nextState: "updating", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/off_btn_icon.png") | |
state("heat", action: "changeMode", nextState: "updating", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/heat_btn_icon.png") | |
state("updating", label: "", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/cmd_working.png") | |
} | |
standardTile("offBtn", "device.off", width: 1, height: 1, decoration: "flat") { | |
state("default", action: "offbtn", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/off_btn_icon.png") | |
} | |
standardTile("heatBtn", "device.canHeat", width: 1, height: 1, decoration: "flat") { | |
state("true", action: "heatbtn", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/heat_btn_icon.png") | |
state "false", label: '' | |
} | |
standardTile("refresh", "device.refresh", width: 2, height: 2, decoration: "flat") { | |
state "default", action: "refresh.refresh", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/refresh_icon.png" | |
} | |
valueTile("heatingSetpoint", "device.thermostatSetpoint", width: 1, height: 1) { | |
state("heatingSetpoint", label: '${currentValue}', unit: unitString, foregroundColor: "#FFFFFF", | |
backgroundColors: [ | |
[value: 0, color: "#FFFFFF"], | |
[value: 7, color: "#FF3300"], | |
[value: 15, color: "#FF3300"] | |
]) | |
state("disabled", label: '', foregroundColor: "#FFFFFF", backgroundColor: "#FFFFFF") | |
} | |
standardTile("heatingSetpointUp", "device.thermostatSetpoint", width: 1, height: 1, canChangeIcon: true, decoration: "flat") { | |
state "default", label: '', action: "heatingSetpointUp", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/heat_arrow_up.png" | |
state "", label: '' | |
} | |
standardTile("heatingSetpointDown", "device.thermostatSetpoint", width: 1, height: 1, canChangeIcon: true, decoration: "flat") { | |
state "default", label: '', action: "heatingSetpointDown", icon: "https://raw.githubusercontent.com/tonesto7/nest-manager/master/Images/Devices/heat_arrow_down.png" | |
state "", label: '' | |
} | |
controlTile("heatSliderControl", "device.thermostatSetpoint", "slider", height: 1, width: 3, range: getRange(), inactiveLabel: false) { | |
state "default", action: "setHeatingSetpoint", backgroundColor: "#FF3300" | |
state "", label: '' | |
} | |
main("temp2") | |
details(["temperature", "thermostatMode", | |
"heatingSetpointDown", "heatingSetpoint", "heatingSetpointUp", | |
"heatSliderControl", "offBtn", "heatBtn", "refresh" | |
]) | |
} | |
/*preferences { | |
input "resetHistoryOnly", "bool", title: "Reset History Data", description: "", displayDuringSetup: false | |
input "resetAllData", "bool", title: "Reset All Stored Event Data", description: "", displayDuringSetup: false | |
}*/ | |
} | |
def compileForC() { | |
def retVal = false // if using C mode, set this to true so that enums and colors are correct (due to ST issue of compile time evaluation) | |
return retVal | |
} | |
def installed() { | |
log.trace "Executing 'installed'" | |
initialize() | |
done() | |
} | |
def configure() { | |
log.trace "Executing 'configure'" | |
initialize() | |
done() | |
} | |
private initialize() { | |
log.trace "Executing 'initialize'" | |
sendEvent(name: "temperature", value: defaultTemp, unit: unitString) | |
sendEvent(name: "thermostatSetpoint", value: defaultTemp, unit: unitString) | |
sendEvent(name: "heatingSetpoint", value: defaultTemp, unit: unitString) | |
sendEvent(name: "thermostatOperatingState", value: "off") | |
sendEvent(name: "thermostatMode", value: "heat") | |
} | |
def getTempColors() { | |
def colorMap | |
//getTemperatureScale() == "C" wantMetric() | |
if (compileForC()) { | |
colorMap = [ | |
// Celsius Color Range | |
[value: 0, color: "#153591"], | |
[value: 7, color: "#1e9cbb"], | |
[value: 15, color: "#90d2a7"], | |
[value: 23, color: "#44b621"], | |
[value: 29, color: "#f1d801"], | |
[value: 33, color: "#d04e00"], | |
[value: 36, color: "#bc2323"] | |
] | |
} else { | |
colorMap = [ | |
// Fahrenheit Color Range | |
[value: 40, color: "#153591"], | |
[value: 44, color: "#1e9cbb"], | |
[value: 59, color: "#90d2a7"], | |
[value: 74, color: "#44b621"], | |
[value: 84, color: "#f1d801"], | |
[value: 92, color: "#d04e00"], | |
[value: 96, color: "#bc2323"] | |
] | |
} | |
} | |
def unitString() { | |
return compileForC() ? "°C": "°F" | |
} | |
def defaultTemp() { | |
return compileForC() ? 20 : 70 | |
} | |
def lowRange() { | |
return compileForC() ? 9 : 45 | |
} | |
def highRange() { | |
return compileForC() ? 32 : 90 | |
} | |
def getRange() { | |
return "${lowRange()}..${highRange()}" | |
} | |
def getTemperature() { | |
return device.currentValue("temperature") | |
} | |
def setHeatingSetpoint(temp) { | |
log.debug "setting temp to: $temp" | |
sendEvent(name: "thermostatSetpoint", value: temp, unit: unitString) | |
sendEvent(name: "heatingSetpoint", value: temp, unit: unitString) | |
refresh() | |
runIn(10, refresh) | |
} | |
def heatingSetpointUp() { | |
def hsp = device.currentValue("thermostatSetpoint") | |
setHeatingSetpoint(hsp + 1.0) | |
} | |
def heatingSetpointDown() { | |
def hsp = device.currentValue("thermostatSetpoint") | |
setHeatingSetpoint(hsp - 1.0) | |
} | |
def levelUp() { | |
def hsp = device.currentValue("thermostatSetpoint") | |
setHeatingSetpoint(hsp + 1.0) | |
} | |
def levelDown() { | |
def hsp = device.currentValue("thermostatSetpoint") | |
setHeatingSetpoint(hsp - 1.0) | |
} | |
private void done() { | |
log.trace "---- DONE ----" | |
} | |
def ping() { | |
log.trace "Executing ping" | |
refresh() | |
} | |
def parse(data) { | |
log.debug "parse data: $data" | |
} | |
def refresh() { | |
log.trace "Executing refresh" | |
sendEvent(name: "thermostatMode", value: getThermostatMode()) | |
sendEvent(name: "thermostatOperatingState", value: getOperatingState()) | |
sendEvent(name: "thermostatSetpoint", value: getThermostatSetpoint(), unit: unitString) | |
sendEvent(name: "heatingSetpoint", value: getHeatingSetpoint(), unit: unitString) | |
sendEvent(name: "temperature", value: getTemperature(), unit: unitString) | |
done() | |
} | |
def getThermostatMode() { | |
return device.currentValue("thermostatMode") | |
} | |
def getOperatingState() { | |
return device.currentValue("thermostatOperatingState") | |
} | |
def thermostatSetpoint() { | |
return device.currentValue("thermostatSetpoint") | |
} | |
def getHeatingSetpoint() { | |
return device.currentValue("heatingSetpoint") | |
} | |
def poll() {} | |
def offbtn() { | |
sendEvent(name: "thermostatMode", value: "off") | |
} | |
def heatbtn() { | |
sendEvent(name: "thermostatMode", value: "heat") | |
} | |
def setThermostatMode(mode) { | |
sendEvent(name: "thermostatMode", value: mode) | |
} | |
def levelUpDown() {} | |
def log() {} | |
def changeMode() { | |
def val = device.currentValue("thermostatMode") == "off" ? "heat" : "off" | |
sendEvent(name: "thermostatMode", value: val) | |
return val | |
} | |
def setVirtualTemperature(temp) { | |
sendEvent(name: "temperature", value: temp, unit: unitString) | |
} | |
def setHeatingStatus(bool) { | |
sendEvent(name: "thermostatOperatingState", value: bool ? "heating" : "idle") | |
} | |
def setEmergencyMode(bool) { | |
sendEvent(name: "thermostatOperatingState", value: bool ? "emergency" : "idle") | |
} | |
def setHeatingOff(bool) { | |
sendEvent(name: "thermostatOperatingState", value: bool ? "off" : "idle") | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment