From 8b389fcdc08b5a49c2fceff0e1df9c895ddbd47c Mon Sep 17 00:00:00 2001 From: ESPHome Device Builder Date: Sun, 28 Jun 2026 18:29:39 +1200 Subject: [PATCH] Edit esp-astroclockstepper1.yaml --- esphome/esp-astroclockstepper1.yaml | 99 +++++++++++++++++++++++------ 1 file changed, 81 insertions(+), 18 deletions(-) diff --git a/esphome/esp-astroclockstepper1.yaml b/esphome/esp-astroclockstepper1.yaml index bfccb42..6083da2 100644 --- a/esphome/esp-astroclockstepper1.yaml +++ b/esphome/esp-astroclockstepper1.yaml @@ -6,6 +6,7 @@ # https://home.fox.co.nz/gitea/zorruno/zorruno-homeassistant/src/branch/master/esphome/esp-astroclockstepper.yaml #:########################################################################################:# # VERSIONS: +# V1.5 2026-06-22 Changed Motor Stop to OFF on boot and added shortest-path auto-positioning # V1.4 2026-06-22 Added Motor Stop switch, swapped reverse buttons 3/4, and separated auto-position motor direction # V1.3 2026-06-22 Added SNTP year auto-positioning button and restored boot auto-position switch # V1.2 2026-06-22 Added DHCP IPv4 address flash sequence on onboard LED after WiFi connects @@ -42,9 +43,9 @@ # - Active-low on most D1 Mini boards #:########################################################################################:# # OPERATION NOTES: -# - Normal rotation starts automatically after boot only when Motor Stop is OFF. -# - Motor Stop is ON by default after every reboot and is not restored. -# - Motor Stop turns off all motor coils and pauses physical position counting. +# - Normal rotation starts automatically after boot because Motor Stop defaults OFF. +# - Motor Stop is OFF by default after every reboot and is not restored. +# - Motor Stop ON turns off all motor coils and pauses physical position counting. # - Default rotation is one full revolution every 365.2422 days. # - Default step count is 4096 steps per full revolution. # - Normal movement is extremely slow, about one step every 2.14 hours. @@ -59,7 +60,8 @@ # - A digit of 0 is represented as 10 flashes. # - SNTP is used for current year-position calculation. # - User should manually align the dial to year-zero, then press Zero Position Counter. -# - Auto Position Now moves forward logically to the current calculated year position. +# - Auto Position Now moves to the current calculated year position by the shortest path. +# - Auto Position can move clockwise or anti-clockwise, whichever is quicker. # - Auto-position motor direction is separately adjustable from normal/manual movement. # - Auto Position On Boot is off by default, restored on power loss, and runs after boot/IP flash if Motor Stop is OFF. #:########################################################################################:# @@ -78,7 +80,7 @@ # d) Device power loss / reboot # - Current position counter is restored from flash # - Auto Position On Boot setting is restored from flash -# - Motor Stop returns to ON after every reboot +# - Motor Stop returns to OFF after every reboot # - Physical position is assumed valid because the motor housing/dial is fixed #:########################################################################################:# @@ -96,7 +98,7 @@ substitutions: # Project Naming project_name: "zorruno.Astronomical Clock Stepper" - project_version: "v1.4" + project_version: "v1.5" # Passwords & Secrets (Unfortunately, you cannot use substitutions inside secret names) api_key: !secret esp-api_key @@ -120,10 +122,16 @@ substitutions: normal_direction_multiplier: "1" # Auto-position motor direction. - # This is separate so auto-position can move clockwise while still counting logically forward. - # Set to -1 because auto-position was observed to be running anti-clockwise. + # This is the physical motor phase direction used when the logical year position increases. + # Reverse auto-position uses the opposite of this automatically. + # Set to -1 because auto-position was observed to be running anti-clockwise when this was 1. auto_position_motor_direction_multiplier: "-1" + # Auto Position Path + # true = move clockwise or anti-clockwise, whichever is quicker + # false = always move logically forward through the year + auto_position_use_shortest_path: "true" + # Manual Movement Speeds manual_fast_rotation_seconds: "30" manual_slow_rotation_seconds: "300" @@ -243,6 +251,9 @@ esphome: then: - output.turn_off: onboard_step_led + # Motor Stop should always be OFF on boot so normal movement can run. + - switch.turn_off: motor_stop_switch + - logger.log: level: INFO format: "Astronomical Clock Stepper started. Normal rotation is %s days per full revolution." @@ -510,6 +521,13 @@ globals: restore_value: no initial_value: "0" + # 1 = logical forward / clockwise year position increase + # -1 = logical reverse / anti-clockwise year position decrease + - id: auto_position_logical_direction + type: int + restore_value: no + initial_value: "1" + #:########################################################################################:# # OUTPUT: @@ -602,6 +620,7 @@ script: then: - lambda: |- const int STEPS_PER_ROTATION = ${steps_per_rotation}; + const bool AUTO_POSITION_USE_SHORTEST_PATH = ${auto_position_use_shortest_path}; auto now = id(sntp_time).now(); @@ -677,13 +696,25 @@ script: current_step += STEPS_PER_ROTATION; } - const int steps_to_move = + const int forward_steps = (target_step - current_step + STEPS_PER_ROTATION) % STEPS_PER_ROTATION; - id(auto_position_target_step) = target_step; - id(auto_position_steps_remaining) = steps_to_move; + const int reverse_steps = + (current_step - target_step + STEPS_PER_ROTATION) % STEPS_PER_ROTATION; - if (steps_to_move == 0) { + int chosen_steps = forward_steps; + int chosen_logical_direction = 1; + + if (AUTO_POSITION_USE_SHORTEST_PATH && reverse_steps < forward_steps) { + chosen_steps = reverse_steps; + chosen_logical_direction = -1; + } + + id(auto_position_target_step) = target_step; + id(auto_position_steps_remaining) = chosen_steps; + id(auto_position_logical_direction) = chosen_logical_direction; + + if (chosen_steps == 0) { id(auto_position_active) = false; ESP_LOGI( "auto_position", @@ -698,13 +729,16 @@ script: ESP_LOGI( "auto_position", - "Auto positioning started. Year: %d, day_of_year: %d/%d, target step: %d, current step: %d, moving forward %d logical steps.", + "Auto positioning started. Year: %d, day_of_year: %d/%d, target step: %d, current step: %d, forward steps: %d, reverse steps: %d, chosen direction: %s, moving %d logical steps.", year, day_of_year, days_in_year, target_step, current_step, - steps_to_move + forward_steps, + reverse_steps, + chosen_logical_direction >= 0 ? "forward" : "reverse", + chosen_steps ); @@ -799,8 +833,10 @@ switch: icon: mdi:motor-off optimistic: true - # ON by default after every boot. State is not restored. - restore_mode: ALWAYS_ON + # OFF by default after every boot. State is not restored. + # OFF means the motor is allowed to run. + # ON means motor outputs are disabled. + restore_mode: ALWAYS_OFF turn_on_action: - switch.turn_off: web_fast_forward_switch @@ -958,6 +994,9 @@ button: - globals.set: id: auto_position_steps_remaining value: "0" + - globals.set: + id: auto_position_logical_direction + value: "1" - logger.log: level: INFO format: "Position counter zeroed." @@ -1103,6 +1142,22 @@ text_sensor: lambda: |- return {"${normal_direction_name}"}; + - platform: template + name: "Auto Position Direction" + id: auto_position_direction_text_sensor + icon: mdi:rotate-3d-variant + update_interval: "${sensor_update_interval}" + lambda: |- + if (!id(auto_position_active)) { + return {"Idle"}; + } + + if (id(auto_position_logical_direction) < 0) { + return {"Reverse / Anti-clockwise"}; + } + + return {"Forward / Clockwise"}; + #:########################################################################################:# # INTERVAL: @@ -1291,8 +1346,15 @@ interval: selected_step_interval_ms = SLOW_STEP_INTERVAL_MS; } else if (id(auto_position_active)) { selected_mode = 5; - selected_logical_direction = 1; - selected_motor_direction = AUTO_POSITION_MOTOR_DIRECTION_MULTIPLIER; + selected_logical_direction = id(auto_position_logical_direction); + + if (selected_logical_direction == 0) { + selected_logical_direction = 1; + } + + selected_motor_direction = + selected_logical_direction * AUTO_POSITION_MOTOR_DIRECTION_MULTIPLIER; + selected_step_interval_ms = AUTO_POSITION_STEP_INTERVAL_MS; } else { selected_mode = 0; @@ -1317,6 +1379,7 @@ interval: if (id(auto_position_steps_remaining) <= 0) { id(auto_position_steps_remaining) = 0; id(auto_position_active) = false; + id(auto_position_logical_direction) = 1; id(current_motion_mode) = 0; ESP_LOGI(