Since the badge has built-in NeoPixels, let's animate them.
brightness = 0.2 direction = 1 speed = 1 # Define the NeoPixel neopixels = neopixel.NeoPixel( board.NEOPIXEL, NEOPIXEL_COUNT, brightness=settings["brightness"], auto_write=False, pixel_order=neopixel.GRB, ) # Remap the calculated rotation to 0 - 255 def remap(vector): return int(((255 * vector + 85) * 0.75) + 0.5) # Calculate the Hue rotation starting with Red as 0 degrees def rotate(degrees): cosA = cos(radians(degrees)) sinA = sin(radians(degrees)) red = cosA + (1.0 - cosA) / 3.0 green = 1./3. * (1.0 - cosA) + sqrt(1./3.) * sinA blue = 1./3. * (1.0 - cosA) - sqrt(1./3.) * sinA return (remap(red), remap(green), remap(blue)) palette = [] pixels = [] # Generate a rainbow palette for degree in range(0, 360): color = rotate(degree) palette.append(color[0] << 16 | color[1] << 8 | color[2]) # Create the Pattern for x in range(0, NEOPIXEL_COUNT): pixels.append(x * 360 // NEOPIXEL_COUNT) while True: for color in range(0, 360, speed): for index in range(0, NEOPIXEL_COUNT): palette_index = pixels[index] + color * direction if palette_index >= 360: palette_index -= 360 elif palette_index < 0: palette_index += 360 neopixels[index] = palette[palette_index] neopixels.show() neopixels.brightness = brightness
This can be broken down. Let's look at each section.
We will begin by including NEOPIXEL_COUNT
, which was discussed in the previous section. Next, we set the default brightness, which is a float
value between 0.0 and 1.0, the direction which will be either 1 or -1, and the speed which has to be a positive int
or integer. Finally, we define the NeoPixel object.
NEOPIXEL_COUNT = 5 brightness = 0.2 direction = 1 speed = 1 # Define the NeoPixel neopixels = neopixel.NeoPixel( board.NEOPIXEL, NEOPIXEL_COUNT, brightness=settings["brightness"], auto_write=False, pixel_order=neopixel.GRB, )
In the next section we define a couple of functions that do the math for generating the rainbow palette. The rotate()
function does most of the work and takes in a number between 0 and 360 degrees, with 0 degrees being red, and performs calculations to get the red, blue, and green component values. The values are then remapped with the remap()
function to be between 0 and 255.
# Remap the calculated rotation to 0 - 255 def remap(vector): return int(((255 * vector + 85) * 0.75) + 0.5) # Calculate the Hue rotation starting with Red as 0 degrees def rotate(degrees): cosA = cos(radians(degrees)) sinA = sin(radians(degrees)) red = cosA + (1.0 - cosA) / 3.0 green = 1./3. * (1.0 - cosA) + sqrt(1./3.) * sinA blue = 1./3. * (1.0 - cosA) - sqrt(1./3.) * sinA return (remap(red), remap(green), remap(blue))
In the next section, we pre-calculate the red, blue, and green components of each of the colors so that we don't need to do as much math during the animation sequence and add them into a palette array. For the pattern, we are really just trying to choose some numbers that are distributed evenly.
palette = [] pixels = [] # Generate a rainbow palette for degree in range(0, 360): color = rotate(degree) palette.append(color[0] << 16 | color[1] << 8 | color[2]) # Create the Pattern for x in range(0, NEOPIXEL_COUNT): pixels.append(x * 360 // NEOPIXEL_COUNT)
Finally, we get to the main loop and do a simple palette rotation. We do this by going through all of the degrees in the color wheel. Depending on the speed, we may skip a few steps to make it go faster. We simply need to get the index of the color we want in the palette that we had pre-calculated.
We can change the direction by making the index a negative number, which is then adjusted to be within the range of 0-360 and we have our index. We look up the color by providing the index to the palette and then assign the color to the neopixel.
We also set the brightness of the NeoPixels here in case we changed it.
while True: for color in range(0, 360, speed): for index in range(0, NEOPIXEL_COUNT): palette_index = pixels[index] + color * direction if palette_index >= 360: palette_index -= 360 elif palette_index < 0: palette_index += 360 neopixels[index] = palette[palette_index] neopixels.show() neopixels.brightness = brightness
Page last edited March 08, 2024
Text editor powered by tinymce.