# adapted from:
# https://github.com/Guitarman9119/Raspberry-Pi-Pico-/blob/main/MIDI%20and%20Macropad%20Project/MIDI.py
# https://www.youtube.com/watch?v=3nKlVuwITiM&ab_channel=NerdCave
import time
import board
import terminalio
import busio
import digitalio
import usb_midi
import adafruit_midi
from adafruit_midi.note_on import NoteOn
from adafruit_midi.note_off import NoteOff
root = 0
third = 0
fifth = 0
seventh = 0
# MIDI setup as MIDI out device
midiChords = adafruit_midi.MIDI(midi_out=usb_midi.ports[1], out_channel=0)
midiMelody = adafruit_midi.MIDI(midi_out=usb_midi.ports[1], out_channel=0)
note_pins = [board.GP0, board.GP13, board.GP14, board.GP15, board.GP17]
note_buttons = []
for pin in note_pins:
note_pin = digitalio.DigitalInOut(pin)
note_pin.direction = digitalio.Direction.INPUT
note_pin.pull = digitalio.Pull.DOWN
note_buttons.append(note_pin)
# note states
note0_pressed = False
note1_pressed = False
note2_pressed = False
note3_pressed = False
note4_pressed = False
# array of note states
note_states = [note0_pressed,
note1_pressed,
note2_pressed,
note3_pressed,
note4_pressed]
# array of default MIDI notes
midi_notes = [60, 61, 62, 63, 64]
lastAttack = 0
def playChord(root, intervals, startTime, duration, currentTime):
global lastAttack
if currentTime > startTime and currentTime < startTime + duration and lastAttack < currentTime - duration:
midi_notes[0] = root
if len(intervals) > 0:
midi_notes[1] = root + intervals[0]
midiChords.send(NoteOn(midi_notes[1], 120))
if len(intervals) > 1:
midi_notes[2] = root + intervals[1]
midiChords.send(NoteOn(midi_notes[2], 120))
if len(intervals) > 2:
midi_notes[3] = root + intervals[2]
midiChords.send(NoteOn(midi_notes[3], 120))
lastAttack = currentTime
else:
midiChords.send(NoteOff(midi_notes[0], 120))
if len(intervals) > 0:
midiChords.send(NoteOff(midi_notes[1], 120))
if len(intervals) > 1:
midiChords.send(NoteOff(midi_notes[2], 120))
if len(intervals) > 2:
midiChords.send(NoteOff(midi_notes[3], 120))
def majorChord(root, startTime, duration, currentTime):
intervals = [4, 7, 11]
playChord(root, intervals, startTime, duration, currentTime)
def minorChord(root, startTime, duration, currentTime):
intervals = [3, 7, 10]
playChord(root, intervals, startTime, duration, currentTime)
def dominantChord(root, startTime, duration, currentTime):
intervals = [4, 7, 10]
playChord(root, intervals, startTime, duration, currentTime)
def majorTriad(root, startTime, duration, currentTime):
intervals = [4, 7, 12]
playChord(root, intervals, startTime, duration, currentTime)
def minorTriad(root, startTime, duration, currentTime):
intervals = [3, 7, 12]
playChord(root, intervals, startTime, duration, currentTime)
D = 62
C = 60
G = 55
A = 57
F = 53
E = 52
initialTime = time.monotonic()
duration = 1
while True:
# MIDI input
for i in range(5):
buttons = note_buttons[i]
# if button is pressed...
if buttons.value:
print('hello')
if buttons.value and note_states[i] is True:
# send the MIDI note and light up the LED
midiMelody.send(NoteOn(midi_notes[i], 120))
note_states[i] = False
print(midi_notes[i])
# if the button is released...
if not buttons.value and note_states[i] is False:
# stop sending the MIDI note and turn off the LED
midiMelody.send(NoteOff(midi_notes[i], 120))
note_states[i] = True
currentTime = time.monotonic()
minorChord(A, initialTime, 2 * duration, currentTime)
minorChord(D, initialTime + 2 * duration, 2 * duration, currentTime)
dominantChord(G, initialTime + 4 * duration, 2 * duration, currentTime)
majorChord(C, initialTime + 6 * duration, 2 * duration, currentTime)
majorTriad(F, initialTime + 8 * duration, 2 * duration, currentTime)
minorTriad(D, initialTime + 10 * duration, 2 * duration, currentTime)
majorTriad(E, initialTime + 12 * duration, 2 * duration, currentTime)
minorTriad(A, initialTime + 14 * duration, 2 * duration, currentTime)
dominantChord(A, initialTime + 15 * duration, 2 * duration, currentTime)
if currentTime > initialTime + 16 * duration:
initialTime = currentTime