Compare commits
77 Commits
10fca9ed03
...
2025.2.5
| Author | SHA1 | Date | |
|---|---|---|---|
|
8b120ae347
|
|||
|
da03ea826b
|
|||
|
66fc0fb906
|
|||
|
4c81a8a6a5
|
|||
|
35a511710e
|
|||
|
4c7bf9a85c
|
|||
|
754e3d6095
|
|||
|
8f707c71bb
|
|||
|
08b5c7b764
|
|||
|
fd37fe589c
|
|||
|
36906d6207
|
|||
|
29dcb654b4
|
|||
|
ec0aed386a
|
|||
|
a96bc99271
|
|||
|
a085e71c86
|
|||
|
4a61f5a45c
|
|||
|
47f23a4e02
|
|||
|
fbec1ae6e2
|
|||
|
d5ddf65270
|
|||
|
53b67bfc87
|
|||
|
725250acd7
|
|||
|
f988f1cccc
|
|||
|
515731fc68
|
|||
|
e1bd79e176
|
|||
|
a57cb4ecb7
|
|||
|
89ef394817
|
|||
|
6b9380f015
|
|||
|
6c145f0ca9
|
|||
|
ff98142b9e
|
|||
|
2ceba7cb57
|
|||
|
1b2ce1e097
|
|||
|
7459005500
|
|||
|
9ed2f658a4
|
|||
|
91d6a32274
|
|||
|
f2e9f6049c
|
|||
|
6f9c9fc8a9
|
|||
|
b819156cfa
|
|||
|
df583c23ff
|
|||
|
84f0e54ddb
|
|||
|
3803e9f9c2
|
|||
|
66d27a09d3
|
|||
|
ed71c557df
|
|||
|
35e5891f5e
|
|||
|
3d4dc4c1d9
|
|||
|
8c029143f2
|
|||
|
c773b29573
|
|||
|
76841ecb19
|
|||
|
f3d5d90593
|
|||
|
c7d1696cca
|
|||
|
db9b221fd9
|
|||
|
955bf32e81
|
|||
|
fc498ca23b
|
|||
|
f61d79dee7
|
|||
|
cc5a94e683
|
|||
|
c8678d831a
|
|||
|
e566d94d90
|
|||
|
54de982d95
|
|||
|
8a4545abed
|
|||
|
bb9e604d33
|
|||
|
e912733bbc
|
|||
|
53b230e0ad
|
|||
|
4761855858
|
|||
|
b83c3e2ecd
|
|||
|
22ba35d631
|
|||
|
b6539ea85c
|
|||
|
37f5314e88
|
|||
|
faef1d02b2
|
|||
|
46df823c24
|
|||
|
707c03804d
|
|||
|
9fea293c23
|
|||
|
703fed14c3
|
|||
|
37a6f31a1e
|
|||
|
8411488ab3
|
|||
|
bda6fc97ba
|
|||
|
261913371f
|
|||
|
b718ad2de2
|
|||
|
2c559ec2c4
|
1
.HA_VERSION
Normal file
1
.HA_VERSION
Normal file
@@ -0,0 +1 @@
|
||||
2025.2.5
|
||||
20
.gitignore
vendored
20
.gitignore
vendored
@@ -3,30 +3,27 @@
|
||||
/.cloud
|
||||
/.google.token
|
||||
/.ssh
|
||||
/.codegpt
|
||||
|
||||
# ignore some directories.
|
||||
/icloud/
|
||||
/www/
|
||||
/www/*
|
||||
/tts/
|
||||
/deps/
|
||||
/hadashboards/
|
||||
/intents/
|
||||
/themes/
|
||||
/custom_components
|
||||
/deps
|
||||
/hacs
|
||||
/image
|
||||
/node-red/
|
||||
/files
|
||||
/appdaemon/*
|
||||
/appdaemon/apps/*
|
||||
/appdaemon/
|
||||
/glances/
|
||||
/downloads/
|
||||
/lightwand/
|
||||
|
||||
# ignore any of these files no matter where they are using double *
|
||||
**.DS_Store
|
||||
**._*
|
||||
**.HA_VERSION
|
||||
**.pyc
|
||||
**.conf
|
||||
**.uuid
|
||||
@@ -71,11 +68,4 @@
|
||||
**test.jinja
|
||||
|
||||
# exceptions
|
||||
!/appdaemon/apps/
|
||||
!/appdaemon/apps/apps.yaml
|
||||
!/node-red/projects/
|
||||
!/node-red/projects/NerdFlows/
|
||||
!/node-red/projects/NerdFlows/flows.json
|
||||
!/node-red/projects/NerdFlows/flows_cred.json
|
||||
!/node-red/projects/NerdFlows/package.json
|
||||
!/node-red/projects/NerdFlows/README.md
|
||||
!/www/bubble/
|
||||
1651
automations.yaml
1651
automations.yaml
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,27 @@
|
||||
blueprint:
|
||||
name: Invert a binary sensor
|
||||
description: Creates a binary_sensor which holds the inverted value of a reference binary_sensor
|
||||
domain: template
|
||||
source_url: https://github.com/home-assistant/core/blob/dev/homeassistant/components/template/blueprints/inverted_binary_sensor.yaml
|
||||
input:
|
||||
reference_entity:
|
||||
name: Binary sensor to be inverted
|
||||
description: The binary_sensor which needs to have its value inverted
|
||||
selector:
|
||||
entity:
|
||||
domain: binary_sensor
|
||||
variables:
|
||||
reference_entity: !input reference_entity
|
||||
binary_sensor:
|
||||
state: >
|
||||
{% if states(reference_entity) == 'on' %}
|
||||
off
|
||||
{% elif states(reference_entity) == 'off' %}
|
||||
on
|
||||
{% else %}
|
||||
{{ states(reference_entity) }}
|
||||
{% endif %}
|
||||
# delay_on: not_used in this example
|
||||
# delay_off: not_used in this example
|
||||
# auto_off: not_used in this example
|
||||
availability: "{{ states(reference_entity) not in ('unknown', 'unavailable') }}"
|
||||
@@ -260,6 +260,8 @@ influxdb:
|
||||
- binary_sensor.kallen_desktop*
|
||||
- sensor.asus_laptop*
|
||||
- binary_sensor.asus_laptop*
|
||||
- sensor.*ashland*
|
||||
- sensor.*kasx*
|
||||
entities:
|
||||
- media_player.living_room_tv
|
||||
- media_player.basement_tv
|
||||
@@ -280,6 +282,7 @@ influxdb:
|
||||
- binary_sensor.internet
|
||||
- binary_sensor.people_present
|
||||
- weather.iron_nerd_weather_station
|
||||
- weather.ashland_weather_station
|
||||
- sensor.circle_k
|
||||
- sensor.kroger
|
||||
- sensor.kecks
|
||||
@@ -312,6 +315,12 @@ influxdb:
|
||||
- sensor.bypassed_sensors
|
||||
- input_boolean.shower_mode
|
||||
- sensor.services_down
|
||||
- sensor.average_room_temperature
|
||||
- sensor.average_room_illuminance
|
||||
- sensor.brightest_room
|
||||
- sensor.dimmest_room
|
||||
- sensor.warmest_room_temperature
|
||||
- sensor.coldest_room_temperature
|
||||
|
||||
logbook:
|
||||
include:
|
||||
@@ -428,6 +437,8 @@ prometheus:
|
||||
- binary_sensor.kallen_desktop*
|
||||
- sensor.asus_laptop*
|
||||
- binary_sensor.asus_laptop*
|
||||
- sensor.*ashland*
|
||||
- sensor.*kasx*
|
||||
include_entities:
|
||||
- media_player.living_room_tv
|
||||
- media_player.basement_tv
|
||||
@@ -448,6 +459,7 @@ prometheus:
|
||||
- binary_sensor.internet
|
||||
- binary_sensor.people_present
|
||||
- weather.iron_nerd_weather_station
|
||||
- weather.ashland_weather_station
|
||||
- sensor.circle_k
|
||||
- sensor.kroger
|
||||
- sensor.kecks
|
||||
@@ -480,3 +492,9 @@ prometheus:
|
||||
- sensor.bypassed_sensors
|
||||
- input_boolean.shower_mode
|
||||
- sensor.services_down
|
||||
- sensor.average_room_temperature
|
||||
- sensor.average_room_illuminance
|
||||
- sensor.brightest_room
|
||||
- sensor.dimmest_room
|
||||
- sensor.warmest_room_temperature
|
||||
- sensor.coldest_room_temperature
|
||||
|
||||
@@ -4,243 +4,417 @@
|
||||
combine contains the text to combine the last time fraction, and error the text to display on wrong date input
|
||||
#}
|
||||
{%- set _time_period_phrases = [
|
||||
{
|
||||
'language': 'en',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['year', 'years', 'yr'],
|
||||
'month': ['month', 'months', 'mth'],
|
||||
'week': ['week', 'weeks', 'wk'],
|
||||
'day': ['day', 'days', 'day'],
|
||||
'hour': ['hour', 'hours', 'hr'],
|
||||
'minute': ['minute', 'minutes', 'min'],
|
||||
'second': ['second', 'seconds', 'sec'],
|
||||
'millisecond': ['millisecond', 'milliseconds', 'ms'],
|
||||
'combine': 'and',
|
||||
'error': 'Invalid date'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'pl',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['rok', 'lat', 'r'],
|
||||
'month': ['miesiąc', 'miesięcy', 'msc'],
|
||||
'week': ['tydzień', 'tygodni', 'tyg'],
|
||||
'day': ['dzień', 'dni', 'dzień'],
|
||||
'hour': ['godzina', 'godzin', 'godz'],
|
||||
'minute': ['minuta', 'minut', 'min'],
|
||||
'second': ['sekunda', 'sekund', 'sek'],
|
||||
'millisecond': ['milisekunda', 'milisekund', 'ms'],
|
||||
'combine': 'i',
|
||||
'error': 'Niepoprawna data'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'fr',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['année', 'années', 'an'],
|
||||
'month': ['mois', 'mois', 'mois'],
|
||||
'week': ['semaine', 'semaines', 'sem'],
|
||||
'day': ['jour', 'jours', 'j'],
|
||||
'hour': ['heure', 'heures', 'h'],
|
||||
'minute': ['minute', 'minutes', 'min'],
|
||||
'second': ['seconde', 'secondes', 'sec'],
|
||||
'millisecond': ['milliseconde', 'millisecondes', 'ms'],
|
||||
'combine': 'et',
|
||||
'error': 'Date non valide'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'it',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['anno', 'anni', 'aa'],
|
||||
'month': ['mese', 'mesi', 'mm'],
|
||||
'week': ['settimana', 'settimane', 'set'],
|
||||
'day': ['giorno', 'giorni', 'gg'],
|
||||
'hour': ['ora', 'ore', 'h'],
|
||||
'minute': ['minuto', 'minuti', 'min'],
|
||||
'second': ['secondo', 'secondi', 'sec'],
|
||||
'millisecond': ['millisecondo', 'millisecondi', 'ms'],
|
||||
'combine': 'e',
|
||||
'error': 'Data non valida'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'nl',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['jaar', 'jaar', 'jr'],
|
||||
'month': ['maand', 'maanden', 'mnd'],
|
||||
'week': ['week', 'weken', 'wk'],
|
||||
'day': ['dag', 'dagen', 'dg'],
|
||||
'hour': ['uur', 'uur', 'u'],
|
||||
'minute': ['minuut', 'minuten', 'min'],
|
||||
'second': ['seconde', 'seconden', 'sec'],
|
||||
'millisecond': ['milliseconde', 'milliseconden', 'ms'],
|
||||
'combine': 'en',
|
||||
'error': 'Ongeldige datum'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'de',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['Jahr', 'Jahre', 'J.'],
|
||||
'month': ['Monat', 'Monate', 'M.'],
|
||||
'week': ['Woche', 'Wochen', 'Wo.'],
|
||||
'day': ['Tag', 'Tage', 'Tg.'],
|
||||
'hour': ['Stunde', 'Stunden', 'Std.'],
|
||||
'minute': ['Minute', 'Minuten', 'Min.'],
|
||||
'second': ['Sekunde', 'Sekunden', 'Sek.'],
|
||||
'millisecond': ['Milliseconde', 'Milliseconden', 'ms'],
|
||||
'combine': 'und',
|
||||
'error': 'Falsches Datum'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'pt',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['ano', 'anos', 'aa'],
|
||||
'month': ['mês', 'meses', 'mm'],
|
||||
'week': ['semana', 'semanas', 'sem'],
|
||||
'day': ['dia', 'dias', 'd'],
|
||||
'hour': ['hora', 'horas', 'h'],
|
||||
'minute': ['minuto', 'minutos', 'min'],
|
||||
'second': ['segundo', 'segundos', 'seg'],
|
||||
'millisecond': ['millissegundo', 'millissegundos', 'ms'],
|
||||
'combine': 'e',
|
||||
'error': 'Data Inválida'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'dk',
|
||||
'phrases':
|
||||
{
|
||||
'year': ['år', 'år', 'år'],
|
||||
'month': ['måned', 'måneder', 'mnd'],
|
||||
'week': ['uge', 'uger', 'uge'],
|
||||
'day': ['dag', 'dage', 'dag'],
|
||||
'hour': ['time', 'timer', 't.'],
|
||||
'minute': ['minut', 'minuter', 'min.'],
|
||||
'second': ['sekund', 'sekunder', 'sek.'],
|
||||
'millisecond': ['millisekund', 'millisekunder', 'ms.'],
|
||||
'combine': 'og',
|
||||
'error': 'Ugyldig dato'
|
||||
}
|
||||
}
|
||||
]
|
||||
%}
|
||||
{
|
||||
'language': 'en',
|
||||
'phrases': {
|
||||
'year': ['year', 'years', 'yr'],
|
||||
'month': ['month', 'months', 'mth'],
|
||||
'week': ['week', 'weeks', 'wk'],
|
||||
'day': ['day', 'days', 'day'],
|
||||
'hour': ['hour', 'hours', 'hr'],
|
||||
'minute': ['minute', 'minutes', 'min'],
|
||||
'second': ['second', 'seconds', 'sec'],
|
||||
'millisecond': ['millisecond', 'milliseconds', 'ms'],
|
||||
'combine': 'and',
|
||||
'error': 'Invalid date',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'pl',
|
||||
'phrases': {
|
||||
'year': ['rok', 'lat', 'r'],
|
||||
'month': ['miesiąc', 'miesięcy', 'msc'],
|
||||
'week': ['tydzień', 'tygodni', 'tyg'],
|
||||
'day': ['dzień', 'dni', 'dzień'],
|
||||
'hour': ['godzina', 'godzin', 'godz'],
|
||||
'minute': ['minuta', 'minut', 'min'],
|
||||
'second': ['sekunda', 'sekund', 'sek'],
|
||||
'millisecond': ['milisekunda', 'milisekund', 'ms'],
|
||||
'combine': 'i',
|
||||
'error': 'Niepoprawna data',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'fr',
|
||||
'phrases': {
|
||||
'year': ['année', 'années', 'an'],
|
||||
'month': ['mois', 'mois', 'mois'],
|
||||
'week': ['semaine', 'semaines', 'sem'],
|
||||
'day': ['jour', 'jours', 'j'],
|
||||
'hour': ['heure', 'heures', 'h'],
|
||||
'minute': ['minute', 'minutes', 'min'],
|
||||
'second': ['seconde', 'secondes', 'sec'],
|
||||
'millisecond': ['milliseconde', 'millisecondes', 'ms'],
|
||||
'combine': 'et',
|
||||
'error': 'Date non valide',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'it',
|
||||
'phrases': {
|
||||
'year': ['anno', 'anni', 'aa'],
|
||||
'month': ['mese', 'mesi', 'mm'],
|
||||
'week': ['settimana', 'settimane', 'set'],
|
||||
'day': ['giorno', 'giorni', 'gg'],
|
||||
'hour': ['ora', 'ore', 'h'],
|
||||
'minute': ['minuto', 'minuti', 'min'],
|
||||
'second': ['secondo', 'secondi', 'sec'],
|
||||
'millisecond': ['millisecondo', 'millisecondi', 'ms'],
|
||||
'combine': 'e',
|
||||
'error': 'Data non valida',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'nb',
|
||||
'phrases': {
|
||||
'year': ['år', 'år', 'år'],
|
||||
'month': ['måned', 'måneder', 'mnd'],
|
||||
'week': ['uke', 'uker', 'u'],
|
||||
'day': ['dag', 'dager', 'd'],
|
||||
'hour': ['time', 'timer', 't'],
|
||||
'minute': ['minutt', 'minutter', 'min'],
|
||||
'second': ['sekund', 'sekunder', 'sek'],
|
||||
'millisecond': ['millisekund', 'millisekunder', 'ms'],
|
||||
'combine': 'og',
|
||||
'error': 'Ugyldig dato',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'nl',
|
||||
'phrases': {
|
||||
'year': ['jaar', 'jaar', 'jr'],
|
||||
'month': ['maand', 'maanden', 'mnd'],
|
||||
'week': ['week', 'weken', 'wk'],
|
||||
'day': ['dag', 'dagen', 'dg'],
|
||||
'hour': ['uur', 'uur', 'u'],
|
||||
'minute': ['minuut', 'minuten', 'min'],
|
||||
'second': ['seconde', 'seconden', 'sec'],
|
||||
'millisecond': ['milliseconde', 'milliseconden', 'ms'],
|
||||
'combine': 'en',
|
||||
'error': 'Ongeldige datum',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'nn',
|
||||
'phrases': {
|
||||
'year': ['år', 'år', 'år'],
|
||||
'month': ['månad', 'månader', 'mnd'],
|
||||
'week': ['veke', 'veker', 'v'],
|
||||
'day': ['dag', 'dagar', 'd'],
|
||||
'hour': ['time', 'timar', 't'],
|
||||
'minute': ['minutt', 'minutt', 'min'],
|
||||
'second': ['sekund', 'sekund', 'sek'],
|
||||
'millisecond': ['millisekund', 'millisekund', 'ms'],
|
||||
'combine': 'og',
|
||||
'error': 'Ugyldig dato',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'de',
|
||||
'phrases': {
|
||||
'year': ['Jahr', 'Jahre', 'J.'],
|
||||
'month': ['Monat', 'Monate', 'M.'],
|
||||
'week': ['Woche', 'Wochen', 'Wo.'],
|
||||
'day': ['Tag', 'Tage', 'Tg.'],
|
||||
'hour': ['Stunde', 'Stunden', 'Std.'],
|
||||
'minute': ['Minute', 'Minuten', 'Min.'],
|
||||
'second': ['Sekunde', 'Sekunden', 'Sek.'],
|
||||
'millisecond': ['Millisekunde', 'Millisekunden', 'ms'],
|
||||
'combine': 'und',
|
||||
'error': 'Falsches Datum',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'pt',
|
||||
'phrases': {
|
||||
'year': ['ano', 'anos', 'aa'],
|
||||
'month': ['mês', 'meses', 'mm'],
|
||||
'week': ['semana', 'semanas', 'sem'],
|
||||
'day': ['dia', 'dias', 'd'],
|
||||
'hour': ['hora', 'horas', 'h'],
|
||||
'minute': ['minuto', 'minutos', 'min'],
|
||||
'second': ['segundo', 'segundos', 'seg'],
|
||||
'millisecond': ['millissegundo', 'millissegundos', 'ms'],
|
||||
'combine': 'e',
|
||||
'error': 'Data Inválida',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'dk',
|
||||
'phrases': {
|
||||
'year': ['år', 'år', 'år'],
|
||||
'month': ['måned', 'måneder', 'mnd'],
|
||||
'week': ['uge', 'uger', 'uge'],
|
||||
'day': ['dag', 'dage', 'dag'],
|
||||
'hour': ['time', 'timer', 't.'],
|
||||
'minute': ['minut', 'minuter', 'min.'],
|
||||
'second': ['sekund', 'sekunder', 'sek.'],
|
||||
'millisecond': ['millisekund', 'millisekunder', 'ms.'],
|
||||
'combine': 'og',
|
||||
'error': 'Ugyldig dato',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'sv',
|
||||
'phrases': {
|
||||
'year': ['år', 'år', 'år'],
|
||||
'month': ['månad', 'månader', 'mån'],
|
||||
'week': ['vecka', 'veckor', 'v'],
|
||||
'day': ['dag', 'dagar', 'dag'],
|
||||
'hour': ['timme', 'timmar', 'tim'],
|
||||
'minute': ['minut', 'minuter', 'min'],
|
||||
'second': ['sekund', 'sekunder', 'sek'],
|
||||
'millisecond': ['millisekund', 'millisekunder', 'ms'],
|
||||
'combine': 'och',
|
||||
'error': 'Ogiltigt datum',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'cs',
|
||||
'phrases': {
|
||||
'year': ['rok', 'roky', 'rok'],
|
||||
'month': ['měsíc', 'měsíce', 'měs'],
|
||||
'week': ['týden', 'týdny', 'týd'],
|
||||
'day': ['den', 'dny', 'd'],
|
||||
'hour': ['hodina', 'hodiny', 'hod'],
|
||||
'minute': ['minuta', 'minuty', 'min'],
|
||||
'second': ['sekunda', 'sekundy', 'sek'],
|
||||
'millisecond': ['millisekunda', 'millisekundy', 'ms'],
|
||||
'combine': 'a',
|
||||
'error': 'špatný datum'
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'fi',
|
||||
'phrases': {
|
||||
'year': ['vuosi', 'vuotta', 'v'],
|
||||
'month': ['kuukausi', 'kuukautta', 'kk'],
|
||||
'week': ['viikko', 'viikkoa', 'vk'],
|
||||
'day': ['päivä', 'päivää', 'pv'],
|
||||
'hour': ['tunti', 'tuntia', 't'],
|
||||
'minute': ['minuutti', 'minuuttia', 'min'],
|
||||
'second': ['sekunti', 'sekuntia', 's'],
|
||||
'millisecond': ['millisekunti', 'millisekuntia', 'ms'],
|
||||
'combine': 'ja',
|
||||
'error': 'Väärä päivämäärä',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'ru',
|
||||
'phrases': {
|
||||
'year': ['год', 'года', 'г'],
|
||||
'month': ['месяц', 'месяцы', 'м'],
|
||||
'week': ['неделя', 'недели', 'н'],
|
||||
'day': ['день', 'дни', 'д'],
|
||||
'hour': ['час', 'часы', 'ч'],
|
||||
'minute': ['минута', 'минут', 'м'],
|
||||
'second': ['секунд', 'секунды', 'с'],
|
||||
'millisecond': ['милисекунд', 'милисекунды', 'мс'],
|
||||
'combine': 'и',
|
||||
'error': 'Неверная дата',
|
||||
}
|
||||
},
|
||||
{
|
||||
'language': 'uk',
|
||||
'phrases': {
|
||||
'year': ['рік', 'років', 'р'],
|
||||
'month': ['місяць', 'місяців', 'м'],
|
||||
'week': ['тиждень', 'тижнів', 'тижд'],
|
||||
'day': ['день', 'днів', 'дн'],
|
||||
'hour': ['годину', 'годин', 'год'],
|
||||
'minute': ['хвилину', 'хвилин', 'хв'],
|
||||
'second': ['секунду', 'секунд', 'сек'],
|
||||
'millisecond': ['мілісекунду', 'мілісекунд', 'мсек'],
|
||||
'combine': 'та',
|
||||
'error': 'Недійсна дата',
|
||||
}
|
||||
},
|
||||
] -%}
|
||||
|
||||
{# macro to convert the abbreviated input for the not_use and always_show lists to the full time part names #}
|
||||
{%- macro _abbr_to_full(input) -%}
|
||||
{# determine not_use list #}
|
||||
{%- set abbr_to_full = dict(yr='year', mth='month', wk='week', day='day', hr='hour', min='minute', sec='second', ms='millisecond') -%}
|
||||
{%- set list = input if input is list else (input | replace(' ', '')).split(',') -%}
|
||||
{%- if list | select('in', abbr_to_full) | list | count > 0 -%}
|
||||
{%- set ns = namespace(output=[]) -%}
|
||||
{%- for i in list -%}
|
||||
{%- set ns.output = ns.output + [abbr_to_full[i] | default(i)] -%}
|
||||
{%- endfor -%}
|
||||
{%- set list = ns.output -%}
|
||||
{%- endif -%}
|
||||
{{- list | select('in', abbr_to_full.values()) | list | to_json -}}
|
||||
{%- endmacro -%}
|
||||
|
||||
{#
|
||||
macro to split a timedelta in years, months, weeks, days, hours, minutes, seconds
|
||||
macro to split a timedelta in years, months, weeks, days, hours, minutes, seconds and milliseconds
|
||||
used by the relative time plus macro, set up as a seperate macro so it can be reused
|
||||
#}
|
||||
{%- macro time_split(date, compare_date=now(), time=true, not_use=[]) -%}
|
||||
{# set defaults for variables #}
|
||||
{%- set date = date | as_local if time else date.date()-%}
|
||||
{%- macro time_split(date, parts=8, compare_date=now(), not_use=[], always_show=['all'], time=true, round_mode='floor') -%}
|
||||
{#- set defaults for input if not entered #}
|
||||
{%- set date = date if date is datetime else date | as_datetime('invalid') -%}
|
||||
{%- set compare_date = compare_date if compare_date is datetime else compare_date | as_datetime('invalid') -%}
|
||||
{%- set time = time | bool(true) -%}
|
||||
{%- set comp_date = compare_date if time else compare_date.date() -%}
|
||||
{%- set date_max = [comp_date, date] | max -%}
|
||||
{%- set date_min = [comp_date, date] | min -%}
|
||||
{#- set time periods in seconds #}
|
||||
{%- set m, h, d, w = 60, 3600, 86400, 604800 -%}
|
||||
{#- set numer of years, and set lowest date using this number of years #}
|
||||
{%- set yrs = date_max.year - date_min.year - (1 if date_max.replace(year=date_min.year) < date_min else 0) -%}
|
||||
{%- set date_max = date_max.replace(year=date_max.year - yrs) -%}
|
||||
{#- set numer of months, and set lowest date using this number of months #}
|
||||
{%- if 'month' not in not_use -%}
|
||||
{%- set mth = (date_max.month - date_min.month - (1 if date_max.day < date_min.day else 0) + 12) % 12 -%}
|
||||
{%- set month_new = (((date_max.month - mth) + 12) % 12) | default(12, true) -%}
|
||||
{%- set day_max = ((date_max.replace(day=1, month=month_new) + timedelta(days=31)).replace(day=1) - timedelta(days=1)).day -%}
|
||||
{%- set extra_days = [0, date_max.day - day_max] | max -%}
|
||||
{%- set date_temp = date_max.replace(month=month_new, day=[date_max.day, day_max]|min) -%}
|
||||
{%- set date_max = date_temp if date_temp <= date_max else date_temp.replace(year=date_max.year-1) -%}
|
||||
{%- set mth = mth + yrs * 12 if 'year' in not_use else mth -%}
|
||||
{%- endif -%}
|
||||
{%- set date_max = date_max.replace(year=date_max.year + yrs) if 'year' in not_use and 'month' in not_use else date_max -%}
|
||||
{%- set yrs = 0 if 'year' in not_use else yrs -%}
|
||||
{#- set other time period variables #}
|
||||
{%- set s = (date_max - date_min).total_seconds() + extra_days | default(0) * 86400 -%}
|
||||
{%- set wks = 0 if 'week' in not_use else (s // w) | int -%}
|
||||
{%- set day = 0 if 'day' in not_use else ((s - wks * w) // d) | int -%}
|
||||
{%- set hrs = 0 if 'hour' in not_use else ((s - wks * w - day * d) // h) | int -%}
|
||||
{%- set min = 0 if 'minute' in not_use else ((s - wks * w - day * d - hrs * h) // m) | int -%}
|
||||
{%- set sec = 0 if 'second' in not_use else (s - wks * w - day * d - hrs * h - min * m) | int -%}
|
||||
{%- set ms = (s % 1 * 1000) | round | int -%}
|
||||
{# output result #}
|
||||
{%- set output = dict(year=yrs, month=mth | default(0), week=wks, day=day, hour=hrs, minute=min, second=sec, millisecond=ms) %}
|
||||
{{- dict(output.items() | rejectattr('0', 'in', not_use)) | to_json -}}
|
||||
{%- set parts = [parts | int(1), always_show | count] | max -%}
|
||||
{# 1: check if date input is correct #}
|
||||
{%- if date is datetime and compare_date is datetime -%}
|
||||
{# convert date input to local or date only #}
|
||||
{%- set date = date | as_local if time else (date | as_local).date() -%}
|
||||
{%- set compare_date = compare_date | as_local if time else (compare_date | as_local).date() -%}
|
||||
{# determine highest and lowest date #}
|
||||
{%- set date_max = [compare_date, date] | max -%}
|
||||
{%- set date_min = [compare_date, date] | min -%}
|
||||
{#- set time periods in seconds #}
|
||||
{%- set days_year = 365 + (1 if (compare_date.replace(month=3, day=1) - timedelta(days=1)).day == 29 else 0) -%}
|
||||
{%- set days_month = ((compare_date.replace(day=20) + timedelta(days=20)).replace(day=1) - timedelta(days=1)).day -%}
|
||||
{%- set dur = dict(
|
||||
year=days_year * 86400000,
|
||||
month=days_month * 86400000,
|
||||
week=604800000,
|
||||
day=86400000,
|
||||
hour=3600000,
|
||||
minute=60000,
|
||||
second=1000,
|
||||
millisecond=1,
|
||||
)
|
||||
-%}
|
||||
{# make sure input for not_use and always_show is correct #}
|
||||
{%- if not not_use in [['millisecond'], []] -%}
|
||||
{%- set not_use = _abbr_to_full(not_use) | from_json -%}
|
||||
{%- endif -%}
|
||||
{%- set not_use = not_use + ['hour', 'minute', 'second', 'millisecond' ] if not time else not_use -%}
|
||||
{%- if always_show in [['all'], 'all'] -%}
|
||||
{%- set always_show = dur.keys() | list -%}
|
||||
{%- elif always_show != [] -%}
|
||||
{%- set always_show = _abbr_to_full(always_show) | from_json | reject('in' , not_use) | list -%}
|
||||
{%- endif -%}
|
||||
{%- set always_show = always_show | reject('in', not_use) | list -%}
|
||||
{%- set do_use = dur.keys() | reject('in', not_use) | list -%}
|
||||
{# determine number of milliseconds #}
|
||||
{%- set ms = ((date_max - date_min).total_seconds() * 1000) | round(0, 'ceil')-%}
|
||||
{# 2: Check if the number of milliseconds is more then the duration of the last time part to output #}
|
||||
{%- if do_use and ms < dur[do_use|last] -%}
|
||||
{{- {do_use | last: (ms / dur[do_use|last]) | round(0, round_mode)} | to_json -}}
|
||||
{%- else -%}
|
||||
{# check if it is needed to determine years #}
|
||||
{%- if ms >= dur.day * 365 -%}
|
||||
{#- set numer of years, and set highest date using this number of years #}
|
||||
{%- set yrs = date_max.year - date_min.year - (1 if date_max.replace(year=date_min.year) < date_min else 0) -%}
|
||||
{%- set date_max = date_max.replace(year=date_max.year - yrs) -%}
|
||||
{%- set ms = (date_max - date_min).total_seconds() * 1000 -%}
|
||||
{%- set ms_yrs = ms -%}
|
||||
{%- endif -%}
|
||||
{%- set yrs = yrs | default(0) -%}
|
||||
{# check if it is needed to determine months #}
|
||||
{%- set check_mth =
|
||||
ms >= dur.day * 28
|
||||
and 'month' in do_use
|
||||
-%}
|
||||
{%- if check_mth -%}
|
||||
{#- set numer of months, and set highest date using this number of months #}
|
||||
{%- set ns = namespace(dm=date_max, mth=0) -%}
|
||||
{%- set dmd = ns.dm.day -%}
|
||||
{%- for m in range(1, 12) -%}
|
||||
{%- set dmm, dmy = ns.dm.month, ns.dm.year -%}
|
||||
{%- set day_max = (ns.dm.replace(day=1) - timedelta(days=1)).day -%}
|
||||
{%- set dm = ns.dm.replace(
|
||||
month=12 if dmm == 1 else dmm - 1,
|
||||
year=dmy - 1 if dmm == 1 else dmy,
|
||||
day= [dmd, day_max] | min
|
||||
)
|
||||
-%}
|
||||
{%- if dm < date_min -%}
|
||||
{%- break -%}
|
||||
{%- else -%}
|
||||
{%- set ns.mth = ns.mth + 1 -%}
|
||||
{%- set ns.dm = dm -%}
|
||||
{%- endif -%}
|
||||
{%- endfor -%}
|
||||
{%- set date_max, mth = ns.dm, ns.mth -%}
|
||||
{%- set mth = mth + yrs * 12 if 'year' in not_use else mth -%}
|
||||
{%- set ms = (date_max - date_min).total_seconds() * 1000 -%}
|
||||
{%- endif -%}
|
||||
{%- set mth = mth | default(0) -%}
|
||||
{# prepare for other time parts #}
|
||||
{%- set date_max = date_max.replace(year=date_max.year + yrs) if 'year' in not_use and 'month' in not_use else date_max -%}
|
||||
{#- set other time period variables #}
|
||||
{%- set ms = ((date_max - date_min).total_seconds() * 1000 + extra_days | default(0) * dur.day) | round(0) -%}
|
||||
{%- set wks = (ms // dur.week) | int -%}
|
||||
{%- set days = ((ms % dur.week // dur.day) + (wks * dur.week / dur.day if 'week' in not_use else 0)) | int -%}
|
||||
{%- set hrs = ((ms % dur.day // dur.hour) + (days * dur.day / dur.hour if 'day' in not_use else 0)) | int -%}
|
||||
{%- set min = ((ms % dur.hour // dur.minute) + (hrs * dur.hour / dur.minute if 'hour' in not_use else 0)) | int -%}
|
||||
{%- set sec = ((ms % dur.minute // dur.second) + (min * dur.minute / dur.second if 'minute' in not_use else 0)) | int -%}
|
||||
{%- set mis = ((ms % dur.second) | round + (sec * dur.second if 'second' in not_use else 0)) | int -%}
|
||||
{# prepare dict with ouput #}
|
||||
{%- set output = dict(year=yrs, month=mth | default(0), week=wks, day=days, hour=hrs, minute=min, second=sec, millisecond=mis) -%}
|
||||
{%- set output = dict(output.items() | selectattr('0', 'in', do_use)) -%}
|
||||
{%- set keys = output.keys() | list -%}
|
||||
{%- set with_value = output.items() | rejectattr('1', 'eq', 0) | map(attribute='0') | list -%}
|
||||
{%- set first = with_value | first | default('millisecond') -%}
|
||||
{%- set first = keys | select('in', always_show | default([], true) + [first]) | first -%}
|
||||
{%- set to_use = keys[keys.index(first):] -%}
|
||||
{%- set to_output = to_use[:parts] -%}
|
||||
{%- set last = to_output | last |default('millisecond') -%}
|
||||
{# 3: check if there is anything left to use #}
|
||||
{%- if to_use -%}
|
||||
{%- set to_output = to_use[:parts] -%}
|
||||
{%- set always_return = to_output | last -%}
|
||||
{# check if all values for always_show are included #}
|
||||
{%- set as_check = always_show | reject('in', to_output) | list | count -%}
|
||||
{%- if always_show and as_check > 0 -%}
|
||||
{%- set to_reject = to_use | reject('in', to_output) | reject('in', always_show) | list -%}
|
||||
{%- set not_use = not_use + to_output[as_check*-1:] + to_reject -%}
|
||||
{%- set to_output = to_output | reject('in', not_use) | list + always_show -%}
|
||||
{%- set to_output = keys | select('in', to_output) | list -%}
|
||||
{%- set output = time_split(date, parts, compare_date, not_use, always_show, time, round_mode) | from_json -%}
|
||||
{%- endif -%}
|
||||
{# apply round if needed #}
|
||||
{%- if round_mode in ['common', 'ceil'] and last != 'millisecond' -%}
|
||||
{# determine first and last item with data #}
|
||||
{%- set ms = ms_yrs if last == 'year' else ms -%}
|
||||
{%- set remain = ms % dur[last] -%}
|
||||
{%- set remain_part = remain / dur[last] -%}
|
||||
{%- set to_round = 1 if remain_part >= 0.5 and round_mode == 'common' else remain_part | round(0, round_mode) -%}
|
||||
{%- set sec_to_add = ((dur[last] + (dur.day if last in ['year', 'month'] else 1) - remain) | round(0, 'ceil') * to_round) / 1000 -%}
|
||||
{%- set round_mode = 'floor' -%}
|
||||
{%- set date_max = [compare_date, date] | max + timedelta(seconds=sec_to_add) -%}
|
||||
{%- set date_min = [compare_date, date] | min -%}
|
||||
{%- set output = time_split(date_max, parts, date_min, not_use, always_show, time, round_mode) | from_json -%}
|
||||
{%- endif -%}
|
||||
{# output result #}
|
||||
{%- set zero_values = output.items() | selectattr('1', 'eq', 0) | map(attribute='0') | list -%}
|
||||
{%- set reject_list = zero_values | reject('in', always_show) | list -%}
|
||||
{{- dict(output.items() | selectattr('0', 'in', to_output) | rejectattr('0', 'in', reject_list)) | default({always_return: 0}, true) | to_json -}}
|
||||
{%- else -%} {{- dict(error='No time parts left to output') | to_json -}}
|
||||
{%- endif -%} {# 3 #}
|
||||
{%- endif -%} {# 2 #}
|
||||
{%- else -%} {{- dict(error='Invalid date input') | to_json -}}
|
||||
{%- endif -%} {# 1 #}
|
||||
{%- endmacro -%}
|
||||
|
||||
{# macro to output a timedelta in a readable format #}
|
||||
{%- macro relative_time_plus(date, parts=1, abbr=false, verbose=false, language='en', compare_date=now(), month=none, week=none, millisecond=none, not_use=['millisecond'], always_show=[], time=true) -%}
|
||||
{#- set defaults for input if not entered #}
|
||||
{%- set date = date if date is datetime else date | as_datetime -%}
|
||||
{%- set compare_date = compare_date if compare_date is datetime else compare_date | as_datetime -%}
|
||||
{%- macro relative_time_plus(date, parts=1, abbr=false, language='en', compare_date=now(), not_use=['millisecond'], always_show=[], time=true, round_mode='floor') -%}
|
||||
{#- select correct phrases bases on language input #}
|
||||
{%- set phrases = _time_period_phrases -%}
|
||||
{%- set languages = phrases | map(attribute='language') | list -%}
|
||||
{%- set language = iif(language in languages, language, 'en') -%}
|
||||
{%- set phr = phrases | selectattr('language', 'eq', language) | map(attribute='phrases') | list | first -%}
|
||||
{#- perform smart stuff #}
|
||||
{%- if date is datetime and compare_date is datetime -%}
|
||||
{# determine not_use list #}
|
||||
{%- set abbr_to_full = dict(yr='year', mth='month', wk='week', hr='hour', min='minute', sec='second', ms='millisecond') -%}
|
||||
{%- set add = [('month', month),('week',week),('millisecond',millisecond)] | selectattr('1', 'eq', false) | map(attribute='0') | list -%}
|
||||
{%- set not_use = not_use if not_use is list else (not_use | replace(' ', '')).split(',') -%}
|
||||
{%- set not_use = (not_use + add) | unique | list -%}
|
||||
{%- if not_use | select('in', abbr_to_full) | list | count > 0 -%}
|
||||
{%- set ns = namespace(not_use=[]) -%}
|
||||
{%- for i in not_use -%}
|
||||
{%- set ns.not_use = ns.not_use + [abbr_to_full[i] | default(i)] -%}
|
||||
{%- endfor -%}
|
||||
{%- set not_use = ns.not_use | unique | list -%}
|
||||
{%- endif -%}
|
||||
{# set variables #}
|
||||
{%- set date, compare_date = date | as_local, compare_date | as_local -%}
|
||||
{%- set parts = parts | int(1) -%}
|
||||
{%- set time = time | bool(true) -%}
|
||||
{%- set abbr = abbr | bool(false) or verbose | bool(false) -%}
|
||||
{# split timedelta #}
|
||||
{%- set time_parts = time_split(date, compare_date, time, not_use) | from_json -%}
|
||||
{#- find first non zero time period #}
|
||||
{%- set time_periods = ['year', 'month', 'week', 'day', 'hour', 'minute', 'second', 'millisecond'] -%}
|
||||
{%- set do_use = time_periods | reject('in', not_use) | list -%}
|
||||
{# continue if there are still time periods to use #}
|
||||
{%- if do_use | count > 0 -%}
|
||||
{%- set always_return = do_use | last -%}
|
||||
{%- set always_show = always_show if always_show is list else (always_show | replace(' ', '')).split(',') -%}
|
||||
{%- if always_show | select('in', abbr_to_full) | list | count > 0 -%}
|
||||
{%- set ns = namespace(always_show=[]) -%}
|
||||
{%- for i in always_show -%}
|
||||
{%- set ns.always_show = ns.always_show + [abbr_to_full[i] | default(i)] -%}
|
||||
{%- endfor -%}
|
||||
{%- set always_show = ns.always_show | unique | list -%}
|
||||
{%- endif -%}
|
||||
{%- set parts = [parts, always_show | count] | max -%}
|
||||
{%- set to_show = (time_parts.items() | selectattr('1') | map(attribute='0') | list + always_show) | unique | list | default([always_return], true) -%}
|
||||
{%- set first = do_use | select('in', to_show) | first -%}
|
||||
{#-select itemw to show based on input #}
|
||||
{%- set index_first = (time_parts.keys() | list).index(first) -%}
|
||||
{%- set items = (time_parts.keys() | list)[index_first:index_first + parts] -%}
|
||||
{# convert to phrases #}
|
||||
{%- set ns = namespace(phrases=[]) -%}
|
||||
{%- for i in items if i in to_show or i == first -%}
|
||||
{%- set phr_abbr = phr[i][2] -%}
|
||||
{%- set phr_verb = phr[i][1] if time_parts[i] != 1 else phr[i][0] -%}
|
||||
{%- set phrase = '{} {}'.format(time_parts[i], phr_abbr if abbr else phr_verb) -%}
|
||||
{%- set ns.phrases = ns.phrases + [phrase] -%}
|
||||
{%- endfor -%}
|
||||
{#- join phrases in a string, using phr.combine for the last item #}
|
||||
{{- '{} {} {}'.format(ns.phrases[:-1] | join(', '), phr.combine, ns.phrases[-1]) if ns.phrases | count > 1 else ns.phrases | first -}}
|
||||
{%- else -%}
|
||||
All time periods are excluded
|
||||
{%- endif -%}
|
||||
{%- set abbr = abbr | bool(false) -%}
|
||||
{# split timedelta #}
|
||||
{%- set time_parts = time_split(date, parts, compare_date, not_use, always_show, time, round_mode) | from_json -%}
|
||||
{# check for error #}
|
||||
{%- if 'error' in time_parts -%}
|
||||
{{- time_parts['error'] -}}
|
||||
{%- else -%}
|
||||
{{- phr.error -}}
|
||||
{# convert to phrases #}
|
||||
{%- set ns = namespace(phrases=[]) -%}
|
||||
{%- for i in time_parts.keys() -%}
|
||||
{%- set phr_abbr = phr[i][2] -%}
|
||||
{%- set phr_verb = phr[i][1] if time_parts[i] != 1 else phr[i][0] -%}
|
||||
{%- set phrase = '{} {}'.format(time_parts[i], phr_abbr if abbr else phr_verb) -%}
|
||||
{%- set ns.phrases = ns.phrases + [phrase] -%}
|
||||
{%- endfor -%}
|
||||
{#- join phrases in a string, using phr.combine for the last item #}
|
||||
{{- '{} {} {}'.format(ns.phrases[:-1] | join(', '), phr.combine, ns.phrases[-1]) if ns.phrases | count > 1 else ns.phrases | first -}}
|
||||
{%- endif -%}
|
||||
{%- endmacro -%}
|
||||
{%- endmacro -%}
|
||||
|
||||
11
custom_templates/server.jinja
Normal file
11
custom_templates/server.jinja
Normal file
@@ -0,0 +1,11 @@
|
||||
{% from 'formatting.jinja' import cleanup %}
|
||||
|
||||
{% macro services_down() %}
|
||||
{% if states('sensor.services_down') | int == 1 %}
|
||||
There is one service offline. It is {{ state_attr('sensor.services_down','services') }}.
|
||||
{% elif states('sensor.services_down') | int > 1 %}
|
||||
There are {{ states('sensor.services_down') }} services currently offline. They are {{ state_attr('sensor.services_down','services') }}.
|
||||
{% else %}
|
||||
There are no services currently offline.
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
@@ -146,7 +146,7 @@ It is {{ now().strftime("%I:%M %p") }}.
|
||||
{% endmacro %}
|
||||
|
||||
{% macro kallenSleepMsg() %}
|
||||
{% set schedMode = states('input_select.scheduled_climate_mode_kallen_fan') %}
|
||||
{% set schedMode = states('input_select.scheduled_climate_mode_kallen_bedroom') %}
|
||||
{% if schedMode == 'White Noise' %}
|
||||
{{ [
|
||||
"No fan in Collin's room tonight. Too cold outside. Brr. Enjoy your white noise.",
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
{% if is_state(team,'PRE') %}
|
||||
{% set date = state_attr(team,'date') | as_timestamp | timestamp_custom('%m-%d') %}
|
||||
{% if date == now().strftime('%m-%d') %}
|
||||
The {{ state_attr(team,'friendly_name') }} will be playing today against the {{ state_attr(team,'opponent_name') }} at {{ state_attr(team,'venue') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} will be playing today against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} at {{ state_attr(team,'venue') }}.
|
||||
{{ sports_str(team,'start') }} is at {{ state_attr(team,'date') | as_timestamp | timestamp_custom('%I:%M %p') }}.
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
@@ -34,11 +34,11 @@
|
||||
{% if state_attr(team,'clock') in ['postponed','Postponed'] %}
|
||||
The {{ state_attr(team,'friendly_name') }} had their game postponed today, and it will be played at a later date.
|
||||
{% elif (state_attr(team,'team_score') | int) == state_attr(team,'opponent_score') | int %}
|
||||
The {{ state_attr(team,'friendly_name') }} tied in their game today against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} tied in their game today against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% elif state_attr(team,'team_winner') == true %}
|
||||
The {{ state_attr(team,'friendly_name') }} won their game today against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} won their game today against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% elif state_attr(team,'opponent_winner') == true %}
|
||||
The {{ state_attr(team,'friendly_name') }} lost their game today against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} lost their game today against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
{% endif %}
|
||||
{% if state_attr(team,'clock') not in ['postponed','Postponed'] %}
|
||||
This brings their record to {{ state_attr(team,'team_record') | replace("-"," and ") }} on the season.
|
||||
@@ -47,11 +47,11 @@
|
||||
{% if state_attr(team,'clock') in ['postponed','Postponed'] %}
|
||||
The {{ state_attr(team,'friendly_name') }} had their game postponed yesterday, and it will be played at a later date.
|
||||
{% elif (state_attr(team,'team_score') | int) == state_attr(team,'opponent_score') | int %}
|
||||
The {{ state_attr(team,'friendly_name') }} tied in their game yesterday against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} tied in their game yesterday against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% elif state_attr(team,'team_winner') == true %}
|
||||
The {{ state_attr(team,'friendly_name') }} won their game yesterday against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} won their game yesterday against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% elif state_attr(team,'opponent_winner') == true %}
|
||||
The {{ state_attr(team,'friendly_name') }} lost their game yesterday against the {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} lost their game yesterday against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} by a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
{% endif %}
|
||||
{% if state_attr(team,'clock') not in ['postponed','Postponed'] %}
|
||||
This brings their record to {{ state_attr(team,'team_record') | replace("-"," and ") }} on the season.
|
||||
@@ -59,11 +59,11 @@
|
||||
{% endif %}
|
||||
{% elif is_state(team,'IN') %}
|
||||
{% if (state_attr(team,'team_score') | int) == (state_attr(team,'opponent_score') | int) %}
|
||||
The {{ state_attr(team,'friendly_name') }} are currently tied in their game against the {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} are currently tied in their game against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% elif (state_attr(team,'team_score') | int) > (state_attr(team,'opponent_score') | int) %}
|
||||
The {{ state_attr(team,'friendly_name') }} are currently winning their game against the {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} are currently winning their game against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'team_score') }} to {{ state_attr(team,'opponent_score') }}.
|
||||
{% else %}
|
||||
The {{ state_attr(team,'friendly_name') }} are currently losing their game against the {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
The {{ state_attr(team,'friendly_name') }} are currently losing their game against {% if state_attr(team,'league') != 'NCAAF'%}the{% endif %} {{ state_attr(team,'opponent_name') }} with a score of {{ state_attr(team,'opponent_score') }} to {{ state_attr(team,'team_score') }}.
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
@@ -71,7 +71,9 @@
|
||||
{% endmacro %}
|
||||
|
||||
{% macro sports_inhibit(team) %}
|
||||
{% if state_attr(team,'kickoff_in') %}
|
||||
{% if is_state(team,'NOT_FOUND') %}
|
||||
true
|
||||
{% elif state_attr(team,'kickoff_in') %}
|
||||
{{ 'months' in state_attr(team,'kickoff_in') or
|
||||
'month' in state_attr(team,'kickoff_in') or
|
||||
'weeks' in state_attr(team,'kickoff_in') }}
|
||||
@@ -107,12 +109,12 @@
|
||||
{% if is_state('binary_sensor.san_francisco_49ers_inhibit','off') %}
|
||||
{{ sports_pregame('sensor.san_francisco_49ers') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.cleveland_guardians_inhibit','off') %}
|
||||
{{ sports_pregame('sensor.cleveland_guardians') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.minnesota_twins_inhibit','off') %}
|
||||
{{ sports_pregame('sensor.minnesota_twins') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.cleveland_guardians_inhibit','off') %}
|
||||
{{ sports_pregame('sensor.cleveland_guardians') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.los_angeles_dodgers_inhibit','off') %}
|
||||
{{ sports_pregame('sensor.los_angeles_dodgers') }}
|
||||
{% endif %}
|
||||
@@ -135,12 +137,12 @@
|
||||
{% if is_state('binary_sensor.san_francisco_49ers_inhibit','off') %}
|
||||
{{ sports_main('sensor.san_francisco_49ers') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.cleveland_guardians_inhibit','off') %}
|
||||
{{ sports_main('sensor.cleveland_guardians') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.minnesota_twins_inhibit','off') %}
|
||||
{{ sports_main('sensor.minnesota_twins') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.cleveland_guardians_inhibit','off') %}
|
||||
{{ sports_main('sensor.cleveland_guardians') }}
|
||||
{% endif %}
|
||||
{% if is_state('binary_sensor.los_angeles_dodgers_inhibit','off') %}
|
||||
{{ sports_main('sensor.los_angeles_dodgers') }}
|
||||
{% endif %}
|
||||
@@ -152,4 +154,6 @@
|
||||
{{ cleanup(data()) }}
|
||||
{% endmacro %}
|
||||
|
||||
{{ sports_updates('pregame') }}
|
||||
{% macro sports_datetime(team) %}
|
||||
{{ as_timestamp(state_attr(team,'date')) | timestamp_custom('%Y-%m-%d %H:%M:%S') }}
|
||||
{% endmacro%}
|
||||
|
||||
@@ -13,9 +13,21 @@
|
||||
{% set houseEveningRan = is_state('input_boolean.house_scheduling_evening_ran','on') %}
|
||||
{% set masterBedroomEveningRan = is_state('input_boolean.master_bedroom_scheduling_evening_ran','on') %}
|
||||
{% set emmaEveningRan = is_state('input_boolean.emma_scheduling_evening_ran','on') %}
|
||||
{% set kallenMorningAnnc = is_state('input_boolean.kallen_morning_announcements','on') %}
|
||||
{% set kallenText = 'Kallen' %}
|
||||
{% set kallenTTS = 'Collin' %}
|
||||
|
||||
{% macro morning_annc(type,method) %}
|
||||
{% if method == 'text' %}
|
||||
{% set identKallen = kallenText %}
|
||||
{% elif method == 'tts' %}
|
||||
{% set identKallen = kallenTTS %}
|
||||
{% endif %}
|
||||
{% if kallenMorningAnnc %}
|
||||
First things first, we have some announcements for {{ identKallen }}. {{ states('input_text.kallen_morning_announcements') }}
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
|
||||
{% macro laundry_report(type,method) %}
|
||||
{% macro data() %}
|
||||
{% set washerTimer = states('timer.washer_timer') %}
|
||||
@@ -591,38 +603,20 @@
|
||||
{% endmacro %}
|
||||
|
||||
{% macro emma_sleep(type,method) %}
|
||||
{% set asleep = state_attr('input_datetime.emma_down_for_nap','timestamp') | int %}
|
||||
{% set wakeup = state_attr('input_datetime.emma_up_from_nap','timestamp') | int %}
|
||||
{% set day = now().strftime("%-d") %}
|
||||
{% set asleep_day = asleep | timestamp_custom("%-d") %}
|
||||
{% set wakeup_day = wakeup | timestamp_custom("%-d") %}
|
||||
{% if is_state('input_boolean.emma_sleeping','off') and (is_state('input_boolean.emma_has_napped','on') or ((asleep_day == day) and (wakeup > asleep))) %}
|
||||
Emma napped today for {{ custom_time_between('input_datetime.emma_down_for_nap','input_datetime.emma_up_from_nap','hour,minute') }}. She was retrieved from her room at around {{ input_datetime_read('input_datetime.emma_up_from_nap') | trim }}.
|
||||
{% elif (is_state('input_boolean.emma_has_napped','off') and (((asleep_day == day) and (wakeup_day != day)) or wakeup < asleep)) and is_state('input_boolean.emma_sleeping','on') %}
|
||||
Emma is down for nap. She was put down at around {{ input_datetime_read('input_datetime.emma_down_for_nap') | trim }}. She has been asleep for {{ custom_time('input_datetime.emma_down_for_nap','hour,minute') }}.
|
||||
{% elif is_state('input_boolean.emma_sleeping','on') %}
|
||||
{% if is_state('input_boolean.emma_sleeping','on') %}
|
||||
{% if is_state('binary_sensor.early_night_mode','on') %}
|
||||
Emma is asleep for the night. She went to bed at {{ input_datetime_read('input_datetime.emma_asleep_at') | trim }}.
|
||||
{% else %}
|
||||
Emma has not yet awoken for the day. She went to bed at {{ input_datetime_read('input_datetime.emma_asleep_at') | trim }}. Her wakeup time is scheduled for {{ input_datetime_read('input_datetime.emma_wakeup') | trim }}.
|
||||
{% endif %}
|
||||
{% else %}
|
||||
Emma is awake, and does not appear to have napped yet. She woke up at {{ input_datetime_read('input_datetime.emma_awake_at') | trim }}.
|
||||
Emma is awake. She woke up at {{ input_datetime_read('input_datetime.emma_awake_at') | trim }}.
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
|
||||
{% macro emma_sleep_notification(type,method) %}
|
||||
{% set asleep = state_attr('input_datetime.emma_down_for_nap','timestamp') | int %}
|
||||
{% set wakeup = state_attr('input_datetime.emma_up_from_nap','timestamp') | int %}
|
||||
{% set day = now().strftime("%-d") %}
|
||||
{% set asleep_day = asleep | timestamp_custom("%-d") %}
|
||||
{% set wakeup_day = wakeup | timestamp_custom("%-d") %}
|
||||
{% if is_state('input_boolean.emma_sleeping','off') and (is_state('input_boolean.emma_has_napped','on') or ((asleep_day == day) and (wakeup > asleep))) %}
|
||||
Emma has awoken. She napped today for {{ custom_time_between('input_datetime.emma_down_for_nap','input_datetime.emma_up_from_nap','hour,minute') }}. She was retrieved from her room at {{ clock('12-hr') }}
|
||||
{% elif is_state('input_boolean.emma_has_napped','off') and is_state('input_boolean.emma_sleeping','off') and ((asleep_day != day) or (wakeup_day != day)) %}
|
||||
{% if is_state('input_boolean.emma_sleeping','off') %}
|
||||
Emma has awoken for the day at {{ clock('12-hr') }}
|
||||
{% elif is_state('input_boolean.emma_has_napped','off') and ((asleep_day == day) and (wakeup_day != day)) and is_state('input_boolean.emma_sleeping','on') %}
|
||||
Emma is being put down for nap. She was put down at {{ clock('12-hr') }}
|
||||
{% elif is_state('input_boolean.emma_sleeping','on') %}
|
||||
Emma is asleep for the night (or at least, her sleep switch is active) at {{ clock('12-hr') }}
|
||||
{% else %}
|
||||
|
||||
@@ -68,6 +68,31 @@
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
|
||||
{% macro datetime_from_calendar(calendar,start_or_end,action,operator,days,hours,minutes) %}
|
||||
{% set base = as_timestamp(strptime(state_attr(calendar,start_or_end), '%Y-%m-%d %H:%M:%S')) | int %}
|
||||
{% if minutes is defined %}
|
||||
{% set mod = ((((days * 24) * 60) * 60) + (hours* 60) * 60) + (minutes * 60) | int %}
|
||||
{% elif hours is defined %}
|
||||
{% set mod = (((days * 24) * 60) * 60) + (hours* 60) * 60 | int %}
|
||||
{% elif days is defined %}
|
||||
{% set mod = ((days * 24) * 60) * 60 | int %}
|
||||
{% endif %}
|
||||
{% if action == 'set' %}
|
||||
{% set ts = "%Y-%m-%d %H:%M:%S" %}
|
||||
{% elif action == 'read' %}
|
||||
{% set ts = "%Y-%m-%d %-I:%M %p" %}
|
||||
{% endif %}
|
||||
{% if operator is defined %}
|
||||
{% if operator == 'add' %}
|
||||
{{ (base + mod) | timestamp_custom(ts) }}
|
||||
{% elif operator == 'subtract' %}
|
||||
{{ (base - mod) | timestamp_custom(ts) }}
|
||||
{% endif %}
|
||||
{% else %}
|
||||
{{ base | timestamp_custom(ts) }}
|
||||
{% endif %}
|
||||
{% endmacro %}
|
||||
|
||||
{% macro set_datetime(hours,minutes,seconds) %}
|
||||
{% if seconds is defined %}
|
||||
{{ (as_timestamp(now()) + (((hours * 60) * 60) + (minutes * 60)) + seconds) | int | timestamp_custom('%Y-%m-%d %H:%M:%S') }}
|
||||
|
||||
25
issue_template/adjustment.yaml
Normal file
25
issue_template/adjustment.yaml
Normal file
@@ -0,0 +1,25 @@
|
||||
name: Adjustment
|
||||
about: Request a change/adjustment to an existing feature
|
||||
title: "[Adjustment]: "
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Thanks for taking the time to fill out this adjustment request!
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
This issue was created by an issue **template**
|
||||
visible: [content]
|
||||
- type: textarea
|
||||
id: adjustment-request
|
||||
attributes:
|
||||
label: Describe your request
|
||||
description: Which existing feature would you like changed/adjusted?
|
||||
placeholder: Tell me what you want, what you really really want!
|
||||
value: "Request here!"
|
||||
validations:
|
||||
required: true
|
||||
labels:
|
||||
- type/adjustment
|
||||
- needs-response
|
||||
25
issue_template/bug_report.yaml
Normal file
25
issue_template/bug_report.yaml
Normal file
@@ -0,0 +1,25 @@
|
||||
name: Bug Report
|
||||
about: Report a bug that you have found
|
||||
title: "[Bug]: "
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Thanks for taking the time to fill out this bug report!
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
This issue was created by an issue **template**
|
||||
visible: [content]
|
||||
- type: textarea
|
||||
id: what-happened
|
||||
attributes:
|
||||
label: What happened?
|
||||
description: Also, what were you expecting to happen?
|
||||
placeholder: Tell me what you saw!
|
||||
value: "A bug happened!"
|
||||
validations:
|
||||
required: true
|
||||
labels:
|
||||
- type/bug
|
||||
- needs-response
|
||||
1
issue_template/config.yaml
Normal file
1
issue_template/config.yaml
Normal file
@@ -0,0 +1 @@
|
||||
blank_issues_enabled: false
|
||||
25
issue_template/feature_request.yaml
Normal file
25
issue_template/feature_request.yaml
Normal file
@@ -0,0 +1,25 @@
|
||||
name: Feature Request
|
||||
about: Request a new feature to be added
|
||||
title: "[Feature Request]: "
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Thanks for taking the time to fill out this feature request form!
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
This issue was created by an issue **template**
|
||||
visible: [content]
|
||||
- type: textarea
|
||||
id: feature-request
|
||||
attributes:
|
||||
label: Feature Request
|
||||
description: What new feature would you like to see?
|
||||
placeholder: What is your feature request!
|
||||
value: "I would like this feature"
|
||||
validations:
|
||||
required: true
|
||||
labels:
|
||||
- type/enhancement
|
||||
- needs-response
|
||||
@@ -61,6 +61,10 @@ input_text:
|
||||
name: Kallen Briefing Extras
|
||||
icon: mdi:plus
|
||||
max: 255
|
||||
kallen_morning_announcements:
|
||||
name: Kallen Morning Announcements
|
||||
icon: mdi:bullhorn
|
||||
max: 255
|
||||
|
||||
input_boolean:
|
||||
briefing_extras:
|
||||
@@ -69,6 +73,9 @@ input_boolean:
|
||||
kallen_briefing_extras:
|
||||
name: Kallen Briefing Extras
|
||||
icon: mdi:plus
|
||||
kallen_morning_announcements:
|
||||
name: Kallen Morning Announcements
|
||||
icon: mdi:bullhorn
|
||||
good_morning:
|
||||
name: Good Morning Ran
|
||||
icon: mdi:home-analytics
|
||||
@@ -96,6 +103,15 @@ input_boolean:
|
||||
sun_reports:
|
||||
name: Sun Reports
|
||||
icon: mdi:weather-sunny-alert
|
||||
morning_briefing_allowed:
|
||||
name: Morning Briefing Allowed
|
||||
icon: mdi:bullhorn
|
||||
daily_briefing_allowed:
|
||||
name: Daily Briefing Allowed
|
||||
icon: mdi:bullhorn
|
||||
nightly_briefing_allowed:
|
||||
name: Nightly Briefing Allowed
|
||||
icon: mdi:bullhorn
|
||||
|
||||
intent_script:
|
||||
PlayAnnouncement:
|
||||
@@ -267,7 +283,6 @@ script:
|
||||
- light.living_room_color_1
|
||||
- light.living_room_color_2
|
||||
- light.living_room_color_3
|
||||
- light.tina_desk_strip
|
||||
- light.tina_lamp_side
|
||||
- light.tina_lamp_top
|
||||
- light.mud_room_overhead
|
||||
@@ -304,7 +319,6 @@ script:
|
||||
entity_id:
|
||||
- light.living_room_lights
|
||||
- light.tina_lamp
|
||||
- light.tina_desk_strip
|
||||
- light.basement_studio_lights
|
||||
data:
|
||||
color_name: >
|
||||
|
||||
4
packages/basement_studio.yaml
Normal file
4
packages/basement_studio.yaml
Normal file
@@ -0,0 +1,4 @@
|
||||
input_boolean:
|
||||
do_not_enter_basement_studio:
|
||||
name: Do Not Enter - Basement Studio
|
||||
icon: mdi:minus-circle
|
||||
@@ -217,6 +217,14 @@ input_boolean:
|
||||
name: Cold Day
|
||||
icon: mdi:snowflake
|
||||
|
||||
basement_studio_heat_allowed:
|
||||
name: Basement Studio Heat Allowed
|
||||
icon: mdi:heating-coil
|
||||
|
||||
emma_bedroom_heater_installed:
|
||||
name: Emma Bedroom Heater Installed
|
||||
icon: mdi:heating-coil
|
||||
|
||||
input_select:
|
||||
scheduled_climate_mode_master_bedroom_aircon:
|
||||
name: Scheduled Climate Mode - Master Bedroom Aircon
|
||||
@@ -231,22 +239,16 @@ input_select:
|
||||
- Fan
|
||||
- N/A
|
||||
icon: mdi:home-thermometer
|
||||
scheduled_climate_mode_emma_aircon:
|
||||
name: Scheduled Climate Mode - Emma Aircon
|
||||
scheduled_climate_mode_emma_bedroom:
|
||||
name: Scheduled Climate Mode - Emma Bedroom
|
||||
options:
|
||||
- AC
|
||||
- Heat
|
||||
- White Noise
|
||||
- N/A
|
||||
icon: mdi:home-thermometer
|
||||
naptime_climate_mode_emma_aircon:
|
||||
name: Naptime Climate Mode - Emma Aircon
|
||||
options:
|
||||
- AC
|
||||
- White Noise
|
||||
- N/A
|
||||
icon: mdi:home-thermometer
|
||||
scheduled_climate_mode_kallen_fan:
|
||||
name: Scheduled Climate Mode - Kallen Fan
|
||||
scheduled_climate_mode_kallen_bedroom:
|
||||
name: Scheduled Climate Mode - Kallen Bedroom
|
||||
options:
|
||||
- Fan
|
||||
- White Noise
|
||||
@@ -310,13 +312,6 @@ input_number:
|
||||
step: 1
|
||||
unit_of_measurement: °F
|
||||
icon: mdi:thermometer
|
||||
emma_naptime_aircon_threshold:
|
||||
name: Emma Naptime Aircon Threshold
|
||||
min: 40
|
||||
max: 80
|
||||
step: 1
|
||||
unit_of_measurement: °F
|
||||
icon: mdi:thermometer
|
||||
kallen_fan_threshold:
|
||||
name: Kallen Fan Threshold
|
||||
min: 40
|
||||
@@ -374,6 +369,38 @@ input_number:
|
||||
unit_of_measurement: °F
|
||||
icon: mdi:thermometer
|
||||
|
||||
climate:
|
||||
- platform: generic_thermostat
|
||||
unique_id: c2979677-045e-4393-a1cb-e6618978394f
|
||||
name: Basement Studio Thermostat
|
||||
heater: switch.basement_studio_heater
|
||||
target_sensor: sensor.basement_studio_temperature
|
||||
min_temp: 50
|
||||
max_temp: 80
|
||||
target_temp: 62
|
||||
ac_mode: false
|
||||
min_cycle_duration:
|
||||
minutes: 2
|
||||
cold_tolerance: 1
|
||||
hot_tolerance: 0
|
||||
initial_hvac_mode: "off"
|
||||
precision: 1.0
|
||||
- platform: generic_thermostat
|
||||
unique_id: 52cb7523-155a-4b26-808a-d6037b3ef7e4
|
||||
name: Emma Bedroom Thermostat
|
||||
heater: switch.emma_bedroom_heater
|
||||
target_sensor: sensor.emma_bedroom_temperature
|
||||
min_temp: 50
|
||||
max_temp: 80
|
||||
target_temp: 62
|
||||
ac_mode: false
|
||||
min_cycle_duration:
|
||||
minutes: 2
|
||||
cold_tolerance: 1
|
||||
hot_tolerance: 0
|
||||
initial_hvac_mode: "off"
|
||||
precision: 1.0
|
||||
|
||||
intent_script:
|
||||
MasterBedroomModes:
|
||||
action:
|
||||
|
||||
@@ -170,6 +170,87 @@ weather:
|
||||
{{ states(result) | float }}
|
||||
precipitation_unit: in
|
||||
|
||||
- platform: template
|
||||
name: "Ashland Weather Station"
|
||||
condition_template: >
|
||||
{% set stations = [
|
||||
states.weather.ashland,
|
||||
states.weather.kasx,
|
||||
states.weather.pirateweather_ashland
|
||||
] %}
|
||||
{% set result = stations | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) }}
|
||||
temperature_template: >
|
||||
{% set temps = [
|
||||
states.sensor.ashland_temperature,
|
||||
states.sensor.kasx_temperature,
|
||||
states.sensor.pirateweather_ashland_temperature
|
||||
] %}
|
||||
{% set sensor = temps | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(sensor) | float }}
|
||||
temperature_unit: °F
|
||||
humidity_template: >
|
||||
{% set humidity = [
|
||||
states.sensor.ashland_relative_humidity,
|
||||
states.sensor.kasx_relative_humidity,
|
||||
states.sensor.pirateweather_ashland_humidity
|
||||
] %}
|
||||
{% set result = humidity | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
forecast_daily_template: >
|
||||
{% set forecasts = [
|
||||
states.sensor.weather_com_ashland_daily_weather_forecast.attributes,
|
||||
states.weather.kasx.attributes,
|
||||
states.sensor.pirateweather_ashland_daily_weather_forecast.attributes
|
||||
] %}
|
||||
{{ forecasts | selectattr('forecast','defined') | map(attribute='forecast') | list | first }}
|
||||
forecast_hourly_template: >
|
||||
{% set forecasts = [
|
||||
states.sensor.weather_com_ashland_hourly_weather_forecast,
|
||||
states.sensor.pirateweather_ashland_hourly_weather_forecast.attributes
|
||||
] %}
|
||||
{{ forecasts | selectattr('forecast','defined') | map(attribute='forecast') | list | first }}
|
||||
pressure_template: >
|
||||
{% set pressures = [
|
||||
states.sensor.ashland_pressure,
|
||||
states.sensor.kasx_barometric_pressure
|
||||
] %}
|
||||
{% set result = pressures | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
pressure_unit: inHg
|
||||
wind_speed_template: >
|
||||
{% set windspeeds = [
|
||||
states.sensor.ashland_wind_speed,
|
||||
states.sensor.pirateweather_ashland_wind_speed,
|
||||
states.sensor.kasx_wind_speed
|
||||
] %}
|
||||
{% set result = windspeeds | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
wind_speed_unit: mph
|
||||
wind_bearing_template: >
|
||||
{% set windbearings = [
|
||||
states.sensor.ashland_wind_direction_degrees,
|
||||
states.sensor.pirateweather_ashland_wind_bearing
|
||||
] %}
|
||||
{% set result = windbearings | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
visibility_template: >
|
||||
{% set vis = [
|
||||
states.sensor.kasx_visibility,
|
||||
states.sensor.pirateweather_ashland_visibility
|
||||
] %}
|
||||
{% set result = vis | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
visibility_unit: mi
|
||||
attribution_template: "Daily weather data from Iron Nerd's custom weather station template"
|
||||
ozone_template: >
|
||||
{% set ozones = [
|
||||
states.sensor.pirateweather_ashland_ozone
|
||||
] %}
|
||||
{% set result = ozones | selectattr('state','ne','unavailable') | selectattr('state','ne','unknown') | map(attribute='entity_id') | list | first %}
|
||||
{{ states(result) | float }}
|
||||
precipitation_unit: in
|
||||
|
||||
# binary_sensor:
|
||||
# - platform: bayesian
|
||||
# unique_id: 3e9640d9-57a0-4495-8731-e64b34774065
|
||||
@@ -386,6 +467,119 @@ template:
|
||||
unique_id: 5bece9ad-2e1e-45a9-a690-93f8ff1d8780
|
||||
state: "{{ today.precipitation_probability }}"
|
||||
unit_of_measurement: "%"
|
||||
- trigger:
|
||||
- platform: time_pattern
|
||||
minutes: /15
|
||||
- platform: state
|
||||
entity_id: weather.pirateweather_ashland
|
||||
- platform: homeassistant
|
||||
event: start
|
||||
action:
|
||||
- service: weather.get_forecasts
|
||||
data:
|
||||
type: daily
|
||||
target:
|
||||
entity_id: weather.pirateweather_ashland
|
||||
response_variable: daily
|
||||
- variables:
|
||||
today: "{{ daily['weather.pirateweather_ashland'].forecast[0] }}"
|
||||
sensor:
|
||||
- name: Pirateweather Ashland Daily Weather Forecast
|
||||
unique_id: 9b103d9e-0fa3-4b47-b95d-c0caa4621895
|
||||
state: "{{ now().isoformat() }}"
|
||||
attributes:
|
||||
forecast: "{{ daily['weather.pirateweather_ashland'].forecast }}"
|
||||
- name: Pirateweather Ashland High
|
||||
unique_id: 21bf1e49-c3e3-4cec-8c89-add9e9efe9f3
|
||||
state: "{{ today.temperature }}"
|
||||
unit_of_measurement: °F
|
||||
- name: Pirateweather Ashland Low
|
||||
unique_id: fe06c076-807e-43a1-8413-c31ec389ec08
|
||||
state: "{{ today.templow }}"
|
||||
unit_of_measurement: °F
|
||||
- name: Pirateweather Ashland Rain Chance Today
|
||||
unique_id: 687b2246-ae49-47e0-95f3-f93dd159a43c
|
||||
state: "{{ today.precipitation_probability }}"
|
||||
unit_of_measurement: "%"
|
||||
- trigger:
|
||||
- platform: time_pattern
|
||||
minutes: /15
|
||||
- platform: state
|
||||
entity_id: weather.pirateweather_ashland
|
||||
- platform: homeassistant
|
||||
event: start
|
||||
action:
|
||||
- service: weather.get_forecasts
|
||||
data:
|
||||
type: hourly
|
||||
target:
|
||||
entity_id: weather.pirateweather_ashland
|
||||
response_variable: hourly
|
||||
sensor:
|
||||
- name: Pirateweather Ashland Hourly Weather Forecast
|
||||
unique_id: bcc4ca8c-aee7-4238-a78d-c35dae8c2c2b
|
||||
state: "{{ now().isoformat() }}"
|
||||
attributes:
|
||||
forecast: "{{ hourly['weather.pirateweather_ashland'].forecast }}"
|
||||
- trigger:
|
||||
- platform: time_pattern
|
||||
minutes: /15
|
||||
- platform: state
|
||||
entity_id: weather.ashland
|
||||
- platform: homeassistant
|
||||
event: start
|
||||
action:
|
||||
- service: weather.get_forecasts
|
||||
data:
|
||||
type: daily
|
||||
target:
|
||||
entity_id: weather.ashland
|
||||
response_variable: daily
|
||||
- variables:
|
||||
today: "{{ daily['weather.ashland'].forecast[0] }}"
|
||||
sensor:
|
||||
- name: Weather.com Ashland Daily Weather Forecast
|
||||
unique_id: f658e6ce-26a2-4c0d-9dc1-0bf26e95caf3
|
||||
state: "{{ now().isoformat() }}"
|
||||
attributes:
|
||||
forecast: "{{ daily['weather.ashland'].forecast }}"
|
||||
- name: Weather.com Ashland High
|
||||
unique_id: b5cf81b7-9a24-47c5-a5ee-9f3367251c83
|
||||
state: >
|
||||
{% if is_number(today.temperature) %}
|
||||
{{ today.temperature }}
|
||||
{% else %}
|
||||
{{ state_attr('weather.ashland','temperature') }}
|
||||
{% endif %}
|
||||
unit_of_measurement: °F
|
||||
- name: Weather.com Ashland Low
|
||||
unique_id: 196fb8a5-8ff5-47f1-ada5-dd1d3a69d596
|
||||
state: "{{ today.templow }}"
|
||||
unit_of_measurement: °F
|
||||
- name: Weather.com Ashland Rain Chance Today
|
||||
unique_id: 2e84209b-8d0a-425a-8c24-10ad8cf0c029
|
||||
state: "{{ today.precipitation_probability }}"
|
||||
unit_of_measurement: "%"
|
||||
- trigger:
|
||||
- platform: time_pattern
|
||||
minutes: /15
|
||||
- platform: state
|
||||
entity_id: weather.ashland
|
||||
- platform: homeassistant
|
||||
event: start
|
||||
action:
|
||||
- service: weather.get_forecasts
|
||||
data:
|
||||
type: hourly
|
||||
target:
|
||||
entity_id: weather.ashland
|
||||
response_variable: hourly
|
||||
sensor:
|
||||
- name: Weather.com Ashland Hourly Weather Forecast
|
||||
unique_id: 463cbe89-997c-49cc-a644-9e05ffd804ff
|
||||
state: "{{ now().isoformat() }}"
|
||||
attributes:
|
||||
forecast: "{{ hourly['weather.ashland'].forecast }}"
|
||||
- binary_sensor:
|
||||
- name: Heat Threshold
|
||||
unique_id: 849a08bb-d4e6-40e9-ae42-50f7fb71b727
|
||||
|
||||
@@ -4,9 +4,6 @@ input_boolean:
|
||||
emma_sleeping:
|
||||
name: Emma Sleeping
|
||||
icon: mdi:sleep
|
||||
emma_has_napped:
|
||||
name: Emma Has Napped
|
||||
icon: mdi:check
|
||||
emma_alternating_meds_active:
|
||||
name: Emma Alternating Meds Active
|
||||
icon: mdi:medication
|
||||
@@ -71,16 +68,6 @@ input_datetime:
|
||||
has_date: false
|
||||
has_time: true
|
||||
icon: mdi:weather-sunset-up
|
||||
emma_down_for_nap:
|
||||
name: Emma Down For Nap
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:sleep
|
||||
emma_up_from_nap:
|
||||
name: Emma Up From Nap
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:eye
|
||||
# These are for use in remembering which medications she has had when she is sick, and when to safely give them again
|
||||
emma_ibuprofen:
|
||||
name: Emma Ibuprofen
|
||||
@@ -145,31 +132,13 @@ automation:
|
||||
id: sleep-on
|
||||
sequence:
|
||||
- service: script.emma_sleep
|
||||
- if:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'off'
|
||||
- condition: time
|
||||
before: "23:00:00"
|
||||
after: "07:00:00"
|
||||
then:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_down_for_nap
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
else:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_asleep_at
|
||||
data:
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('time',24) }}
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_asleep_at
|
||||
data:
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('time',24) }}
|
||||
- delay:
|
||||
seconds: 1
|
||||
- service: script.text_notify
|
||||
@@ -186,28 +155,6 @@ automation:
|
||||
- condition: trigger
|
||||
id: sleep-off
|
||||
sequence:
|
||||
- if:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'off'
|
||||
- condition: time
|
||||
after: "18:00:00"
|
||||
before: "01:00:00"
|
||||
then:
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_up_from_nap
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
- delay:
|
||||
seconds: 1
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_scheduling_evening_ran
|
||||
@@ -260,41 +207,6 @@ automation:
|
||||
target:
|
||||
entity_id: input_boolean.emma_sleeping
|
||||
|
||||
- id: e44c2ab8-00cd-40ab-9b42-824511ac20aa
|
||||
alias: Emma Naptime Climate
|
||||
description: Sets the climate mode for when Emma goes down for nap
|
||||
mode: restart
|
||||
trigger:
|
||||
- platform: time_pattern
|
||||
minutes: "/5"
|
||||
- platform: state
|
||||
entity_id: input_number.emma_naptime_aircon_threshold
|
||||
- platform: state
|
||||
entity_id: input_boolean.hot_day
|
||||
condition:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_sleeping
|
||||
state: 'off'
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_bedroom_climate_override
|
||||
state: 'off'
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_bedroom_aircon_installed
|
||||
state: 'on'
|
||||
action:
|
||||
- service: input_select.select_option
|
||||
target:
|
||||
entity_id: input_select.naptime_climate_mode_emma_aircon
|
||||
data:
|
||||
option: >
|
||||
{% set temp = state_attr('weather.iron_nerd_weather_station','temperature') | int %}
|
||||
{% set threshold = states('input_number.emma_naptime_aircon_threshold') | int %}
|
||||
{% if (temp >= threshold) or is_state('input_boolean.hot_day','on') %}
|
||||
AC
|
||||
{% else %}
|
||||
White Noise
|
||||
{% endif %}
|
||||
|
||||
- id: 5b45eeb2-171e-4bac-825b-8ac7aa672dab
|
||||
alias: Emma Asleep Update
|
||||
description: Attempt to make readouts of when Emma went to bed more accurate
|
||||
@@ -310,11 +222,6 @@ automation:
|
||||
event_data:
|
||||
entity_id: timer.emma_bedtime_update
|
||||
id: bedtime-timer-finished
|
||||
- platform: event
|
||||
event_type: timer.finished
|
||||
event_data:
|
||||
entity_id: timer.emma_naptime_update
|
||||
id: naptime-timer-finished
|
||||
- platform: state
|
||||
entity_id: light.emma_bedroom_light
|
||||
to: 'off'
|
||||
@@ -325,37 +232,11 @@ automation:
|
||||
- condition: trigger
|
||||
id: initial
|
||||
sequence:
|
||||
- choose:
|
||||
- conditions:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'off'
|
||||
- condition: time
|
||||
before: "23:00:00"
|
||||
after: "07:00:00"
|
||||
sequence:
|
||||
- service: timer.start
|
||||
target:
|
||||
entity_id: timer.emma_naptime_update
|
||||
data:
|
||||
duration: "01:00:00"
|
||||
- conditions:
|
||||
- condition: or
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'on'
|
||||
- condition: time
|
||||
after: "23:00:00"
|
||||
before: "07:00:00"
|
||||
sequence:
|
||||
- service: timer.start
|
||||
target:
|
||||
entity_id: timer.emma_bedtime_update
|
||||
data:
|
||||
duration: "01:00:00"
|
||||
- service: timer.start
|
||||
target:
|
||||
entity_id: timer.emma_bedtime_update
|
||||
data:
|
||||
duration: "01:00:00"
|
||||
- conditions:
|
||||
- condition: trigger
|
||||
id: lights-off
|
||||
@@ -364,71 +245,18 @@ automation:
|
||||
target:
|
||||
entity_id:
|
||||
- timer.emma_bedtime_update
|
||||
- timer.emma_naptime_update
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_sleeping
|
||||
state: 'on'
|
||||
then:
|
||||
- choose:
|
||||
- conditions:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'off'
|
||||
- condition: time
|
||||
before: "23:00:00"
|
||||
after: "07:00:00"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_down_for_nap
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
- conditions:
|
||||
- condition: or
|
||||
conditions:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
state: 'on'
|
||||
- condition: time
|
||||
after: "23:00:00"
|
||||
before: "07:00:00"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_asleep_at
|
||||
data:
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('time',24) }}
|
||||
- conditions:
|
||||
- condition: trigger
|
||||
id: naptime-timer-finished
|
||||
sequence:
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: light.emma_bedroom_light
|
||||
state: 'on'
|
||||
then:
|
||||
- delay:
|
||||
seconds: 1
|
||||
- service: timer.start
|
||||
target:
|
||||
entity_id: timer.emma_naptime_update
|
||||
data:
|
||||
duration: "01:00:00"
|
||||
else:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_down_for_nap
|
||||
entity_id: input_datetime.emma_asleep_at
|
||||
data:
|
||||
datetime: >
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
{{ current_time('time',24) }}
|
||||
- conditions:
|
||||
- condition: trigger
|
||||
id: bedtime-timer-finished
|
||||
@@ -986,17 +814,13 @@ script:
|
||||
who: basement
|
||||
type: normal
|
||||
message: Emma has awoken, so it is time to make your way upstairs now
|
||||
- if:
|
||||
- condition: template
|
||||
value_template: "{{ is_state('binary_sensor.morning','on') or is_state('binary_sensor.midday','on') }}"
|
||||
then:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_awake_at
|
||||
data:
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('time',24) }}
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.emma_awake_at
|
||||
data:
|
||||
time: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('time',24) }}
|
||||
- service: switch.turn_off
|
||||
target:
|
||||
entity_id:
|
||||
|
||||
@@ -1,101 +1,3 @@
|
||||
scrape:
|
||||
- resource: https://www.gasbuddy.com/station/59010
|
||||
sensor:
|
||||
- name: South Side Shell
|
||||
unique_id: b3385058-173c-4446-9f0f-3a45f21715d8
|
||||
select: &selector "#root > div > div.Page-module__content___196kn.Page-module__padded___3hQ0U > div > div > div:nth-child(2) > div.grid__column___nhz7X.grid__desktop10___2T18R > div:nth-child(1) > div.grid__column___nhz7X.grid__desktop8___38Y4U > div:nth-child(3) > div > div.GasPriceCollection-module__collectionContainer___29Ngz > div:nth-child(2) > div:nth-child(1) > span"
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59007
|
||||
sensor:
|
||||
- name: Circle K
|
||||
unique_id: 63d947bc-486a-478e-9fbe-7fb2f38a1e1e
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/123478
|
||||
sensor:
|
||||
- name: Kroger
|
||||
unique_id: b705d912-8ef4-4e55-9168-d7e152773ba0
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59014
|
||||
sensor:
|
||||
- name: Kecks
|
||||
unique_id: 4fa4a7bb-45b1-4d17-ab92-06ebd6a39ebb
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59006
|
||||
sensor:
|
||||
- name: The Barn
|
||||
unique_id: 51137245-9c4a-4992-aa7c-19cd38bd614d
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59016
|
||||
sensor:
|
||||
- name: The Big Fish
|
||||
unique_id: d5e057d5-3f7b-4c6b-ad0c-5e6ffa10b861
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/107803
|
||||
sensor:
|
||||
- name: Marathon Cleveland Avenue
|
||||
unique_id: 3ef9c1d0-46b0-4850-8df2-d478c833aa4d
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59013
|
||||
sensor:
|
||||
- name: Speedway
|
||||
unique_id: 44484541-1a71-4e36-9e81-486eea3882cc
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59009
|
||||
sensor:
|
||||
- name: Meijer
|
||||
unique_id: dc687fd2-ed4d-4fae-a2b8-38ae7a944a68
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59012
|
||||
sensor:
|
||||
- name: East Side Shell
|
||||
unique_id: db36f6b4-6f87-48af-a339-1f8e8bbc95e3
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/59011
|
||||
sensor:
|
||||
- name: Shell Ottawa Avenue
|
||||
unique_id: d9508ad6-4298-4262-bac9-931a3bc510df
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
- resource: https://www.gasbuddy.com/station/71535
|
||||
sensor:
|
||||
- name: Ridis
|
||||
unique_id: 9db2cbc3-39ea-4471-9541-64aa7aa8de71
|
||||
select: *selector
|
||||
device_class: monetary
|
||||
value_template: '{{ value | replace("$", "") | float }}'
|
||||
icon: mdi:gas-station
|
||||
|
||||
sensor:
|
||||
- platform: statistics
|
||||
unique_id: fcf4e80e-8459-4e23-a94f-5f127b628c20
|
||||
|
||||
@@ -16,9 +16,15 @@ input_boolean:
|
||||
kallen_late_bedtime:
|
||||
name: Kallen Late Bedtime
|
||||
icon: mdi:weather-night
|
||||
kallen_morning_meds_reminder:
|
||||
name: Kallen Morning Meds Reminder
|
||||
icon: mdi:medication
|
||||
kallen_morning_meds_taken:
|
||||
name: Kallen Morning Meds Taken
|
||||
icon: mdi:medication
|
||||
kallen_night_meds_reminder:
|
||||
name: Kallen Night Meds Reminder
|
||||
icon: mdi:medication
|
||||
kallen_night_meds_taken:
|
||||
name: Kallen Night Meds Taken
|
||||
icon: mdi:medication
|
||||
@@ -67,12 +73,12 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
kallen_morning_meds_notify:
|
||||
name: Kallen Morning Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
kallen_night_meds_notify:
|
||||
name: Kallen Night Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
kallen_alarm_clock:
|
||||
|
||||
@@ -32,9 +32,6 @@ input_boolean:
|
||||
give_me_darkness:
|
||||
name: Give Me Darkness
|
||||
icon: mdi:weather-night
|
||||
tina_desk_lights:
|
||||
name: Tina Desk Lights
|
||||
icon: mdi:desk
|
||||
holiday_mode_hold:
|
||||
name: Holiday Mode Hold
|
||||
icon: mdi:party-popper
|
||||
@@ -819,7 +816,6 @@ switch:
|
||||
- light.living_room_color_3
|
||||
- light.tina_lamp_top
|
||||
- light.tina_lamp_side
|
||||
- light.tina_desk_strip
|
||||
colors:
|
||||
- color_type: rgb_color
|
||||
color: [255,0,0]
|
||||
|
||||
@@ -301,10 +301,6 @@ notify:
|
||||
services:
|
||||
- service: alexa_media_living_room_echo_dot
|
||||
- service: alexa_media_basement_echo_dot
|
||||
- platform: html5
|
||||
vapid_pub_key: !secret vapid_pub_key
|
||||
vapid_prv_key: !secret vapid_prv_key
|
||||
vapid_email: tm24fan8@gmail.com
|
||||
|
||||
script:
|
||||
volume_reset:
|
||||
@@ -1786,6 +1782,15 @@ script:
|
||||
] | random }}
|
||||
{%- endmacro -%}
|
||||
|
||||
{%- macro snark_shower_mode_window() -%}
|
||||
{{ [
|
||||
'Now that you have finished showering, you may want to consider shutting the upstairs bathroom window.',
|
||||
'As there is no screen in the upstairs bathroom window, you should shut it to prevent bugs and other unwanted creatures from getting into the house.',
|
||||
'Hey, you left the upstairs bathroom window open after your shower. Do something about that ASAP.',
|
||||
'The second floor already has enough trouble maintaining temperature, please close the upstairs bathroom window after your shower.'
|
||||
] | random }}
|
||||
{%- endmacro -%}
|
||||
|
||||
{%- macro school_pickup_reminder() -%}
|
||||
{{ [
|
||||
'It is almost time to head to school ',
|
||||
@@ -1943,7 +1948,11 @@ script:
|
||||
{% endif %}
|
||||
|
||||
{% if call_snark_door_closed == 1 %}
|
||||
{{ snark_door_closed () }}
|
||||
{{ snark_door_closed() }}
|
||||
{% endif %}
|
||||
|
||||
{% if call_snark_shower_mode_window == 1 %}
|
||||
{{ snark_shower_mode_window() }}
|
||||
{% endif %}
|
||||
|
||||
{% if call_school_pickup_reminder == 1 %}
|
||||
|
||||
@@ -89,7 +89,7 @@ template:
|
||||
- binary_sensor:
|
||||
- name: People Present
|
||||
state: >
|
||||
{{ is_state('person.tony_stork', 'home') or is_state('person.christina_stork', 'home') }}
|
||||
{{ is_state('person.tony_stork', 'home') or is_state('person.christina_stork', 'home') or is_state('person.kallen_stork', 'home') or is_state('input_boolean.guest_mode', 'on') }}
|
||||
- name: "Tony Home"
|
||||
unique_id: 4f0d8c3d-dc49-4b7a-a1fc-5d286b4a954d
|
||||
state: "{{ is_state('device_tracker.tony_s_iphone', 'home') }}" # Add new tracker when we have one
|
||||
@@ -124,6 +124,8 @@ template:
|
||||
state: >
|
||||
{% if is_state('binary_sensor.basement_studio_motion','on') %}
|
||||
true
|
||||
{% elif is_state('sensor.xia_desktop_current_username','tm24f') %}
|
||||
false
|
||||
{% elif is_state('binary_sensor.tony_desktop_on','off') and
|
||||
is_state('binary_sensor.kallen_desktop_on','off') %}
|
||||
false
|
||||
@@ -405,7 +407,6 @@ automation:
|
||||
# - light.living_room_led_strip
|
||||
# - light.tina_lamp_top
|
||||
# - light.tina_lamp_side
|
||||
# - light.tina_desk_strip
|
||||
# - alias: "Save Current Adaptive State"
|
||||
# service: scene.create
|
||||
# data:
|
||||
@@ -425,7 +426,6 @@ automation:
|
||||
# entity_id:
|
||||
# - light.living_room_lights
|
||||
# - light.tina_lamp
|
||||
# - light.tina_desk_strip
|
||||
# - light.living_room_led_strip
|
||||
# data:
|
||||
# color_name: green
|
||||
@@ -865,9 +865,7 @@ script:
|
||||
- front_porch
|
||||
- living_room
|
||||
- mud_room
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.tina_desk_lights
|
||||
- tina_desk
|
||||
- delay:
|
||||
hours: 0
|
||||
minutes: 0
|
||||
@@ -925,9 +923,7 @@ script:
|
||||
area_id:
|
||||
- living_room
|
||||
- mud_room
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.tina_desk_lights
|
||||
- tina_desk
|
||||
- delay:
|
||||
hours: 0
|
||||
minutes: 0
|
||||
|
||||
@@ -164,7 +164,7 @@ script:
|
||||
time: >
|
||||
{% from 'time.jinja' import time_from_calendar %}
|
||||
{% if is_state('input_boolean.two_hour_delay','on') %}
|
||||
10:00
|
||||
{{ time_from_calendar('calendar.kallen_school_days','start_time','set','add',2)}}
|
||||
{% else %}
|
||||
{{ time_from_calendar('calendar.kallen_school_days','start_time','set') }}
|
||||
{% endif %}
|
||||
@@ -247,11 +247,14 @@ script:
|
||||
target:
|
||||
entity_id: input_datetime.kallen_morning_meds_notify
|
||||
data:
|
||||
time: >
|
||||
datetime: >
|
||||
{% set date = now().strftime('%Y-%m-%d') %}
|
||||
{% set wakeup = state_attr('input_datetime.kallen_wakeup_time','timestamp') | int %}
|
||||
{% set wakeup_mod = (wakeup + 600) | timestamp_custom('%T',false) %}
|
||||
{% if is_state('input_boolean.kallen_school_today','on') %}
|
||||
{{ (state_attr('input_datetime.kallen_wakeup_time','timestamp') + 600) | timestamp_custom('%H:%M', false) }}
|
||||
{{ date + ' ' + wakeup_mod }}
|
||||
{% else %}
|
||||
{{ states('input_datetime.kallen_wakeup_time') }}
|
||||
{{ date + ' ' + states('input_datetime.kallen_wakeup_time') }}
|
||||
{% endif %}
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
@@ -271,16 +274,16 @@ script:
|
||||
time: >
|
||||
{% if is_state('input_boolean.school_in_session','on') %}
|
||||
{% if is_state('binary_sensor.kallen_school_tomorrow', 'on') %}
|
||||
21:00
|
||||
{% else %}
|
||||
22:00
|
||||
{% endif %}
|
||||
{% else %}
|
||||
{% if is_state('binary_sensor.kallen_btb_tomorrow','on') %}
|
||||
22:00
|
||||
{% else %}
|
||||
23:00
|
||||
{% endif %}
|
||||
{% else %}
|
||||
{% if is_state('binary_sensor.kallen_btb_tomorrow','on') %}
|
||||
23:00
|
||||
{% else %}
|
||||
00:00
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
- delay:
|
||||
seconds: 1
|
||||
@@ -300,7 +303,7 @@ script:
|
||||
then:
|
||||
- service: input_select.select_option
|
||||
target:
|
||||
entity_id: input_select.scheduled_climate_mode_kallen_fan
|
||||
entity_id: input_select.scheduled_climate_mode_kallen_bedroom
|
||||
data:
|
||||
option: >
|
||||
{% if is_state('input_boolean.kallen_overnight','on') %}
|
||||
@@ -324,7 +327,15 @@ script:
|
||||
target:
|
||||
entity_id: input_datetime.kallen_night_meds_notify
|
||||
data:
|
||||
time: "{{ (state_attr('input_datetime.kallen_bedtime','timestamp') - 600) | timestamp_custom('%H:%M', false) }}"
|
||||
datetime: >
|
||||
{% set bedtime = state_attr('input_datetime.kallen_bedtime','timestamp') | int %}
|
||||
{% set bedtime_mod = (bedtime - 600) | timestamp_custom('%T',false) %}
|
||||
{% if bedtime < 13800 %}
|
||||
{% set date = (as_timestamp(now()) + 86400) | timestamp_custom("%Y-%m-%d", True) %}
|
||||
{% else %}
|
||||
{% set date = now().strftime('%Y-%m-%d') %}
|
||||
{% endif %}
|
||||
{{ date + ' ' + bedtime_mod }}
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: input_boolean.kallen_late_bedtime
|
||||
@@ -354,7 +365,7 @@ script:
|
||||
target:
|
||||
entity_id: input_datetime.kallen_night_meds_notify
|
||||
data:
|
||||
time: "{{ (state_attr('input_datetime.kallen_night_meds_notify','timestamp') + 3600) | timestamp_custom('%H:%M', false) }}"
|
||||
datetime: "{{ (state_attr('input_datetime.kallen_night_meds_notify','timestamp') + 3600) | timestamp_custom('%Y-%m-%d %H:%M:%S') }}"
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.kallen_scheduling_evening_ran
|
||||
@@ -383,11 +394,7 @@ script:
|
||||
{% set kallenbriefing = state_attr('input_datetime.kallen_morning_briefing','timestamp') %}
|
||||
{% set kallenloc = states('input_select.kallen_morning_briefing_location') %}
|
||||
{% if is_state('input_boolean.kallen_school_today','on') %}
|
||||
{% if is_state('input_boolean.two_hour_delay','on') %}
|
||||
9:20
|
||||
{% else %}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 2400) | timestamp_custom('%H:%M', false) }}
|
||||
{% endif %}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 3600) | timestamp_custom('%H:%M', false) }}
|
||||
{% elif is_state('input_boolean.work_today','on') and is_state('input_boolean.kallen_school_today','off') %}
|
||||
{% if (state_attr('input_datetime.tina_workday_start','timestamp')) > 43200 %}
|
||||
{% if kallenloc == 'Common Areas' and kallenbriefing == 43200 %}
|
||||
@@ -586,11 +593,13 @@ script:
|
||||
target:
|
||||
entity_id: input_datetime.tina_morning_meds_notify
|
||||
data:
|
||||
time: >
|
||||
datetime: >
|
||||
{% from 'time.jinja' import datetime_from_calendar %}
|
||||
{% set date = now().strftime('%Y-%m-%d') %}
|
||||
{% if is_state('input_boolean.work_today','on') %}
|
||||
{{ (state_attr('input_datetime.tina_workday_start','timestamp') | int - 1800) | timestamp_custom('%H:%M', false) }}
|
||||
{{ datetime_from_calendar('calendar.family_tinawork','start_time','set','subtract',0,0,30) }}
|
||||
{% else %}
|
||||
{{ states('input_datetime.master_bedroom_wakeup') }}
|
||||
{{ date + ' ' + states('input_datetime.master_bedroom_wakeup') }}
|
||||
{% endif %}
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
@@ -676,7 +685,7 @@ script:
|
||||
target:
|
||||
entity_id: input_datetime.tina_night_meds_notify
|
||||
data:
|
||||
time: '03:00'
|
||||
datetime: "{{ (as_timestamp(now()) + 86400) | timestamp_custom('%Y-%m-%d', True) + ' 03:00:00' }}"
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.master_bedroom_scheduling_evening_ran
|
||||
@@ -684,9 +693,6 @@ script:
|
||||
emma_bedroom_scheduling_morning:
|
||||
alias: 'Emma Bedroom Scheduling Morning'
|
||||
sequence:
|
||||
- service: input_boolean.turn_off
|
||||
target:
|
||||
entity_id: input_boolean.emma_has_napped
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_wakeup_override
|
||||
@@ -696,11 +702,6 @@ script:
|
||||
entity_id: input_datetime.emma_wakeup
|
||||
data:
|
||||
time: "{{ states('input_datetime.master_bedroom_wakeup') }}"
|
||||
- service: input_select.select_option
|
||||
target:
|
||||
entity_id: input_select.naptime_climate_mode_emma_aircon
|
||||
data:
|
||||
option: "{{ states('input_select.scheduled_climate_mode_emma_aircon') }}"
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.emma_scheduling_morning_ran
|
||||
@@ -718,15 +719,9 @@ script:
|
||||
data:
|
||||
time: >
|
||||
{% set awake = state_attr('input_datetime.emma_awake_at','timestamp') | int %}
|
||||
{% set up_from_nap = state_attr('input_datetime.emma_up_from_nap','timestamp') | int %}
|
||||
{% set hours = states('input_number.emma_bedtime_hours') | int %}
|
||||
{% set math = (hours * 60) * 60 %}
|
||||
{% set math_nap = 14400 %}
|
||||
{% if is_state('input_boolean.emma_has_napped','on') %}
|
||||
{{ (up_from_nap + math_nap) | timestamp_custom('%H:%M') }}
|
||||
{% else %}
|
||||
{{ (awake + math) | timestamp_custom('%H:%M',false) }}
|
||||
{% endif %}
|
||||
{{ (awake + math) | timestamp_custom('%H:%M',false) }}
|
||||
- if:
|
||||
- condition: state
|
||||
entity_id: input_boolean.emma_bedroom_climate_override
|
||||
@@ -734,7 +729,7 @@ script:
|
||||
then:
|
||||
- service: input_select.select_option
|
||||
target:
|
||||
entity_id: input_select.scheduled_climate_mode_emma_aircon
|
||||
entity_id: input_select.scheduled_climate_mode_emma_bedroom
|
||||
data:
|
||||
option: >
|
||||
{% if is_state('input_boolean.emma_bedroom_aircon_installed','on') %}
|
||||
@@ -778,16 +773,16 @@ script:
|
||||
{% if ct > state_attr('input_datetime.kallen_school_day_start','timestamp') %}
|
||||
{{ (state_attr('input_datetime.tina_workday_start','timestamp') - 1800) | timestamp_custom('%H:%M', false) }}
|
||||
{% elif ct > state_attr('input_datetime.tina_workday_start','timestamp') and ct < state_attr('input_datetime.kallen_school_day_start','timestamp') %}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 2700) | timestamp_custom('%H:%M', false) }}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 3900) | timestamp_custom('%H:%M', false) }}
|
||||
{% elif state_attr('input_datetime.tina_workday_start','timestamp') < (state_attr('input_datetime.kallen_school_day_start','timestamp')) %}
|
||||
{{ (state_attr('input_datetime.tina_workday_start','timestamp') - 1800) | timestamp_custom('%H:%M', false) }}
|
||||
{% else %}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 2700) | timestamp_custom('%H:%M', false) }}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 3900) | timestamp_custom('%H:%M', false) }}
|
||||
{% endif %}
|
||||
{% elif is_state('input_boolean.work_today','on') and is_state('input_boolean.kallen_school_today','off') %}
|
||||
{{ (state_attr('input_datetime.tina_workday_start', 'timestamp') - 1800) | timestamp_custom('%H:%M', false) }}
|
||||
{% elif is_state('input_boolean.kallen_school_today','on') %}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 2700) | timestamp_custom('%H:%M', false) }}
|
||||
{{ (state_attr('input_datetime.kallen_school_day_start','timestamp') - 3900) | timestamp_custom('%H:%M', false) }}
|
||||
{% else %}
|
||||
11:00
|
||||
{% endif %}
|
||||
|
||||
@@ -288,6 +288,17 @@ automation:
|
||||
target:
|
||||
entity_id: input_boolean.school_today_ran
|
||||
|
||||
- id: 59ae3bfe-5c58-4ff4-aaf5-7b76fd0ac442
|
||||
alias: Start of School Year
|
||||
initial_state: true
|
||||
trigger:
|
||||
- platform: template
|
||||
value_template: "{{ states('sensor.school_start_days2go') | int == 1 }}"
|
||||
action:
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.school_in_session
|
||||
|
||||
- id: 05ee0f8d-5411-4486-8acf-9bfadad2b23a
|
||||
alias: End of School Year
|
||||
initial_state: true
|
||||
|
||||
@@ -3,6 +3,53 @@ input_boolean:
|
||||
name: Sports Updates
|
||||
icon: mdi:strategy
|
||||
|
||||
input_datetime:
|
||||
michigan_wolverines_start:
|
||||
name: Michigan Wolverines Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:football
|
||||
ohio_state_buckeyes_start:
|
||||
name: Ohio State Buckeyes Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:football
|
||||
toledo_rockets_start:
|
||||
name: Toledo Rockets Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:football
|
||||
minnesota_vikings_start:
|
||||
name: Minnesota Vikings Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:football
|
||||
san_francisco_49ers_start:
|
||||
name: San Francisco 49ers Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:football
|
||||
minnesota_twins_start:
|
||||
name: Minnesota Twins Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:baseball
|
||||
cleveland_guardians_start:
|
||||
name: Cleveland Guardians Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:baseball
|
||||
los_angeles_dodgers_start:
|
||||
name: Los Angeles Dodgers Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:baseball
|
||||
minnesota_wild_start:
|
||||
name: Minnesota Wild Start
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:hockey-puck
|
||||
|
||||
template:
|
||||
- binary_sensor:
|
||||
- name: Michigan Wolverines Inhibit
|
||||
@@ -55,16 +102,6 @@ template:
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_today %}
|
||||
{{ sports_today('sensor.san_francisco_49ers') }}
|
||||
- name: Cleveland Guardians Inhibit
|
||||
unique_id: b0980d47-d762-4f23-97b1-9e88da729d8f
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_inhibit %}
|
||||
{{ sports_inhibit('sensor.cleveland_guardians') }}
|
||||
- name: Cleveland Guardians Event Today
|
||||
unique_id: 985a7b2c-9ebd-4a2e-8ee2-2ab5359310e0
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_today %}
|
||||
{{ sports_today('sensor.cleveland_guardians') }}
|
||||
- name: Minnesota Twins Inhibit
|
||||
unique_id: 2987ae95-f55d-4994-b9dd-018278d2f5ad
|
||||
state: >
|
||||
@@ -75,6 +112,16 @@ template:
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_today %}
|
||||
{{ sports_today('sensor.minnesota_twins') }}
|
||||
- name: Cleveland Guardians Inhibit
|
||||
unique_id: b0980d47-d762-4f23-97b1-9e88da729d8f
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_inhibit %}
|
||||
{{ sports_inhibit('sensor.cleveland_guardians') }}
|
||||
- name: Cleveland Guardians Event Today
|
||||
unique_id: 985a7b2c-9ebd-4a2e-8ee2-2ab5359310e0
|
||||
state: >
|
||||
{% from 'sports.jinja' import sports_today %}
|
||||
{{ sports_today('sensor.cleveland_guardians') }}
|
||||
- name: Los Angeles Dodgers Inhibit
|
||||
unique_id: 2c6aae6e-eff6-46e5-bee9-311f9bbc0c0e
|
||||
state: >
|
||||
|
||||
@@ -88,23 +88,15 @@ template:
|
||||
- name: Tony Desktop Idle
|
||||
unique_id: f0ace986-a874-4fb0-ad29-8f3ebf95d8cc
|
||||
state: "{{ (states('sensor.tony_asus_system_idle_time') | int) > (states('input_number.basement_computers_idle_time') | int * 60) }}"
|
||||
attributes:
|
||||
idle_time: "{{ states('sensor.tony_asus_system_idle_time') | int }}s"
|
||||
- name: Tina Desktop Idle
|
||||
unique_id: 1933c638-c94b-468e-bb7a-c1c5b36c3651
|
||||
state: "{{ (states('sensor.xia_desktop_system_idle_time') | int) > (states('input_number.first_floor_computers_idle_time') | int * 60) }}"
|
||||
attributes:
|
||||
idle_time: "{{ states('sensor.xia_desktop_system_idle_time') | int }}s"
|
||||
- name: Kallen Desktop Idle
|
||||
unique_id: 680c6ae3-2ed2-451e-858b-2aee688af461
|
||||
state: "{{ (states('sensor.kallen_desktop_system_idle_time') | int) > (states('input_number.basement_computers_idle_time') | int * 60) }}"
|
||||
attributes:
|
||||
idle_time: "{{ states('sensor.kallen_desktop_system_idle_time') | int }}s"
|
||||
- name: Asus Laptop Idle
|
||||
unique_id: 7d8eb80a-0a2e-48a9-84b3-33175304dd95
|
||||
state: "{{ states('sensor.asus_laptop_system_idle_time') | int > 1800 }}"
|
||||
attributes:
|
||||
idle_time: "{{ states('sensor.asus_laptop_system_idle_time') }}s"
|
||||
- sensor:
|
||||
- name: "Min Ping"
|
||||
unique_id: ddcb9f6f-7c94-41fe-9453-2a2205b078e0
|
||||
|
||||
@@ -7,12 +7,30 @@ input_boolean:
|
||||
work_today_extended:
|
||||
name: Work Today Extended
|
||||
icon: mdi:briefcase-plus
|
||||
tina_morning_meds_reminder:
|
||||
name: Tina Morning Meds Reminder
|
||||
icon: mdi:medication
|
||||
tina_morning_meds_taken:
|
||||
name: Tina Morning Meds Taken
|
||||
icon: mdi:medication
|
||||
tina_night_meds_reminder:
|
||||
name: Tina Night Meds Reminder
|
||||
icon: mdi:medication
|
||||
tina_night_meds_taken:
|
||||
name: Tina Night Meds Taken
|
||||
icon: mdi:medication
|
||||
tina_ibuprofen_active:
|
||||
name: Tina Ibuprofen Active
|
||||
icon: mdi:medication
|
||||
tina_ibuprofen_taken:
|
||||
name: Tina Ibuprofen Taken
|
||||
icon: mdi:medication
|
||||
tina_tylenol_active:
|
||||
name: Tina Tylenol Active
|
||||
icon: mdi:medication
|
||||
tina_tylenol_taken:
|
||||
name: Tina Tylenol Taken
|
||||
icon: mdi:medication
|
||||
tina_awake:
|
||||
name: Tina Awake
|
||||
icon: mdi:eye-check
|
||||
@@ -35,7 +53,7 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tina_morning_meds_notify:
|
||||
name: Tina Morning Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tina_night_meds_taken:
|
||||
@@ -45,7 +63,27 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tina_night_meds_notify:
|
||||
name: Tina Night Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tina_ibuprofen_taken:
|
||||
name: Tina Ibuprofen Taken
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tina_ibuprofen_notify:
|
||||
name: Tina Ibuprofen Notify
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tina_tylenol_taken:
|
||||
name: Tina Tylenol Taken
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tina_tylenol_notify:
|
||||
name: Tina Tylenol Notify
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
|
||||
@@ -103,78 +141,6 @@ automation:
|
||||
data:
|
||||
reason: "{{ reason }}"
|
||||
|
||||
- id: 513e33b8-a236-474b-a9cc-e40af36a052d
|
||||
alias: Tina Meds Handler
|
||||
description: Make sure Tina has taken her meds in the morning and at night
|
||||
mode: parallel
|
||||
max: 4
|
||||
trigger:
|
||||
- platform: time
|
||||
at: input_datetime.tina_morning_meds_notify
|
||||
id: wakeup
|
||||
- platform: state
|
||||
entity_id: input_boolean.tina_morning_meds_taken
|
||||
to: 'on'
|
||||
id: boolean-morning
|
||||
- platform: time
|
||||
at: input_datetime.tina_night_meds_notify
|
||||
id: sleep
|
||||
- platform: state
|
||||
entity_id: input_boolean.tina_night_meds_taken
|
||||
to: 'on'
|
||||
id: boolean-night
|
||||
action:
|
||||
- choose:
|
||||
- conditions:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: trigger
|
||||
id: wakeup
|
||||
- condition: state
|
||||
entity_id: input_boolean.tina_morning_meds_taken
|
||||
state: 'off'
|
||||
sequence:
|
||||
- service: script.turn_on
|
||||
target:
|
||||
entity_id: script.tina_morning_meds
|
||||
- conditions:
|
||||
- condition: trigger
|
||||
id: boolean-morning
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_morning_meds_taken
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
- conditions:
|
||||
- condition: and
|
||||
conditions:
|
||||
- condition: trigger
|
||||
id: sleep
|
||||
- condition: state
|
||||
entity_id: input_boolean.tina_night_meds_taken
|
||||
state: 'off'
|
||||
- condition: state
|
||||
entity_id: input_boolean.master_bedroom_sleeping
|
||||
state: 'off'
|
||||
sequence:
|
||||
- service: script.turn_on
|
||||
target:
|
||||
entity_id: script.tina_night_meds
|
||||
- conditions:
|
||||
- condition: trigger
|
||||
id: boolean-night
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_night_meds_taken
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import current_time %}
|
||||
{{ current_time('datetime',24) }}
|
||||
|
||||
script:
|
||||
tina_work_today:
|
||||
alias: 'Tina Work Today'
|
||||
@@ -263,165 +229,3 @@ script:
|
||||
- service: script.master_bedroom_scheduling_evening
|
||||
- service: script.emma_bedroom_scheduling_evening
|
||||
- service: script.security_scheduling
|
||||
|
||||
tina_morning_meds:
|
||||
alias: 'Tina Morning Meds'
|
||||
icon: mdi:medication
|
||||
mode: restart
|
||||
sequence:
|
||||
- service: script.text_notify
|
||||
data:
|
||||
who: tina
|
||||
type: alert
|
||||
title: Morning Meds
|
||||
message: You need to take your morning meds
|
||||
tag: tina-morning-meds
|
||||
actions:
|
||||
- action: "TINA_MORNING_MEDS_TAKEN"
|
||||
title: Taken
|
||||
- action: "TINA_MORNING_MEDS_SKIPPED"
|
||||
title: Skip
|
||||
- action: "TINA_MORNING_MEDS_ASK_LATER"
|
||||
title: Ask Later
|
||||
- wait_for_trigger:
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_MORNING_MEDS_TAKEN"
|
||||
id: taken
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_MORNING_MEDS_SKIPPED"
|
||||
id: skipped
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_MORNING_MEDS_ASK_LATER"
|
||||
id: ask-later
|
||||
- platform: state
|
||||
entity_id: person.christina_stork
|
||||
from: 'home'
|
||||
id: left
|
||||
- platform: state
|
||||
entity_id: input_boolean.tina_morning_meds_taken
|
||||
to: 'on'
|
||||
id: manual
|
||||
timeout: "00:30:00"
|
||||
continue_on_timeout: true
|
||||
- choose:
|
||||
- conditions: "{{ wait.trigger.id in ['taken','manual'] }}"
|
||||
sequence:
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.tina_morning_meds_taken
|
||||
- conditions: "{{ wait.trigger.id == 'ask-later' }}"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_morning_meds_notify
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import set_datetime %}
|
||||
{{ set_datetime(0,30) }}
|
||||
- conditions: "{{ wait.trigger.id == 'left' }}"
|
||||
sequence:
|
||||
- service: script.text_notify
|
||||
data:
|
||||
who: tina
|
||||
type: alert
|
||||
title: HEY DUMBASS
|
||||
message: YOU FORGOT TO TAKE YOUR MORNING MEDS!!!!!
|
||||
- conditions: "{{ wait.trigger == 'none' or wait.trigger.idx is undefined }}"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_morning_meds_notify
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import set_datetime %}
|
||||
{{ set_datetime(0,1) }}
|
||||
- service: script.text_notify
|
||||
data:
|
||||
type: alert
|
||||
who: tina
|
||||
message: clear_notification
|
||||
tag: tina-morning-meds
|
||||
|
||||
tina_night_meds:
|
||||
alias: 'Tina Night Meds'
|
||||
icon: mdi:medication
|
||||
mode: restart
|
||||
sequence:
|
||||
- service: script.text_notify
|
||||
data:
|
||||
who: tina
|
||||
type: alert
|
||||
title: Night Meds
|
||||
message: You need to take your night meds
|
||||
tag: tina-night-meds
|
||||
actions:
|
||||
- action: "TINA_NIGHT_MEDS_TAKEN"
|
||||
title: Taken
|
||||
- action: "TINA_NIGHT_MEDS_SKIPPED"
|
||||
title: Skip
|
||||
- action: "TINA_NIGHT_MEDS_ASK_LATER"
|
||||
title: Ask Later
|
||||
- wait_for_trigger:
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_NIGHT_MEDS_TAKEN"
|
||||
id: taken
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_NIGHT_MEDS_SKIPPED"
|
||||
id: skipped
|
||||
- platform: event
|
||||
event_type: ios.notification_action_fired
|
||||
event_data:
|
||||
actionName: "TINA_NIGHT_MEDS_ASK_LATER"
|
||||
id: ask-later
|
||||
- platform: state
|
||||
entity_id: input_boolean.tina_night_meds_taken
|
||||
to: 'on'
|
||||
id: manual
|
||||
- platform: state
|
||||
entity_id:
|
||||
- input_boolean.master_bedroom_sleeping
|
||||
- input_boolean.goodnight
|
||||
to: 'on'
|
||||
id: sleeping
|
||||
timeout: "00:30:00"
|
||||
continue_on_timeout: true
|
||||
- choose:
|
||||
- conditions: "{{ wait.trigger.id in ['taken','manual'] }}"
|
||||
sequence:
|
||||
- service: input_boolean.turn_on
|
||||
target:
|
||||
entity_id: input_boolean.tina_night_meds_taken
|
||||
- conditions: "{{ wait.trigger.id == 'ask-later' }}"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_night_meds_notify
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import set_datetime %}
|
||||
{{ set_datetime(0,30) }}
|
||||
- conditions: "{{ wait.trigger == 'none' or wait.trigger.idx is undefined }}"
|
||||
sequence:
|
||||
- service: input_datetime.set_datetime
|
||||
target:
|
||||
entity_id: input_datetime.tina_night_meds_notify
|
||||
data:
|
||||
datetime: >
|
||||
{% from 'time.jinja' import set_datetime %}
|
||||
{{ set_datetime(0,1) }}
|
||||
- service: script.text_notify
|
||||
data:
|
||||
type: alert
|
||||
who: tina
|
||||
message: clear_notification
|
||||
tag: tina-night-meds
|
||||
@@ -4,12 +4,21 @@ input_boolean:
|
||||
tony_streaming_today:
|
||||
name: Tony Streaming Today
|
||||
icon: mdi:twitch
|
||||
tony_morning_meds_reminder:
|
||||
name: Tony Morning Meds Reminder
|
||||
icon: mdi:medication
|
||||
tony_morning_meds_taken:
|
||||
name: Tony Morning Meds Taken
|
||||
icon: mdi:medication
|
||||
tony_afternoon_meds_reminder:
|
||||
name: Tony Afternoon Meds Reminder
|
||||
icon: mdi:medication
|
||||
tony_afternoon_meds_taken:
|
||||
name: Tony Afternoon Meds Taken
|
||||
icon: mdi:medication
|
||||
tony_night_meds_reminder:
|
||||
name: Tony Night Meds Reminder
|
||||
icon: mdi:medication
|
||||
tony_night_meds_taken:
|
||||
name: Tony Night Meds Taken
|
||||
icon: mdi:medication
|
||||
@@ -64,17 +73,17 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tony_morning_meds_notify:
|
||||
name: Tony Morning Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_afternoon_meds_notify:
|
||||
name: Tony Afternoon Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_night_meds_notify:
|
||||
name: Tony Night Meds Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_custom_meds_taken_p1:
|
||||
@@ -84,7 +93,7 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tony_custom_meds_notify_p1:
|
||||
name: Tony Custom Meds Notify P1
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_custom_meds_taken_p2:
|
||||
@@ -94,7 +103,7 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tony_custom_meds_notify_p2:
|
||||
name: Tony Custom Meds Notify P2
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_ibuprofen_taken:
|
||||
@@ -104,7 +113,7 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tony_ibuprofen_notify:
|
||||
name: Tony Ibuprofen Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
tony_tylenol_taken:
|
||||
@@ -114,7 +123,7 @@ input_datetime:
|
||||
icon: mdi:medication
|
||||
tony_tylenol_notify:
|
||||
name: Tony Tylenol Notify
|
||||
has_date: false
|
||||
has_date: true
|
||||
has_time: true
|
||||
icon: mdi:medication
|
||||
|
||||
@@ -178,4 +187,34 @@ sensor:
|
||||
json_attributes:
|
||||
- project
|
||||
- items
|
||||
scan_interval: 30
|
||||
scan_interval: 30
|
||||
|
||||
# template:
|
||||
# - binary_sensor:
|
||||
# - name: Tony Morning Meds Needed
|
||||
# unique_id: 32f2f158-8c59-486e-bf85-f14909375ff7
|
||||
# state: >
|
||||
# {% set ct = as_timestamp(now()) %}
|
||||
# {% set notify = state_attr('input_datetime.tony_morning_meds_notify','timestamp') %}
|
||||
# {{ (ct >= notify) and is_state('input_boolean.tony_morning_meds_taken','off') }}
|
||||
# attributes:
|
||||
# reminder_time: "{{ states('input_datetime.tony_morning_meds_notify') }}"
|
||||
# icon: mdi:medication
|
||||
# - name: Tony Afternoon Meds Needed
|
||||
# unique_id: 363b5ea0-3ad7-4e98-b0b0-5ff67bbef2f4
|
||||
# state: >
|
||||
# {% set ct = as_timestamp(now()) %}
|
||||
# {% set notify = state_attr('input_datetime.tony_afternoon_meds_notify','timestamp') %}
|
||||
# {{ (ct >= notify) and is_state('input_boolean.tony_afternoon_meds_taken','off') }}
|
||||
# attributes:
|
||||
# reminder_time: "{{ states('input_datetime.tony_afternoon_meds_notify') }}"
|
||||
# icon: mdi:medication
|
||||
# - name: Tony Night Meds Needed
|
||||
# unique_id: b927b5a4-27a7-42aa-af4e-fa37a7036d25
|
||||
# state: >
|
||||
# {% set ct = as_timestamp(now()) %}
|
||||
# {% set notify = state_attr('input_datetime.tony_night_meds_notify','timestamp') %}
|
||||
# {{ (ct >= notify) and is_state('input_boolean.tony_night_meds_taken','off') }}
|
||||
# attributes:
|
||||
# reminder_time: "{{ states('input_datetime.tony_night_meds_notify') }}"
|
||||
# icon: mdi:medication
|
||||
|
||||
@@ -1617,7 +1617,6 @@ script:
|
||||
# snapshot_entities:
|
||||
# - light.tina_lamp_side
|
||||
# - light.tina_lamp_top
|
||||
# - light.tina_desk_strip
|
||||
# - switch.adaptive_lighting_living_room
|
||||
# - switch.adaptive_lighting_tina_lamp
|
||||
# - service: switch.turn_off
|
||||
@@ -1631,7 +1630,6 @@ script:
|
||||
# entity_id:
|
||||
# - light.tina_lamp_side
|
||||
# - light.tina_lamp_top
|
||||
# - light.tina_desk_strip
|
||||
# data:
|
||||
# color_name: red
|
||||
# - service: script.living_room_lights_alert
|
||||
|
||||
13
readme.md
13
readme.md
@@ -57,6 +57,7 @@ ## HACS Components
|
||||
- [Powercalc](https://github.com/bramstroker/homeassistant-powercalc)
|
||||
- [Govee LAN Control](https://github.com/wez/govee-lan-hass)
|
||||
- [Discord Game](https://github.com/LordBoos/discord_game)
|
||||
- [Versatile Thermostat](https://github.com/jmcollin78/versatile_thermostat)
|
||||
|
||||
</details>
|
||||
|
||||
@@ -67,6 +68,9 @@ ## HACS Lovelace Cards
|
||||
<details>
|
||||
<summary>Click here</summary>
|
||||
|
||||
- [Bubble Card](https://github.com/Clooos/Bubble-Card) Backbone of the new mobile dashboard
|
||||
- [Config Template Card](https://github.com/iantrich/config-template-card)
|
||||
- [Decluttering Card](https://github.com/custom-cards/decluttering-card)
|
||||
- [Card Tools](https://github.com/thomasloven/lovelace-card-tools) (required for various other cards)
|
||||
- [Layout Card](https://github.com/thomasloven/lovelace-layout-card)
|
||||
- [Scheduler Card](https://github.com/nielsfaber/scheduler-card) (required for Scheduler component)
|
||||
@@ -79,22 +83,16 @@ ## HACS Lovelace Cards
|
||||
- [Atomic Calendar Revive](https://github.com/totaldebug/atomic-calendar-revive)
|
||||
- [Plotly Graph Card](https://github.com/dbuezas/lovelace-plotly-graph-card)
|
||||
- [Mushroom](https://github.com/piitaya/lovelace-mushroom)
|
||||
- [Todoist Card](https://github.com/tm24fan8/todoist-card)
|
||||
- [Apexcharts Card](https://github.com/RomRider/apexcharts-card)
|
||||
- [Auto Entities Card](https://github.com/thomasloven/lovelace-auto-entities)
|
||||
- [Header Cards](https://github.com/gadgetchnnel/lovelace-header-cards)
|
||||
- [Plex Meets Home Assistant](https://github.com/JurajNyiri/PlexMeetsHomeAssistant)
|
||||
- [Slider Button Card](https://github.com/custom-cards/slider-button-card)
|
||||
- [Weather Radar Card](https://github.com/Makin-Things/weather-radar-card)
|
||||
- [Platinum Weather Card](https://github.com/Makin-Things/platinum-weather-card) (Not currently in use, but VERY nicely done)
|
||||
- [Stack In Card](https://github.com/custom-cards/stack-in-card)
|
||||
- [Canary](https://github.com/jcwillox/lovelace-canary)
|
||||
- [Paper Buttons Row](https://github.com/jcwillox/lovelace-paper-buttons-row)
|
||||
- [State Switch](https://github.com/thomasloven/lovelace-state-switch)
|
||||
- [Multiple Entity Row](https://github.com/benct/lovelace-multiple-entity-row)
|
||||
- [Weather Card](https://github.com/bramkragten/weather-card)
|
||||
- [Template Entity Row](https://github.com/thomasloven/lovelace-template-entity-row)
|
||||
- [Config Template Card](https://github.com/iantrich/config-template-card)
|
||||
- [Canvas Gauge Card](https://github.com/custom-cards/canvas-gauge-card)
|
||||
- [Datetime Card](https://github.com/a-p-z/datetime-card)
|
||||
- [Waze Travel Time](https://github.com/r-renato/ha-card-waze-travel-time)
|
||||
@@ -122,10 +120,9 @@ ## HACS Lovelace Cards
|
||||
- [Windrose Card](https://github.com/aukedejong/lovelace-windrose-card)
|
||||
- [Swipe Card](https://github.com/bramkragten/swipe-card)
|
||||
- [Meteoalarm Card](https://github.com/MrBartusek/MeteoalarmCard)
|
||||
- [Bubble Card](https://github.com/Clooos/Bubble-Card)
|
||||
- [Weather Chart Card](https://github.com/mlamberts78/weather-chart-card)
|
||||
- [Twitch Followed Live Streams Card](https://github.com/stefmde/HomeAssistant-TwitchFollowedLiveStreamsCard)
|
||||
- [Comfortable Environment Card](https://github.com/argaar/comfortable-environment-card)
|
||||
- [Versatile Thermostat UI Card](https://github.com/jmcollin78/versatile-thermostat-ui-card)
|
||||
|
||||
</details>
|
||||
|
||||
|
||||
1903
scripts.yaml
1903
scripts.yaml
File diff suppressed because it is too large
Load Diff
@@ -68,7 +68,6 @@
|
||||
states.light.downstairs_bathroom_right,
|
||||
states.light.tina_lamp_top,
|
||||
states.light.tina_lamp_side,
|
||||
states.light.tina_desk_strip,
|
||||
states.light.basement_tall_lamp,
|
||||
states.light.basement_short_lamp,
|
||||
states.light.basement_stairwell,
|
||||
@@ -103,7 +102,6 @@
|
||||
states.light.downstairs_bathroom_right,
|
||||
states.light.tina_lamp_top,
|
||||
states.light.tina_lamp_side,
|
||||
states.light.tina_desk_strip
|
||||
] %}
|
||||
{{ lights | selectattr('state','eq','on') | list | count | int }}
|
||||
- name: Second Floor Lights On
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
{% from 'speech.jinja' import greeting, today_is, sun_status %}
|
||||
{% from 'weather.jinja' import weatherReport %}
|
||||
{% from 'sports.jinja' import sports_updates %}
|
||||
{% from 'server.jinja' import services_down %}
|
||||
<p>
|
||||
{{ greeting('date') }}
|
||||
</p>
|
||||
@@ -22,10 +23,7 @@
|
||||
</p>
|
||||
|
||||
<p>
|
||||
There are {{ states('sensor.services_down') }} services currently offline.
|
||||
{% if states('sensor.services_down') | int > 0 %}
|
||||
They are {{ state_attr('sensor.services_down','services') }}.
|
||||
{% endif %}
|
||||
{{ services_down() }}
|
||||
</p>
|
||||
|
||||
<p>
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
{% from 'formatting.jinja' import cleanup %}
|
||||
{%- macro getReport() -%}
|
||||
{% from 'speech.jinja' import greeting, dadjoke, inspirational_quote, today_is %}
|
||||
{% from 'status.jinja' import tony_status_report, tina_status_report, kallen_status_report, emma_status_report %}
|
||||
{% from 'status.jinja' import tony_status_report, tina_status_report, kallen_status_report, emma_status_report, morning_annc %}
|
||||
{% from 'easy_time.jinja' import count_the_days %}
|
||||
{% from 'weather.jinja' import weatherReport %}
|
||||
{% from 'sports.jinja' import sports_updates %}
|
||||
@@ -14,6 +14,10 @@
|
||||
{{ today_is() }}
|
||||
</p>
|
||||
|
||||
<p>
|
||||
{{ morning_annc('full','tts') }}
|
||||
</p>
|
||||
|
||||
<p>
|
||||
{{ weatherReport('full','tts','morning') }}
|
||||
</p>
|
||||
|
||||
@@ -61,20 +61,20 @@
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% if is_state('input_boolean.kallen_overnight','off') %}
|
||||
{% if not is_state('input_select.scheduled_climate_mode_kallen_fan','N/A') %}
|
||||
{% if is_state('input_select.scheduled_climate_mode_kallen_fan','Fan') and is_state('fan.kallen_bedroom_fan','off') %}
|
||||
{% if not is_state('input_select.scheduled_climate_mode_kallen_bedroom','N/A') %}
|
||||
{% if is_state('input_select.scheduled_climate_mode_kallen_bedroom','Fan') and is_state('fan.kallen_bedroom_fan','off') %}
|
||||
"Collin's fan will activate at {{ input_datetime_read('input_datetime.kallen_fan') }}. "
|
||||
{% elif is_state('input_select.scheduled_climate_mode_kallen_fan','White Noise') and is_state('input_boolean.white_noise_kallen_bedroom','off') %}
|
||||
{% elif is_state('input_select.scheduled_climate_mode_kallen_bedroom','White Noise') and is_state('input_boolean.white_noise_kallen_bedroom','off') %}
|
||||
"Collin's white noise generator will activate at {{ input_datetime_read('input_datetime.kallen_bedtime') }}. "
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% else %}
|
||||
"Collin's room will be left alone, as he is spending the night elsewhere tonight. "
|
||||
{% endif %}
|
||||
{% if states('input_select.scheduled_climate_mode_emma_aircon') != 'N/A' %}
|
||||
{% if is_state('input_select.scheduled_climate_mode_emma_aircon','AC') and is_state('fan.emma_air_conditioner','off') %}
|
||||
{% if states('input_select.scheduled_climate_mode_emma_bedroom') != 'N/A' %}
|
||||
{% if is_state('input_select.scheduled_climate_mode_emma_bedroom','AC') and is_state('fan.emma_air_conditioner','off') %}
|
||||
"Emma's air conditioner will be activated at {{ input_datetime_read('input_datetime.emma_bedroom_cooling') }}. "
|
||||
{% elif is_state('input_select.scheduled_climate_mode_emma_aircon','White Noise') and is_state('input_boolean.white_noise_emma_bedroom','off') %}
|
||||
{% elif is_state('input_select.scheduled_climate_mode_emma_bedroom','White Noise') and is_state('input_boolean.white_noise_emma_bedroom','off') %}
|
||||
"Emma's white noise generator will activate at {{ input_datetime_read('input_datetime.emma_bedtime') }}. "
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
|
||||
429
www/bubble/bubble-modules.yaml
Normal file
429
www/bubble/bubble-modules.yaml
Normal file
@@ -0,0 +1,429 @@
|
||||
# Bubble Modules
|
||||
#
|
||||
# How to use:
|
||||
#
|
||||
# - To edit or add modules (global styles and templates), first copy the
|
||||
# "bubble-modules.yaml" file from "/www/community/Bubble-Card/" (if installed via HACS)
|
||||
# to "/www/bubble/" (you'll need to create this folder).
|
||||
#
|
||||
# Then add these lines in your "configuration.yaml" under "homeassistant:":
|
||||
#
|
||||
# homeassistant:
|
||||
# allowlist_external_dirs:
|
||||
# - /config/www/bubble
|
||||
# # This step is not needed if you already have this line:
|
||||
# - /config/www
|
||||
#
|
||||
# Then save and restart Home Assistant.
|
||||
#
|
||||
# - After making changes, you need to refresh your page to apply the modifications.
|
||||
#
|
||||
# - Styles and templates defined under "default:" are applied globally to all cards by default.
|
||||
#
|
||||
# - See the final example in this file for further details on how to create a module.
|
||||
#
|
||||
# - You can share/find modules here:
|
||||
# github.com/Clooos/Bubble-Card/discussions/categories/share-your-modules
|
||||
|
||||
|
||||
default:
|
||||
name: Default
|
||||
description: Empty and enabled by default. Move your styles/templates here in the <code>bubble-modules.yaml</code> file to apply them to all cards.
|
||||
code: |
|
||||
/* CSS or JS templates (see examples below) */
|
||||
|
||||
|
||||
home-assistant-default:
|
||||
name: Home Assistant default styling
|
||||
version: "v1.1"
|
||||
creator: "Clooos"
|
||||
link: "https://github.com/Clooos/Bubble-Card/discussions/1230"
|
||||
description: This module applies Home Assistant’s default styling to Bubble Card. To set it as the default, move it under <code>default:</code> in the <code>bubble-modules.yaml</code> file.
|
||||
code: |
|
||||
:host {
|
||||
--bubble-button-accent-color: rgba(0,140,255,0.3); /* Edit this color if needed */
|
||||
--bubble-main-background-color: var(--ha-card-background, var(--card-background-color, #fff));
|
||||
--bubble-border-radius: var(--ha-card-border-radius, 12px);
|
||||
--bubble-icon-border-radius: 32px;
|
||||
--bubble-button-border-radius: var(--bubble-border-radius);
|
||||
--bubble-climate-button-background-color: var(--bubble-icon-background-color);
|
||||
--bubble-border: var(--ha-card-border-width, 1px) solid var(--ha-card-border-color, var(--divider-color, #e0e0e0));
|
||||
--bubble-secondary-background-color: transparent;
|
||||
}
|
||||
|
||||
.bubble-container {
|
||||
-webkit-backdrop-filter: var(--ha-card-backdrop-filter, none);
|
||||
backdrop-filter: var(--ha-card-backdrop-filter, none);
|
||||
box-shadow: var(--ha-card-box-shadow, none);
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
.bubble-icon-container,
|
||||
.large .bubble-icon-container {
|
||||
--mdc-icon-size: 22px;
|
||||
min-width: 36px !important;
|
||||
min-height: 36px !important;
|
||||
}
|
||||
|
||||
.large .bubble-cover-card-container > .bubble-buttons {
|
||||
--bubble-cover-main-background-color: none;
|
||||
}
|
||||
|
||||
.bubble-range-fill {
|
||||
--bubble-accent-color: var(--bubble-button-accent-color);
|
||||
}
|
||||
|
||||
.bubble-sub-button.background-on::before,
|
||||
.bubble-sub-button.background-off::before,
|
||||
.bubble-temperature-container::before,
|
||||
.bubble-icon-container::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
opacity: var(--control-number-buttons-background-opacity, .2);
|
||||
border-radius: var(--bubble-border-radius);
|
||||
background: var(--control-number-buttons-background-color, var(--disabled-color));
|
||||
}
|
||||
|
||||
.is-on {
|
||||
--bubble-icon-background-color: var(--view-background,var(--lovelace-background,var(--primary-background-color)));
|
||||
transition: all ease-in 0.3s !important;
|
||||
}
|
||||
|
||||
.bubble-icon-container::before {
|
||||
background: var(--state-inactive-color);
|
||||
border-radius: var(--bubble-icon-border-radius);
|
||||
}
|
||||
|
||||
.bubble-sub-button {
|
||||
border: 0px solid transparent !important;
|
||||
}
|
||||
|
||||
.no-icon-select-arrow {
|
||||
right: 4px !important;
|
||||
}
|
||||
|
||||
.large .bubble-icon-container {
|
||||
margin-left: 9px;
|
||||
}
|
||||
|
||||
.bubble-state {
|
||||
opacity: 1;
|
||||
font-weight: 400;
|
||||
font-size: 12px;
|
||||
letter-spacing: .4px;
|
||||
}
|
||||
|
||||
:not(.bubble-separator) > .bubble-name {
|
||||
font-weight: 500;
|
||||
font-size: 14px;
|
||||
letter-spacing: 0.1px;
|
||||
}
|
||||
|
||||
.bubble-pop-up-background {
|
||||
filter: brightness(0.96); /* Improve pop-up background contrast */
|
||||
--bubble-pop-up-border-radius: calc(var(--ha-card-border-radius, 12px) * 1.4);
|
||||
}
|
||||
|
||||
.bubble-header-container {
|
||||
--bubble-secondary-background-color: var(--background-color-2);
|
||||
}
|
||||
|
||||
ha-select {
|
||||
--bubble-list-item-accent-color: none !important;
|
||||
--mdc-theme-surface: var(--card-background-color);
|
||||
}
|
||||
|
||||
mwc-list-item[selected] {
|
||||
color: inherit !important;
|
||||
--mdc-ripple-press-opacity: 0 !important;
|
||||
}
|
||||
|
||||
mwc-list-item[selected]::before {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
background-color: var(--primary-color);
|
||||
opacity: 0.24;
|
||||
}
|
||||
|
||||
|
||||
icon_container_color:
|
||||
name: "Example: Customize the icon container color"
|
||||
version: "v1.1"
|
||||
creator: "Clooos"
|
||||
link: "https://github.com/Clooos/Bubble-Card/discussions/1231"
|
||||
|
||||
unsupported:
|
||||
- horizontal-buttons-stack
|
||||
- separator
|
||||
|
||||
description: |
|
||||
A list of predefined colors to customize the icon container color.
|
||||
Configure this module via the editor or in YAML, for example:
|
||||
<br><br>
|
||||
<code-block><pre>
|
||||
icon_container_color:
|
||||
color: light-blue
|
||||
</pre></code-block>
|
||||
|
||||
code: |
|
||||
.bubble-icon-container {
|
||||
opacity: 1 !important;
|
||||
background: var(--${this.config.icon_container_color?.color}-color) !important;
|
||||
}
|
||||
|
||||
editor:
|
||||
- name: color
|
||||
label: "Color"
|
||||
selector:
|
||||
ui_color:
|
||||
include_none: true
|
||||
|
||||
|
||||
get_state_attribute:
|
||||
|
||||
# Some informations about your module (this is shown in the editor)
|
||||
name: "Advanced example: Get state/attribute from other entities"
|
||||
version: "v1.1"
|
||||
creator: "Clooos"
|
||||
link: "https://github.com/Clooos/Bubble-Card"
|
||||
|
||||
# Disable this module for unsupported "card_type"
|
||||
unsupported:
|
||||
- horizontal-buttons-stack
|
||||
- separator
|
||||
|
||||
# The description have HTML support like in this example. This model is my favorite.
|
||||
description: |
|
||||
Get state/attribute from other entities and replace the default state/attribute field.
|
||||
<img class="example" src="https://github.com/Clooos/Bubble-Card/blob/main/img/get_state_template_example.png?raw=true" />
|
||||
Configure this module via the editor or in YAML, for example:
|
||||
<br><br>
|
||||
<code-block><pre>
|
||||
get_state_attribute:
|
||||
- entity: weather.home
|
||||
- entity: sensor.weather_station
|
||||
attribute: humidity
|
||||
- entity: sensor.weather_station
|
||||
attribute: temperature
|
||||
</pre></code-block>
|
||||
<br>
|
||||
<b>If it doesn't work, make sure at least one of "Show state" or "Show attribute" is turned on in your card configuration.</b>
|
||||
|
||||
# Code blocks must always start with ${(() => { and end with })()}
|
||||
# Inline codes must always start with ${ and end with }
|
||||
#
|
||||
# This section only supports JavaScript and/or CSS
|
||||
code: |
|
||||
${(() => {
|
||||
// Retrieve the configuration or use an empty array by default
|
||||
const config = this.config.get_state_attribute || [];
|
||||
|
||||
// Format the retrieved value from the entity for each entry
|
||||
const values = config
|
||||
.map(cfg => {
|
||||
const entity = hass.states[cfg.entity];
|
||||
if (entity) {
|
||||
return cfg.attribute
|
||||
? hass.formatEntityAttributeValue(entity, cfg.attribute)
|
||||
: hass.formatEntityState(entity);
|
||||
}
|
||||
return null;
|
||||
})
|
||||
.filter(value => value !== null); // Remove null values
|
||||
|
||||
// Update the DOM element with the class 'bubble-state'
|
||||
// displaying values separated by ' • '
|
||||
card.querySelector('.bubble-state').innerText = values.join(' • ');
|
||||
})()}
|
||||
|
||||
# The editor part can be tricky, but improves modules a lot!
|
||||
#
|
||||
# In this example, it will create your configuration to this variable:
|
||||
# this.config.get_state_attribute
|
||||
#
|
||||
# To understand what you can do here, take a look at the "ha-form" sources here:
|
||||
# https://github.com/home-assistant/frontend/tree/03a415beff6e6f9c87a95287804f6c03c8fef3d5/src/components/ha-form
|
||||
#
|
||||
# And here for the selectors:
|
||||
# https://github.com/home-assistant/frontend/blob/03a415beff6e6f9c87a95287804f6c03c8fef3d5/src/data/selector.ts
|
||||
#
|
||||
# I will try to document that for clarity!
|
||||
editor:
|
||||
- type: expandable
|
||||
title: "Select entities and attributes"
|
||||
icon: "mdi:list-box-outline"
|
||||
schema:
|
||||
- name: '0'
|
||||
type: expandable
|
||||
title: "Entity 1"
|
||||
schema:
|
||||
- name: entity
|
||||
label: "Entity"
|
||||
selector:
|
||||
entity: {}
|
||||
- name: attribute
|
||||
label: "Attribute"
|
||||
selector:
|
||||
attribute: {}
|
||||
- name: '1'
|
||||
type: expandable
|
||||
title: "Entity 2"
|
||||
schema:
|
||||
- name: entity
|
||||
label: "Entity"
|
||||
selector:
|
||||
entity: {}
|
||||
- name: attribute
|
||||
label: "Attribute"
|
||||
selector:
|
||||
attribute: {}
|
||||
- name: '2'
|
||||
type: expandable
|
||||
title: "Entity 3"
|
||||
schema:
|
||||
- name: entity
|
||||
label: "Entity"
|
||||
selector:
|
||||
entity: {}
|
||||
- name: attribute
|
||||
label: "Attribute"
|
||||
selector:
|
||||
attribute: {}
|
||||
- name: '3'
|
||||
type: expandable
|
||||
title: "Entity 4"
|
||||
schema:
|
||||
- name: entity
|
||||
label: "Entity"
|
||||
selector:
|
||||
entity: {}
|
||||
- name: attribute
|
||||
label: "Attribute"
|
||||
selector:
|
||||
attribute: {}
|
||||
|
||||
# Temperature
|
||||
temperature_colouring:
|
||||
name: "Temperature colouring"
|
||||
version: "v1.0"
|
||||
creator: "Timmy"
|
||||
|
||||
unsupported:
|
||||
- horizontal-buttons-stack
|
||||
- media-player
|
||||
|
||||
description: |
|
||||
This module provides dynamic colouring based on temperature sensor values.
|
||||
Colour adjustments are applied to selected sub-buttons and/or state display elements.
|
||||
|
||||
Required entities:
|
||||
- A temperature sensor
|
||||
|
||||
You can configure which elements should receive dynamic colouring:
|
||||
- Sub-buttons (1-6)
|
||||
- State display
|
||||
|
||||
Example YAML configuration:
|
||||
|
||||
temperature_colouring:
|
||||
temperature_sensor: sensor.kitchen_temperature
|
||||
elements:
|
||||
sub_buttons: [1, 3, 5] # Apply to sub-buttons 1, 3, and 5
|
||||
state_display: true # Apply to state display element
|
||||
|
||||
code: |
|
||||
${(() => {
|
||||
const temperature = parseFloat(hass?.states[this.config?.temperature_colouring?.temperature_sensor]?.state || 0);
|
||||
const elements = this.config?.temperature_colouring?.elements || {};
|
||||
|
||||
let color;
|
||||
if (temperature <= 32) {
|
||||
color = 'rgba(0,0,139,0.8)';
|
||||
} else if (temperature <= 41) {
|
||||
color = 'rgba(0,71,171,0.8)';
|
||||
} else if (temperature <= 50) {
|
||||
color = 'rgba(30,144,255,0.8)';
|
||||
} else if (temperature <= 61) {
|
||||
color = 'rgba(100,149,237,0.8)';
|
||||
} else if (temperature <= 68) {
|
||||
color = 'rgba(60,179,113,0.8)';
|
||||
} else if (temperature <= 73) {
|
||||
color = 'rgba(152,251,152,0.8)';
|
||||
} else if (temperature <= 78) {
|
||||
color = 'rgba(255,223,186,0.8)';
|
||||
} else if (temperature <= 80) {
|
||||
color = 'rgba(255,215,0,0.8)';
|
||||
} else if (temperature <= 95) {
|
||||
color = 'rgba(178,34,34,0.8)';
|
||||
} else {
|
||||
color = 'rgba(139,0,0,0.8)';
|
||||
}
|
||||
|
||||
// Apply colour to selected sub-buttons
|
||||
if (elements.sub_buttons) {
|
||||
const subButtons = Array.isArray(elements.sub_buttons) ? elements.sub_buttons : [];
|
||||
subButtons.forEach(num => {
|
||||
if (num >= 1 && num <= 6) {
|
||||
const subButton = card?.querySelector(`.bubble-sub-button-${num} ha-icon`);
|
||||
if (subButton) {
|
||||
subButton.style.color = color;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// Apply colour to state display if enabled
|
||||
if (elements.state_display) {
|
||||
const stateElement = card?.querySelector('.bubble-state.state.display-state');
|
||||
if (stateElement) {
|
||||
stateElement.style.color = color;
|
||||
}
|
||||
}
|
||||
|
||||
return ''; // No CSS needed as we're applying styles directly to elements
|
||||
})()}
|
||||
|
||||
editor:
|
||||
- type: expandable
|
||||
title: "Entity Configuration"
|
||||
icon: "mdi:thermometer"
|
||||
schema:
|
||||
- name: temperature_sensor
|
||||
label: "Temperature Sensor (Required)"
|
||||
selector:
|
||||
entity:
|
||||
device_class: temperature
|
||||
required: true
|
||||
- name: elements
|
||||
type: grid
|
||||
schema:
|
||||
- name: sub_buttons
|
||||
label: "Sub-buttons to Style"
|
||||
selector:
|
||||
select:
|
||||
multiple: true
|
||||
options:
|
||||
- label: "Sub-button 1"
|
||||
value: 1
|
||||
- label: "Sub-button 2"
|
||||
value: 2
|
||||
- label: "Sub-button 3"
|
||||
value: 3
|
||||
- label: "Sub-button 4"
|
||||
value: 4
|
||||
- label: "Sub-button 5"
|
||||
value: 5
|
||||
- label: "Sub-button 6"
|
||||
value: 6
|
||||
- name: state_display
|
||||
label: "State Display"
|
||||
selector:
|
||||
boolean: {}
|
||||
Reference in New Issue
Block a user