Last active
April 26, 2023 11:15
-
-
Save GottZ/5e6477eccf36e6eda4f3ffa6b89d4e95 to your computer and use it in GitHub Desktop.
little CircuitPython USB MIDI wrapper for the Adafruit Neo Trinkey SAMD21 USB. It forwards the touch inputs to control channels 1 and 2 and allows setting the LED's according to line
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# for Adafruit Neo Trinkey SAMD21 USB https://www.adafruit.com/product/4870 | |
# code is at: https://gist.github.com/GottZ/5e6477eccf36e6eda4f3ffa6b89d4e95 | |
# revision 4 | |
# | |
# touch pads will send control change events for 1 and 2 with 127 and 0 for their state | |
# when touching both at once, it will emit a control change event with id 3 additionally to 1 and 2 | |
# if you want this with a delay, just remove # for all code lines that have been commented out | |
# | |
# the four neopixel LED's will respond to defined control change events as defined in the midipixels tuple | |
# 10, 20, 30 and 40 describe the led position. 10 is red, 11 is green, 12 is blue, 13 set's rgb to greyscale | |
# 50 is special, it will behave like a led but instead change all led's at once. | |
#import time | |
import board | |
import neopixel | |
import touchio | |
import usb_midi | |
import adafruit_midi | |
from adafruit_midi.midi_message import MIDIMessage | |
from adafruit_midi.control_change import ControlChange | |
# neopixels: | |
pixels = neopixel.NeoPixel(board.NEOPIXEL, 4, brightness=1, auto_write=False) | |
# touch pads: | |
touch1 = touchio.TouchIn(board.TOUCH1) | |
touch2 = touchio.TouchIn(board.TOUCH2) | |
# generic midi boilerplate: | |
midi = adafruit_midi.MIDI( | |
midi_in=usb_midi.ports[0], | |
midi_out=usb_midi.ports[1], | |
in_channel=0, | |
out_channel=0, | |
) | |
# state machines: | |
touch1_pressed = False | |
touch2_pressed = False | |
touch3_pressed = False # both touch inputs together | |
# you may enable these commented out things (also down in the code) to have a delay for the third touch event. | |
#touch1_ev = None | |
#touch2_ev = None | |
#touch3_delay = 0.1 | |
# neopixel midi channels: | |
midipixels = { | |
# bottom right | |
10: (0, 0), # red | |
11: (0, 1), # green | |
12: (0, 2), # blue | |
13: (0, (0, 1, 2)), # white | |
# bottom left | |
20: (1, 0), | |
21: (1, 1), | |
22: (1, 2), | |
23: (1, (0, 1, 2)), | |
# top left | |
30: (2, 0), | |
31: (2, 1), | |
32: (2, 2), | |
33: (2, (0, 1, 2)), | |
# top right | |
40: (3, 0), | |
41: (3, 1), | |
42: (3, 2), | |
43: (3, (0, 1, 2)), | |
# all 4 led's: | |
50: ((0, 1, 2, 3), 0), | |
51: ((0, 1, 2, 3), 1), | |
52: ((0, 1, 2, 3), 2), | |
53: ((0, 1, 2, 3), (0, 1, 2)), | |
} | |
while True: | |
#now = time.monotonic() | |
if touch1_pressed is not touch1.value: | |
touch1_pressed = not touch1_pressed | |
#touch1_ev = (None, now)[touch1_pressed] | |
midi.send(ControlChange(1, (0, 127)[touch1_pressed])) | |
if touch2_pressed is not touch2.value: | |
touch2_pressed = not touch2_pressed | |
#touch2_ev = (None, now)[touch2_pressed] | |
midi.send(ControlChange(2, (0, 127)[touch2_pressed])) | |
#if not touch3_pressed and touch1_pressed and touch2_pressed and (touch1_ev + touch3_delay) < now and (touch2_ev + touch3_delay) < now: | |
if not touch3_pressed and touch1_pressed and touch2_pressed: | |
touch3_pressed = True | |
midi.send(ControlChange(3, 127)) | |
elif touch3_pressed and (not touch1_pressed or not touch2_pressed): | |
touch3_pressed = False | |
midi.send(ControlChange(3, 0)) | |
msg = midi.receive() | |
if msg is None: | |
continue | |
if not isinstance(msg, ControlChange): | |
continue | |
control = msg.control | |
value = msg.value | |
if control not in midipixels: | |
continue | |
(pt, it) = midipixels[control] | |
if type(pt) is not tuple: | |
pt = (pt,) | |
if type(it) is not tuple: | |
it = (it,) | |
for p in pt: | |
for i in it: | |
pixels[p] = pixels[p][0:i] + (value,) + pixels[p][i + 1 : 3] | |
pixels.show() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
20230426_130959.mp4
video showing how it can be used