diff --git a/src/patterns.py b/src/patterns.py index 1cf7509..502e382 100644 --- a/src/patterns.py +++ b/src/patterns.py @@ -37,6 +37,7 @@ class Patterns(PatternsBase): "rainbow": self.rainbow, "pulse": self.pulse, "transition": self.transition, + "chase": self.n_chase, "n_chase": self.n_chase, "circle": self.circle, } @@ -48,7 +49,8 @@ class Patterns(PatternsBase): state = True # True = on, False = off last_update = utime.ticks_ms() - while self.running: + # Only continue running this pattern while it is the selected one + while self.running and self.selected == "blink": current_time = utime.ticks_ms() if utime.ticks_diff(current_time, last_update) >= self.delay: if state: @@ -80,11 +82,12 @@ class Patterns(PatternsBase): return # Auto is True: run continuously - sleep_ms = max(1, int(self.delay)) last_update = utime.ticks_ms() - while self.running: + # Only continue running this pattern while it is the selected one + while self.running and self.selected == "rainbow": current_time = utime.ticks_ms() + sleep_ms = max(1, int(self.delay)) # Access delay directly if utime.ticks_diff(current_time, last_update) >= sleep_ms: for i in range(self.num_leds): rc_index = (i * 256 // self.num_leds) + step @@ -118,7 +121,8 @@ class Patterns(PatternsBase): min_write_time_ms = (self.num_leds * 30) // 1000 + 1 # Convert µs to ms, add 1ms overhead update_interval = max(10, min_write_time_ms + 4) # At least 10ms, add margin for safety - while self.running: + # Only continue running this pattern while it is the selected one + while self.running and self.selected == "pulse": cycle_start = utime.ticks_ms() # Get the current color from the cycle @@ -167,7 +171,8 @@ class Patterns(PatternsBase): # Ensure the cycle takes exactly delay milliseconds before restarting if self.running: self.off() - wait_until = utime.ticks_add(cycle_start, self.delay) + delay_ms = int(self.delay) # Access delay directly + wait_until = utime.ticks_add(cycle_start, delay_ms) while self.running and utime.ticks_diff(wait_until, utime.ticks_ms()) > 0: pass @@ -189,7 +194,7 @@ class Patterns(PatternsBase): if len(self.colors) == 1: # Only one color, just stay that color last_update = utime.ticks_ms() - while self.running: + while self.running and self.selected == "transition": current_time = utime.ticks_ms() if utime.ticks_diff(current_time, last_update) >= 100: self.fill(self.apply_brightness(self.colors[0])) @@ -206,17 +211,18 @@ class Patterns(PatternsBase): self.stopped = True return - transition_duration = max(10, self.delay) # At least 10ms - update_interval = max(10, transition_duration // 50) # Update every ~2% of transition - - # Transition from color1 to color2 - color1 = self.colors[0] - color2 = self.colors[1] - transition_start = utime.ticks_ms() last_update = transition_start - while self.running and utime.ticks_diff(utime.ticks_ms(), transition_start) < transition_duration: + while self.running: + # Access delay and colors directly for live updates + transition_duration = max(10, int(self.delay)) # At least 10ms + update_interval = max(10, transition_duration // 50) # Update every ~2% of transition + color1 = self.colors[0] if len(self.colors) > 0 else (0, 0, 0) + color2 = self.colors[1] if len(self.colors) > 1 else color1 + + if utime.ticks_diff(utime.ticks_ms(), transition_start) >= transition_duration: + break now = utime.ticks_ms() if utime.ticks_diff(now, last_update) >= update_interval: # Calculate interpolation factor (0.0 to 1.0) @@ -239,10 +245,12 @@ class Patterns(PatternsBase): # Auto is True: cycle through all colors continuously color_index = 0 - transition_duration = max(10, self.delay) # At least 10ms - update_interval = max(10, transition_duration // 50) # Update every ~2% of transition - while self.running: + # Auto is True: cycle through all colors continuously + while self.running and self.selected == "transition": + # Access colors directly for live updates + if not self.colors: + break # Get current and next color current_color = self.colors[color_index % len(self.colors)] next_color = self.colors[(color_index + 1) % len(self.colors)] @@ -251,7 +259,13 @@ class Patterns(PatternsBase): transition_start = utime.ticks_ms() last_update = transition_start - while self.running and utime.ticks_diff(utime.ticks_ms(), transition_start) < transition_duration: + while self.running: + # Access delay directly for live updates + transition_duration = max(10, int(self.delay)) # At least 10ms + update_interval = max(10, transition_duration // 50) # Update every ~2% of transition + + if utime.ticks_diff(utime.ticks_ms(), transition_start) >= transition_duration: + break now = utime.ticks_ms() if utime.ticks_diff(now, last_update) >= update_interval: # Calculate interpolation factor (0.0 to 1.0) @@ -280,28 +294,43 @@ class Patterns(PatternsBase): self.stopped = False self.running = True - if len(self.colors) < 2: - # Need at least 2 colors + if len(self.colors) < 1: + # Need at least 1 color self.running = False self.stopped = True return - n1 = max(1, int(self.n1)) # LEDs of color 0 - n2 = max(1, int(self.n2)) # LEDs of color 1 - n3 = int(self.n3) # Step movement on odd steps (can be negative) - n4 = int(self.n4) # Step movement on even steps (can be negative) - - segment_length = n1 + n2 + segment_length = 0 # Will be calculated in loop position = 0 # Current position offset step_count = 0 # Track which step we're on - color0 = self.apply_brightness(self.colors[0]) - color1 = self.apply_brightness(self.colors[1]) - - transition_duration = max(10, self.delay) last_update = utime.ticks_ms() - while self.running: + # Only continue running this pattern while it is the selected one + # Note: this pattern can be selected as "n_chase" or "chase" + while self.running and self.selected in ("n_chase", "chase"): + # Access colors, delay, and n values directly for live updates + if not self.colors: + break + # If only one color provided, use it for both colors + if len(self.colors) < 2: + color0 = self.colors[0] + color1 = self.colors[0] + else: + color0 = self.colors[0] + color1 = self.colors[1] + + color0 = self.apply_brightness(color0) + color1 = self.apply_brightness(color1) + + n1 = max(1, int(self.n1)) # LEDs of color 0 + n2 = max(1, int(self.n2)) # LEDs of color 1 + n3 = int(self.n3) # Step movement on odd steps (can be negative) + n4 = int(self.n4) # Step movement on even steps (can be negative) + + segment_length = n1 + n2 + transition_duration = max(10, int(self.delay)) + current_time = utime.ticks_ms() if utime.ticks_diff(current_time, last_update) >= transition_duration: # Clear all LEDs @@ -361,7 +390,8 @@ class Patterns(PatternsBase): phase = "growing" # "growing", "shrinking", or "off" - while self.running: + # Only continue running this pattern while it is the selected one + while self.running and self.selected == "circle": current_time = utime.ticks_ms() # Clear all LEDs