feat(patterns): reverse animation direction via preset n8

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-05-17 18:32:01 +12:00
parent 55a97ac51c
commit 94266d5a7c
11 changed files with 131 additions and 62 deletions

View File

@@ -13,13 +13,8 @@ class Pulse:
bg_base = preset.background_or(colors)
self.driver.fill(self.driver.apply_brightness(bg_base, preset.b))
manual = not preset.a
color_index = self.driver.step % max(1, len(colors))
if not preset.a:
# Manual / beat trigger: each select restarts this generator and resets
# cycle_start below. Advancing step here makes each beat the next colour
# without requiring a full wall-clock cycle between beats.
nclr = max(1, len(colors))
self.driver.step = (color_index + 1) % nclr
cycle_start = utime.ticks_ms()
# State machine based pulse using a single generator loop
@@ -29,7 +24,7 @@ class Pulse:
attack_ms = max(0, int(preset.n1)) # Attack time in ms
hold_ms = max(0, int(preset.n2)) # Hold time in ms
decay_ms = max(0, int(preset.n3)) # Decay time in ms
delay_ms = max(0, int(preset.d))
delay_ms = 0 if manual else max(0, int(preset.d))
total_ms = attack_ms + hold_ms + decay_ms + delay_ms
if total_ms <= 0:
@@ -58,12 +53,13 @@ class Pulse:
# Delay phase: LEDs off between pulses
self.driver.fill(bg_color)
else:
# End of cycle: auto advances colour and loops; manual already
# advanced step at run start for the next beat.
if not preset.a:
break
color_index = (color_index + 1) % max(1, len(colors))
# End of cycle: advance colour for the next run, then loop or stop.
nclr = max(1, len(colors))
color_index = (color_index + 1) % nclr
self.driver.step = color_index
if manual:
self.driver.fill(bg_color)
break
cycle_start = now
yield
continue