A cyclic timer without the use of automation, scripts, etc. in HA. Possible applications: aquarium aeration, plant illumination. The timer is set to the interval between switching on and off the relay.
Maybe it will be useful to someone. Maybe someone will suggest doing it differently.
substitutions:
platform: bk72xx
board: cb2s
framework_version: recommended
device_name_short: "pm"
friendly_name: "PowerMeter"
device_description: "Aubess PM Smart Switch"
logger_level: WARN
update_interval: 15s
packages:
base: !include common/pm_global.yaml
base_pm: !include common/uart_bl0942.yaml
binary_sensor:
- platform: gpio
pin:
number: P23
mode:
input: true
pullup: true
id: "PM04_button"
filters:
- delayed_on: 50ms
- delayed_off: 50ms
on_press:
- switch.toggle: main_relay
- logger.log:
level: WARN
format: "Button pressed"
- platform: gpio
pin:
number: P24
mode:
input: true
pullup: true
id: "PM04_switch"
filters:
- delayed_on: 50ms
- delayed_off: 50ms
on_press:
- switch.toggle: main_relay
- logger.log:
level: WARN
format: "Switch toggle"
status_led:
id: status_leds
pin:
number: P8
inverted: true
switch:
- platform: gpio
name: "${device_name_short} Relay"
pin: P26
id: main_relay
restore_mode: RESTORE_DEFAULT_OFF
on_turn_off:
- globals.set:
id: is_active
value: 'false'
- logger.log:
level: WARN
format: "Relay turned off"
on_turn_on:
- globals.set:
id: is_active
value: 'true'
- logger.log:
level: WARN
format: "Relay turned on"
- platform: template
name: "${device_name_short} On/Off Timer"
id: timer_switch
icon: "mdi:timer"
entity_category: "config"
restore_mode: RESTORE_DEFAULT_ON
optimistic: true
lambda: |-
return id(timer_enabled);
turn_on_action:
- globals.set:
id: timer_enabled
value: 'true'
- logger.log:
level: WARN
format: "Timer enabled"
turn_off_action:
- globals.set:
id: timer_enabled
value: 'false'
- logger.log:
level: WARN
format: "Timer disabled"
- lambda: |-
id(cycle_start) = esphome::millis();
globals:
- id: is_active
type: bool
restore_value: yes
initial_value: 'true'
- id: cycle_start
type: unsigned long
restore_value: no
initial_value: '0'
- id: timer_enabled
type: bool
restore_value: yes
initial_value: 'true'
- id: on_duration
type: unsigned long
restore_value: yes
initial_value: '7200000' # 2h
- id: off_duration
type: unsigned long
restore_value: yes
initial_value: '3600000' # 1h
number:
- platform: template
name: "${device_name_short} ON Timer"
entity_category: "config"
unit_of_measurement: h
mode: box
id: set_on_time
min_value: 1
max_value: 4
step: 1
optimistic: true
restore_value: yes
set_action:
- lambda: |-
id(on_duration) = static_cast<unsigned long>(x * 3600000UL);
id(cycle_start) = esphome::millis();
- platform: template
name: "${device_name_short} OFF Timer"
entity_category: "config"
unit_of_measurement: h
mode: box
id: set_off_time
min_value: 1
max_value: 4
step: 1
optimistic: true
restore_value: yes
set_action:
- lambda: |-
id(off_duration) = static_cast<unsigned long>(x * 3600000UL);
id(cycle_start) = esphome::millis();
interval:
- interval: 30s
then:
- if:
condition:
lambda: |-
if (!id(timer_enabled)) return false;
const unsigned long now = esphome::millis();
const unsigned long elapsed = now - id(cycle_start);
return id(is_active) ?
(elapsed >= id(on_duration)) :
(elapsed >= id(off_duration));
then:
- if:
condition:
lambda: return id(is_active);
then:
- switch.turn_off: main_relay
- logger.log:
level: WARN
format: "Timer: Reley off"
else:
- switch.turn_on: main_relay
- logger.log:
level: WARN
format: "Timer: Reley on"
- globals.set:
id: cycle_start
value: !lambda return esphome::millis();
text_sensor:
- platform: template
name: "${device_name_short} _Status Timer"
icon: "mdi:list-status"
entity_category: ""
lambda: |-
using namespace esphome;
static char buffer[35];
if (!id(timer_enabled)) {
return optional<std::string>("Timer Off");
}
const unsigned long elapsed = esphome::millis() - id(cycle_start);
const int hours = elapsed / 3600000;
const int minutes = (elapsed % 3600000) / 60000;
snprintf(buffer, sizeof(buffer), "%s: %dh %02dm",
id(is_active) ? "ON" : "OFF",
hours,
minutes);
return optional<std::string>(buffer);
update_interval: 15s