The neotrellis_keypad.py module encapsulates the actions that happen when a key is pressed. A client application need only call setup_keypad() and then in the forever loop, call trellis.sync(). Internally, the doKey() function is associated with each of 16 keys on the neotrellis, and is activated
After the required imports there are a couple module variables. keyColors is an array of Color, one for each of the 16 keys (hopefully, we dont check size, etc). keyAnimations is likewise an array associating each key with an animation.
The setup_keypad() function fills in the globals and sets all 16 neotrellis keys to call doKey() when they are pressed and again when released.
from adafruit_neotrellis.neotrellis import NeoTrellis
import adafruit_led_animation.color as Color
# local modules
import onboard_neopixel
import neotrellis_animations
keyColors = None
keyAnimations = None
__trellis = None
# could be module but short enough for inline
# arrays to map key index to animation and colors
def setup_keypad(trellis):
global keyColors
global keyAnimations
global __trellis
__trellis = trellis
keyColors = neotrellis_animations.rainbowPalette
keyAnimations = neotrellis_animations.trellisAnimations
# associate 16 trellis keys with doKey() for both press and release
for i in range(16):
# activate rising edge events on all keys; key pressed
__trellis.activate_key(i, NeoTrellis.EDGE_RISING)
# activate falling edge events on all keys; key released
__trellis.activate_key(i, NeoTrellis.EDGE_FALLING)
# set all keys to trigger the doKey() callback
__trellis.callbacks[i] = doKey
# --------------- Ready for Main Loop ------------
# but first lets print out the key colors
print("key colors", keyColors)
for clr in keyColors:
print(hex(clr), end=", ")
print("")
The doKey() is a callback function. It is triggered by trellis.sync() and given an event. The event holds a couple entries of interest: edge and number. Depending on whether event.edge shows key was just pressed or just released, we do different actions.
On key press, we set the onboard_neopixel to the key's associated color - by indexing keyColors[] with the event.number. The current animation is frozen (stops updating on animations.animate() call in forever loop). We black out all 16 pixels and set the key's pixel to its keyColor. Lastly, we blink the onboard pixel, which introduces a blocking delay. May want to remove that for a responsive application.
Nothing changes while the key is held down, but when it is released, we set the current_animation to the key's associated keyAnimation. It will be run on then next animate() call in forever loop.
Pretty simple. Fairly straight forward to modify for future functions. Like, maybe, send a midi note like the Astral TV rPi Pico midi remote did?
# doKey() will be called when button events are received
def doKey(event):
print("\nKeyEvent: ", str(event), " event number",event.number, " edge:",event.edge)
if event.edge == NeoTrellis.EDGE_RISING:
# pressed: toggle, stop/freeze current animation, color my pixel
onboard_neopixel.on_board_neopixel[0] = keyColors[event.number]
#toggleOnBoardPixel()
# freeze current animation, set all to black, just the one to its keyColor
neotrellis_animations.freeze()
__trellis.pixels.fill(Color.BLACK)
__trellis.pixels[event.number] = keyColors[event.number]
print("pixel color", hex(keyColors[event.number]))
__trellis.pixels.show()
# blink onboard with same color
onboard_neopixel.blinkOnBoardPixel(keyColors[event.number])
# start animationwhen a falling edge is detected
elif event.edge == NeoTrellis.EDGE_FALLING:
#toggleOnBoardPixel()
onboard_neopixel.on_board_neopixel[0] = Color.BLACK
__trellis.pixels.fill(Color.BLACK)
#trellis.pixels[event.number] = Color.BLACK
neotrellis_animations.set_animation_byIndex(event.number)
neotrellis_animations.current_animation.resume()
print("new animation", neotrellis_animations.current_animation)
Discussions
Become a Hackaday.io Member
Create an account to leave a comment. Already have an account? Log In.