I am trying to control motors with MIDI. I do not need help wiring my motors, but I do need help with code. I need MIDI notes to trigger each motor (8 total, one per note), and I want to read the MIDI files (multiple) from an SD card. I have tried using some of the libraries but they seem to be giving me trouble and it is difficult for me to understand where I need to edit those codes because I am not yet at that level. I know the wiring for my motor output is correct and I know the SD card wiring is correct because I can read and control each part on its own through test code. I need help writing code to read and decipher the MIDI data from the card and send each note to a different digital output pin. I do not have a preferred way of doing this and am open to suggestions on micro-controllers and programming. Thanks!
You have developed Your setup in a very good way, likely the best way.
Using Autoformat in the IDE and code tags, </>, when pasting the code would give helpers a good base for further advice.
In general You could focus on reading, understanding and decoding the MIDI data coming from the SD card.
Then splitting the beauties to engage the proper output would not be difficult.
As I don't know the syntax, the code, used by MIDI I can't be more precise. Once worked with Hpgl ......
Thanks! This has been the crux of my problem, namely, figuring out how to read multiple files sequentially from an SD card, and then more problematically, decode the MIDI data from each file into usable serial data, all from one micro-controller.
I've tried a few different methods so at the moment I am trying to stay open to suggestions. Currently at a new "starting over" point if you will ![]()
Also I've been contemplating whether using a teensy board would provide any kind of advantage for this kind of application...opinions?
Here are a couple reference pictures of my test setup, and here is the code I have figured out for now...I am not getting any output from my test LEDs and I am stumped. Please help!
#include <SD.h>
#include <SPI.h>
//create "filename" placeholder variable for files when opened
File songname;
//variables setup////////
//SD pin designations are as follows for arduino mega: MOSI-51, MISO-50, SCK-52, CS-53
const int chipSelect = 53;
//set indexing variable for files
int i = 0;
//create all motor outputs (relay signals (HIGH/LOW))
const int NoteA = 2;
const int NoteB = 3;
const int NoteC = 4;
const int NoteD = 5;
const int NoteE = 6;
const int NoteF = 7;
const int NoteG = 8;
const int statusLed = LED_BUILTIN;
//MIDI pitch values for each "note"
int Aa [ ] = {0, 1, 12, 13, 24, 25, 36, 37, 48, 49, 60, 61, 72, 73, 84, 85, 96, 97, 108, 109, 120, 121}; //22 items in list
int Bb [ ] = {2, 2, 14, 14, 26, 26, 38, 38, 50, 50, 62, 62, 74, 74, 86, 86, 98, 98, 110, 110, 122, 122};
int Cc [ ] = {3, 4, 15, 16, 27, 28, 39, 40, 51, 52, 63, 64, 75, 76, 87, 88, 99, 100, 111, 112, 123, 124};
int Dd [ ] = {5, 6, 17, 18, 29, 30, 41, 42, 53, 54, 65, 66, 77, 78, 89, 90, 101, 102, 113, 114, 125, 126};
int Ee [ ] = {7, 7, 19, 19, 31, 31, 43, 43, 55, 55, 67, 67, 79, 79, 91, 91, 103, 103, 115, 115, 127, 127};
int Ff [ ] = {8, 9, 20, 21, 32, 33, 44, 45, 56, 57, 68, 69, 80, 81, 92, 93, 104, 105, 116, 117, 128, 129};
int Gg [ ] = {10, 11, 22, 23, 34, 35, 46, 47, 58, 59, 70, 71, 82, 83, 94, 95, 106, 107, 118, 119, 130, 131};
byte incomingByte;
byte note;
byte velocity;
int action=2; //0 =note off ; 1=note on ; 2= nada
//create a new array with all song names in a list form (for indexing) ---eventually I will make this a list of all the filenames on SD card
const char* songList [ ] = {"1.mid", "2.mid"};
int songTotal = 1; //number of items in songlist/on SD card
//setup: declaring iputs and outputs and begin serial
void setup() {
pinMode(statusLed,OUTPUT); // declare the LED's pin as output
pinMode(NoteA,OUTPUT);
pinMode(NoteB,OUTPUT);
pinMode(NoteC,OUTPUT);
pinMode(NoteD,OUTPUT);
pinMode(NoteE,OUTPUT);
pinMode(NoteF,OUTPUT);
pinMode(NoteG,OUTPUT);
//CS pin must be left as an output or else SD library functions will not work.
pinMode(chipSelect, OUTPUT);
//start serial with midi baudrate 31250 or 38400 for debugging
Serial.begin(38400);
digitalWrite(statusLed,HIGH);
while (!Serial);
Serial.print("Initializing SD card...");
SD.begin(chipSelect);
}
//loop: wait for serial data, and interpret the message
void loop () {
for (int i = 0; i<=songTotal; i++){
songname = SD.open(songList[i]); //open file - should be smth like this: "songlist[i]"
if (songname){
while (songname.available()) {
//read file in MIDI format to reference callback function below
if (Serial.available() > 0) {
// read the incoming byte:
incomingByte = Serial.read();
// wait for as status-byte, channel 1, note on or off
if (incomingByte== 144){ // note on message starting starting
action=1;
}else if (incomingByte== 128){ // note off message starting
action=0;
}else if (incomingByte== 208){ // aftertouch message starting
//not implemented yet
}else if (incomingByte== 160){ // polypressure message starting
//not implemented yet
}else if ( (action==0)&&(note==0) ){ // if we received a "note off", we wait for which note (databyte)
note=incomingByte;
playNote(note, 0);
note=0;
velocity=0;
action=2;
}else if ( (action==1)&&(note==0) ){ // if we received a "note on", we wait for the note (databyte)
note=incomingByte;
}else if ( (action==1)&&(note!=0) ){ // ...and then the velocity
velocity=incomingByte;
playNote(note, velocity);
note=0;
velocity=0;
action=0;
}else{
//nada
}
}
}
}
songname.close(); //close file
}
i = 0;
}
///////////////////////////////////////////////////////////////////////////
void playNote(byte note, byte velocity){
int value=LOW;
if (velocity >10){
value=HIGH;
}else{
value=LOW;
}
for (int count = 0; count <= 21; count++){
if(note == Aa[count]){
digitalWrite(NoteA, value);
}
if(note == Bb[count]){
digitalWrite(NoteB, value);
}
if(note == Cc[count]){
digitalWrite(NoteC, value);
}
if(note == Dd[count]){
digitalWrite(NoteD, value);
}
if(note == Ee[count]){
digitalWrite(NoteE, value);
}
if(note == Ff[count]){
digitalWrite(NoteF, value);
}
if(note == Gg[count]){
digitalWrite(NoteG, value);
}
else {
}
}
}

