Init
This commit is contained in:
@@ -0,0 +1,74 @@
|
||||
import appdaemon.plugins.hass.hassapi as hass
|
||||
from datetime import datetime, date, timedelta
|
||||
|
||||
#
|
||||
# Basic alarm clock.
|
||||
# It will trigger 'alarmclock_trigger' event on alarm time.
|
||||
#
|
||||
# Args:
|
||||
#
|
||||
# time = input_datetime for time (alarm time).
|
||||
# state = input_boolean for alarm state (on/off)
|
||||
# days = list of days when alarm is active
|
||||
# prealarm_delta (optional, in minutes, default=15) = time befor main alarm, when 'alarmclock_prealarm' event will fire (you can trigger slow light on before main alarm sound).
|
||||
#
|
||||
# None
|
||||
#
|
||||
# Release Notes
|
||||
#
|
||||
# Version 1.0:
|
||||
# Initial Version
|
||||
|
||||
class AlarmClock(hass.Hass):
|
||||
alarmtimer = None
|
||||
prealarmtimer = None
|
||||
prealarm_delta = 15
|
||||
def initialize(self):
|
||||
if "days" not in self.args or "time" not in self.args or "state" not in self.args:
|
||||
self.error("Please provide days, time and state in config!")
|
||||
return
|
||||
if 'prealarm_delta' in self.args:
|
||||
self.prealarm_delta = self.args['prealarm_delta']
|
||||
self.log('Alarm will trigger in days: {}.'.format(self.args['days']))
|
||||
self.listen_state(self.alarm_time_changed, self.args['time'])
|
||||
self.listen_state(self.alarm_time_changed, self.args['state'])
|
||||
self.alarm_time_changed(None, None, None, None, None)
|
||||
|
||||
def alarm_time_changed(self, entity, attribute, old, new, kwargs):
|
||||
#cacnel old timer
|
||||
self.cancel_current_timer()
|
||||
|
||||
alarm_state = self.get_state(self.args['state'])
|
||||
if alarm_state == 'off':
|
||||
self.log('Turning off alarm.')
|
||||
return
|
||||
|
||||
#set new timer
|
||||
time_string = self.get_state(self.args["time"])
|
||||
if time_string == "unknown":
|
||||
return
|
||||
alarm_time = self.parse_time(time_string)
|
||||
self.run_timer(alarm_time)
|
||||
|
||||
def run_timer(self, alarm_time):
|
||||
prealarm_time = (datetime.combine(date.min, alarm_time) - timedelta(0, self.prealarm_delta * 60)).time()
|
||||
self.alarmtimer = self.run_daily(self.alarmclock_trigger, alarm_time)
|
||||
self.prealarmtimer = self.run_daily(self.alarmclock_prealarm, prealarm_time)
|
||||
self.log("Alarm was set to {}, prealarm: {}.".format(alarm_time, prealarm_time))
|
||||
|
||||
def cancel_current_timer(self):
|
||||
if self.alarmtimer != None and self.prealarmtimer != None:
|
||||
self.cancel_timer(self.alarmtimer)
|
||||
self.cancel_timer(self.prealarmtimer)
|
||||
|
||||
def alarmclock_trigger(self, kwargs):
|
||||
if not self.constrain_days(self.args['days']):
|
||||
return
|
||||
self.log("Alarmclock triggered!")
|
||||
self.fire_event("alarmclock_alarm")
|
||||
|
||||
def alarmclock_prealarm(self, kwargs):
|
||||
if not self.constrain_days(self.args['days']):
|
||||
return
|
||||
self.log("Pre alarmclock triggered!")
|
||||
self.fire_event("alarmclock_prealarm")
|
||||
@@ -0,0 +1,22 @@
|
||||
#################################
|
||||
# ALARM CLOCK #
|
||||
#################################
|
||||
alarmclock_weekdays:
|
||||
module: alarm_clock
|
||||
class: AlarmClock
|
||||
state: input_boolean.alarmclock_weekdays
|
||||
time: input_datetime.alarmclock_weekdays
|
||||
days: mon,tue,wed,thu,fri
|
||||
prealarm_delta: 15
|
||||
global_dependencies:
|
||||
- globals
|
||||
|
||||
alarmclock_weekend:
|
||||
module: alarm_clock
|
||||
class: AlarmClock
|
||||
state: input_boolean.alarmclock_weekend
|
||||
time: input_datetime.alarmclock_weekend
|
||||
days: sat,sun
|
||||
prealarm_delta: 15
|
||||
global_dependencies:
|
||||
- globals
|
||||
@@ -0,0 +1,55 @@
|
||||
import appdaemon.plugins.hass.hassapi as hass
|
||||
import globals
|
||||
#
|
||||
# Very special case, this will run sound 'alarm' on xiaomi gateway based on alarm clock event (alarmclock_trigger)
|
||||
# and stop it when sensor became active.
|
||||
# Args:
|
||||
#
|
||||
# sensor = sensor, which will stop alarm (bath motion sensor for me)
|
||||
# ringtone = (default = 20) xiaomi ringtone id.
|
||||
#
|
||||
# None
|
||||
#
|
||||
# Release Notes
|
||||
#
|
||||
# Version 1.0:
|
||||
# Initial Version
|
||||
|
||||
class AlarmclockAction(hass.Hass):
|
||||
timer = None
|
||||
ringtone = 20
|
||||
volume = 10
|
||||
gw_mac = ''
|
||||
def initialize(self):
|
||||
if not globals.check_args(self, ["sensor","gw_mac"]):
|
||||
return
|
||||
self.gw_mac = self.args['gw_mac']
|
||||
if 'ringtone' in self.args:
|
||||
self.ringtone = self.args['ringtone']
|
||||
self.listen_event(self.alarmclock_alarm, "alarmclock_alarm")
|
||||
self.listen_event(self.alarmclock_stop, "alarmclock_stop")
|
||||
self.listen_state(self.sensor_trigger, self.args['sensor'])
|
||||
|
||||
def alarmclock_stop(self, event_id, event_args, kwargs):
|
||||
self.sensor_trigger(None, None, None, 'on', None)
|
||||
|
||||
def sensor_trigger(self, entity, attribute, old, new, kwargs):
|
||||
if new == "on" and self.timer != None:
|
||||
self.call_service("xiaomi_aqara/stop_ringtone", gw_mac=self.gw_mac)
|
||||
self.cancel_current_timer()
|
||||
|
||||
def alarmclock_alarm(self, event_id, event_args, kwargs):
|
||||
self.log('Alarm triggered!')
|
||||
self.volume = 10
|
||||
self.timer = self.run_every(self.timer_tick, self.datetime(), 17)
|
||||
|
||||
def timer_tick(self, kwargs):
|
||||
self.call_service("xiaomi_aqara/play_ringtone", gw_mac=self.gw_mac, ringtone_id=self.ringtone, ringtone_vol=self.volume)
|
||||
if self.volume < 100:
|
||||
self.volume = self.volume + 10
|
||||
|
||||
def cancel_current_timer(self):
|
||||
if self.timer != None:
|
||||
self.log('canceling timer')
|
||||
self.cancel_timer(self.timer)
|
||||
self.timer = None
|
||||
@@ -0,0 +1,8 @@
|
||||
alarm_clock_action:
|
||||
module: alarm_clock_action
|
||||
class: AlarmclockAction
|
||||
sensor: group.bath_motion #bath motion sensor
|
||||
gw_mac: !secret aqara1_mac
|
||||
ringtone: 20
|
||||
global_dependencies:
|
||||
- globals
|
||||
@@ -0,0 +1,83 @@
|
||||
import appdaemon.plugins.hass.hassapi as hass
|
||||
|
||||
#
|
||||
# Pre alarm event.
|
||||
# This app will slowly turn on the light after 'alarmclock_alarm' event. It will fire 15 mins(by default) before alarm.
|
||||
# and stop when sensor became active.
|
||||
#
|
||||
# Args:
|
||||
# sensor = sensor, which will stop pre-alarm (bath motion sensor for me)
|
||||
# entity = entity to slowly turn on. Must support brightness control.
|
||||
#
|
||||
# None
|
||||
#
|
||||
# Release Notes
|
||||
#
|
||||
# Version 1.0:
|
||||
# Initial Version
|
||||
|
||||
class AlarmclockPrealarm(hass.Hass):
|
||||
brightness = 1
|
||||
color_temp = 588
|
||||
timer = None
|
||||
def initialize(self):
|
||||
if "sensor" not in self.args or "entity" not in self.args:
|
||||
self.error("Please provide sensor and entity in config!")
|
||||
return
|
||||
self.listen_event(self.alarmclock_prealarm, "alarmclock_prealarm")
|
||||
self.listen_event(self.alarmclock_stop, "alarmclock_stop")
|
||||
self.listen_state(self.sensor_trigger, self.args['sensor'])
|
||||
|
||||
def alarmclock_stop(self, event_id, event_args, kwargs):
|
||||
self.sensor_trigger(None, None, None, 'on', None)
|
||||
|
||||
def sensor_trigger(self, entity, attribute, old, new, kwargs):
|
||||
if new == "on":
|
||||
if self.timer != None:
|
||||
self.brightness = 255
|
||||
self.color_temp = 240
|
||||
self.timer_tick(None)
|
||||
self.cancel_current_timer()
|
||||
|
||||
def cancel_current_timer(self):
|
||||
if self.timer != None:
|
||||
self.log('canceling timer')
|
||||
self.cancel_timer(self.timer)
|
||||
self.timer = None
|
||||
|
||||
def alarmclock_prealarm(self, event_id, event_args, kwargs):
|
||||
if 'constraint' in self.args and not self.constrain_input_boolean(self.args['constraint']):
|
||||
return
|
||||
self.log('Prealarm triggered!')
|
||||
self.brightness = 1
|
||||
self.color_temp = 588
|
||||
self.timer = self.run_every(self.timer_tick, self.datetime(), 10)
|
||||
|
||||
def timer_tick(self, kwargs):
|
||||
attributes = self.get_state(self.args['entity'], attribute = "all")
|
||||
if 'attributes' in attributes:
|
||||
attributes = attributes['attributes']
|
||||
# we have a group here
|
||||
if 'entity_id' in attributes:
|
||||
for entity_id in attributes['entity_id']:
|
||||
self.make_entity_action(entity_id, None)
|
||||
else:
|
||||
# simple entity
|
||||
self.make_entity_action(self.args['entity'], attributes)
|
||||
|
||||
if (self.brightness < 245):
|
||||
self.brightness = self.brightness + 2
|
||||
elif (self.color_temp > 220):
|
||||
self.color_temp = self.color_temp - 30
|
||||
else:
|
||||
self.cancel_current_timer()
|
||||
self.log("brightness: {}, color_temp: {}".format(self.brightness, self.color_temp))
|
||||
|
||||
def make_entity_action(self, entity_id, attributes):
|
||||
if attributes == None:
|
||||
attributes = self.get_state(entity_id, attribute = "all")
|
||||
if 'attributes' in attributes:
|
||||
attributes = attributes['attributes']
|
||||
#state = self.get_state(entity_id)
|
||||
self.turn_on(entity_id, brightness = self.brightness, color_temp = self.color_temp)
|
||||
# self.log(attributes)
|
||||
@@ -0,0 +1,7 @@
|
||||
alarm_clock_prealarm:
|
||||
module: alarm_clock_prealarm
|
||||
class: AlarmclockPrealarm
|
||||
sensor: group.bath_motion #bath motion sensor
|
||||
entity: group.mainroom_color
|
||||
global_dependencies:
|
||||
- globals
|
||||
Reference in New Issue
Block a user