From 04ac0bcb33a7d7e2e3036e4484d3ee28197c826c Mon Sep 17 00:00:00 2001
From: Tony Stork
Date: Tue, 4 Apr 2023 22:46:45 -0400
Subject: [PATCH] Improved forecast for the actual overnight low temperature
---
packages/custom_weather.yaml | 71 +++++++++++++++++++++++---
packages/scheduling.yaml | 16 +++---
templates/speech/nightly_briefing.yaml | 2 +-
3 files changed, 73 insertions(+), 16 deletions(-)
diff --git a/packages/custom_weather.yaml b/packages/custom_weather.yaml
index 397d427..05104bb 100644
--- a/packages/custom_weather.yaml
+++ b/packages/custom_weather.yaml
@@ -13,7 +13,25 @@ weather:
wind_bearing_template: "{{ states('sensor.pirateweather_wind_bearing') | float }}"
visibility_template: "{{ states('sensor.kdfi_visibility') | float }}"
visibility_unit: mi
- attribution_template: "Weather data from Iron Nerd's custom weather station template"
+ attribution_template: "Daily weather data from Iron Nerd's custom weather station template"
+ ozone_template: "{{ states('sensor.pirateweather_ozone') | float }}"
+ precipitation_unit: in
+
+ - platform: template
+ name: "Iron Nerd Weather Station - Hourly"
+ condition_template: "{{ states('weather.iron_nerd_studios') }}"
+ temperature_template: "{{ states('sensor.pirateweather_temperature') | float }}"
+ temperature_unit: °F
+ humidity_template: "{{ states('sensor.pirateweather_humidity') | float }}"
+ forecast_template: "{{ state_attr('weather.kdfi_hourly', 'forecast') }}"
+ pressure_template: "{{ states('sensor.kdfi_barometric_pressure') | float }}"
+ pressure_unit: inHg
+ wind_speed_template: "{{ states('sensor.pirateweather_wind_speed') | float }}"
+ wind_speed_unit: mph
+ wind_bearing_template: "{{ states('sensor.pirateweather_wind_bearing') | float }}"
+ visibility_template: "{{ states('sensor.kdfi_visibility') | float }}"
+ visibility_unit: mi
+ attribution_template: "Hourly weather data from Iron Nerd's custom weather station template"
ozone_template: "{{ states('sensor.pirateweather_ozone') | float }}"
precipitation_unit: in
@@ -262,7 +280,7 @@ sensor:
'Later tonight expect a low of ',
'Overnight expect a low of '
] | random }}
- {{ states('sensor.tonights_low_temp') }} degrees.
+ {{ states('sensor.overnight_lowest_temperature') }} degrees.
{%- endmacro -%}
{# a macro that removes all newline characters, empty spaces, and returns formatted text #}
{%- macro cleanup(data) -%}
@@ -605,13 +623,13 @@ sensor:
'Later tonight expect a low of ',
'Overnight expect a low of '
] | random }}
- {{ states('sensor.tonights_low_temp') }} degrees.
+ {{ states('sensor.overnight_lowest_temperature') }} degrees.
{%- else -%}
{{ [
'Tonight expect a low of ',
'Overnight expect a low of '
] | random }}
- {{ states('sensor.tonights_low_temp') }} degrees.
+ {{ states('sensor.overnight_lowest_temperature') }} degrees.
{% endif %}
{%- endmacro -%}
{# a macro that removes all newline characters, empty spaces, and returns formatted text #}
@@ -931,6 +949,45 @@ sensor:
mdi:alert-remove
{% endif %}
+# Sensors to more accurately forecast the overnight temperatures
+ overnight_lowest_temperature:
+ friendly_name: 'Overnight Lowest Temperature'
+ unique_id: 70bdffbe-dc55-4913-af70-a37a6db2bcaa
+ unit_of_measurement: '°F'
+ value_template: >
+ {% set ns = namespace(temps=[]) %}
+ {% set x = state_attr('weather.iron_nerd_weather_station_hourly','forecast') | count %}
+ {% set pd = state_attr('weather.iron_nerd_weather_station_hourly','forecast') %}
+ {% for i in range(0,x) %}
+ {% set hr = as_timestamp(as_local(as_datetime(pd[i].datetime))) | timestamp_custom('%H') | int %}
+ {% if hr in range(21,24) or hr in range(0,8) %}
+ {% if as_local(as_datetime(pd[i].datetime)) == now().replace(hour=hr, minute=00, second=0, microsecond=0) + timedelta(days=0) or
+ as_local(as_datetime(pd[i].datetime)) == now().replace(hour=hr, minute=00, second=0, microsecond=0) + timedelta(days=1) %}
+ {% set ns.temps = ns.temps + [pd[i].temperature] %}
+ {% endif %}
+ {% endif %}
+ {% endfor %}
+ {{ ns.temps | min | int }}
+ icon_template: mdi:thermometer
+
+input_number:
+ today_calculated_high_temp:
+ name: Today Calculated High Temp
+ min: -100
+ max: 150
+ step: 1
+ unit_of_measurement: °F
+ icon: mdi:thermometer
+ mode: box
+ today_calculated_low_temp:
+ name: Today Calculated Low Temp
+ min: -100
+ max: 150
+ step: 1
+ unit_of_measurement: °F
+ icon: mdi:thermometer
+ mode: box
+
input_boolean:
freeze_warning:
name: Freeze Warning
@@ -966,7 +1023,7 @@ automation:
alias: Forecast Low Near Freezing
trigger:
- platform: numeric_state
- entity_id: sensor.tonights_low_temp
+ entity_id: sensor.overnight_lowest_temperature
below: 35
- platform: numeric_state
entity_id: sensor.pirateweather_temperature
@@ -983,14 +1040,14 @@ automation:
alias: Forecast Low Above Freezing
trigger:
- platform: numeric_state
- entity_id: sensor.tonights_low_temp
+ entity_id: sensor.overnight_lowest_temperature
above: 33
condition:
- condition: state
entity_id: input_boolean.freeze_warning
state: 'on'
- condition: numeric_state
- entity_id: sensor.tonights_low_temp
+ entity_id: sensor.overnight_lowest_temperature
above: 35
action:
- service: input_boolean.turn_off
diff --git a/packages/scheduling.yaml b/packages/scheduling.yaml
index 464786c..43bcc87 100644
--- a/packages/scheduling.yaml
+++ b/packages/scheduling.yaml
@@ -319,7 +319,7 @@ script:
option: >
{% if is_state('input_boolean.kallen_overnight','on') %}
N/A
- {% elif (states('sensor.tonights_low_temp') | int) >= (states('input_number.kallen_fan_threshold') | int) %}
+ {% elif (states('sensor.overnight_lowest_temperature') | int) >= (states('input_number.kallen_fan_threshold') | int) %}
Fan
{% else %}
White Noise
@@ -513,7 +513,7 @@ script:
entity_id: input_datetime.master_bedroom_cooling
data:
time: >
- {% set low = states('sensor.tonights_low_temp') | int %}
+ {% set low = states('sensor.overnight_lowest_temperature') | int %}
{% if is_state('input_boolean.hot_day','on') and is_state('binary_sensor.kallen_school_tomorrow','on') %}
20:00
{% elif is_state('input_boolean.hot_day','on') and is_state('binary_sensor.kallen_school_tomorrow','off') %}
@@ -529,7 +529,7 @@ script:
entity_id: input_datetime.master_bedroom_fan
data:
time: >
- {% set low = states('sensor.tonights_low_temp') | int %}
+ {% set low = states('sensor.overnight_lowest_temperature') | int %}
{% set high = states('sensor.todays_high_temp') | int %}
{% if low > 60 or is_state('input_boolean.hot_day','on') %}
22:30
@@ -547,8 +547,8 @@ script:
option: >
{% if is_state('input_boolean.master_bedroom_aircon_installed','off') %}
N/A
- {% elif (states('sensor.tonights_low_temp') | int) >= (states('input_number.master_bedroom_aircon_run_threshold') | int) %}
- {% if (states('sensor.tonights_low_temp') | int) >= (states('input_number.master_bedroom_aircon_mode_threshold') | int) %}
+ {% elif (states('sensor.overnight_lowest_temperature') | int) >= (states('input_number.master_bedroom_aircon_run_threshold') | int) %}
+ {% if (states('sensor.overnight_lowest_temperature') | int) >= (states('input_number.master_bedroom_aircon_mode_threshold') | int) %}
AC
{% else %}
Fan
@@ -561,7 +561,7 @@ script:
entity_id: input_select.scheduled_climate_mode_master_bedroom_fan
data:
option: >
- {% if (states('sensor.tonights_low_temp') | int) >= (states('input_number.master_bedroom_fan_threshold') | int) %}
+ {% if (states('sensor.overnight_lowest_temperature') | int) >= (states('input_number.master_bedroom_fan_threshold') | int) %}
Fan
{% else %}
N/A
@@ -600,7 +600,7 @@ script:
data:
time: >
{% set high = states('sensor.todays_high_temp') | int %}
- {% set low = states('sensor.tonights_low_temp') | int %}
+ {% set low = states('sensor.overnight_lowest_temperature') | int %}
{% if is_state('input_boolean.hot_day','on') %}
22:00
{% elif high >= 80 or low >= 60 %}
@@ -619,7 +619,7 @@ script:
data:
option: >
{% if is_state('input_boolean.emma_bedroom_aircon_installed','on') %}
- {% if (states('sensor.tonights_low_temp') | int) >= (states('input_number.emma_aircon_threshold') | int) %}
+ {% if (states('sensor.overnight_lowest_temperature') | int) >= (states('input_number.emma_aircon_threshold') | int) %}
AC
{% else %}
White Noise
diff --git a/templates/speech/nightly_briefing.yaml b/templates/speech/nightly_briefing.yaml
index 219850a..a13cba6 100644
--- a/templates/speech/nightly_briefing.yaml
+++ b/templates/speech/nightly_briefing.yaml
@@ -458,7 +458,7 @@
- {% if (states('sensor.tonights_low_temp') | int) <= (states('input_number.overnight_low_threshold') | int ) %}
+ {% if (states('sensor.overnight_lowest_temperature') | int) <= (states('input_number.overnight_low_threshold') | int ) %}
"It will be very cold tonight, make sure to use extra blankets, wear more clothes, or whatever else will help you stay warm! Additionally, make sure Emma's heater is set high enough!"
{% endif %}