/ examples / led_animation.py
led_animation.py
 1  # SPDX-FileCopyrightText: 2024 Jeff Epler, written for Adafruit Industries
 2  # SPDX-FileCopyrightText: 2021 Scott Shawcroft, written for Adafruit Industries
 3  #
 4  # SPDX-License-Identifier: MIT
 5  
 6  import time
 7  
 8  import adafruit_pioasm
 9  import adafruit_pixelbuf
10  import adafruit_rp1pio
11  import board
12  from adafruit_led_animation.animation.rainbow import Rainbow
13  from adafruit_led_animation.animation.rainbowchase import RainbowChase
14  from adafruit_led_animation.animation.rainbowcomet import RainbowComet
15  from adafruit_led_animation.animation.rainbowsparkle import RainbowSparkle
16  from adafruit_led_animation.sequence import AnimationSequence
17  
18  # chosen because it's on a connector on the braincraft hat
19  NEOPIXEL = board.D13
20  
21  # NeoPixels are 800khz bit streams. We are choosing zeros as <312ns hi, 936 lo>
22  # and ones as <700 ns hi, 556 ns lo>.
23  # The first two instructions always run while only one of the two final
24  # instructions run per bit. We start with the low period because it can be
25  # longer while waiting for more data.
26  program = """
27  .program ws2812
28  .side_set 1
29  .wrap_target
30  bitloop:
31     out x 1        side 0 [6]; Drive low. Side-set still takes place before instruction stalls.
32     jmp !x do_zero side 1 [3]; Branch on the bit we shifted out previous delay. Drive high.
33   do_one:
34     jmp  bitloop   side 1 [4]; Continue driving high, for a one (long pulse)
35   do_zero:
36     nop            side 0 [4]; Or drive low, for a zero (short pulse)
37  .wrap
38  """
39  
40  assembled = adafruit_pioasm.assemble(program)
41  
42  
43  class Pi5Pixelbuf(adafruit_pixelbuf.PixelBuf):
44      def __init__(self, pin, size, **kwargs):
45          self._pin = pin
46          self.sm = adafruit_rp1pio.StateMachine(
47              assembled,
48              frequency=12_800_000,  # to get appropriate sub-bit times in PIO program
49              first_sideset_pin=pin,
50              auto_pull=True,
51              out_shift_right=False,
52              pull_threshold=8,
53          )
54          #print("real frequency", self.sm.frequency)
55          super().__init__(size=size, **kwargs)
56  
57      def _transmit(self, buf):
58          self.sm.write(buf)
59  
60  pixels = Pi5Pixelbuf(NEOPIXEL, 120, auto_write=True, byteorder="BGR")
61  
62  pixels.fill(0x10102)
63  pixels.show()
64  time.sleep(2)
65  
66  rainbow = Rainbow(pixels, speed=0.02, period=2)
67  rainbow_chase = RainbowChase(pixels, speed=0.02, size=5, spacing=3)
68  rainbow_comet = RainbowComet(pixels, speed=0.02, tail_length=7, bounce=True)
69  rainbow_sparkle = RainbowSparkle(pixels, speed=0.02, num_sparkles=15)
70  
71  
72  animations = AnimationSequence(
73      rainbow,
74      rainbow_chase,
75      rainbow_comet,
76      rainbow_sparkle,
77      advance_interval=5,
78      auto_clear=True,
79  )
80  
81  try:
82      while True:
83          animations.animate()
84  finally:
85      time.sleep(.01)
86      pixels.fill(0)
87      pixels.show()