Sure. Here is the entire sketch:
#include <SoftwareSerial.h>
#include <MIDI.h>
#include <midi_Defs.h>
#include <midi_Message.h>
#include <midi_Namespace.h>
#include <midi_Settings.h>
extern void handleNoteOn(byte channel, byte pitch, byte velocity);
extern void handleNoteOff(byte channel, byte pitch, byte velocity);
extern void handleStop();
#define N_NOTES 12
const int pins[][3] = {{10, 9, 11}, {5, 3, 6}};
volatile int currentNote[] = {0, 0};
int brightness[] = {0, 0, 0};
const int black[] = {0, 0, 0};
const int red[] = {255, 0, 0};
const int yellow[] = {128, 50, 0};
const int green[] = {0, 200, 0};
const int aqua[] = {0, 100, 128};
const int blue[] = {0, 0, 255};
const int violet[] = {128, 0, 128};
const int gain[] = {100, 170, 150};
int notecolor[N_NOTES][3];
SoftwareSerial softSerial(7,8);
MIDI_CREATE_INSTANCE(SoftwareSerial, softSerial, midiA);
void setup() {
// declare pwm pins to be output:
for (int i=0; i<3; i++) {
pinMode(pins[0][i], OUTPUT);
pinMode(pins[1][i], OUTPUT);
}
for (int i=0; i<N_NOTES; i++) {
calcBrightness((i * 768) / N_NOTES);
copyColor(notecolor[i], brightness);
}
midiA.setHandleNoteOn(handleNoteOn);
midiA.setHandleNoteOff(handleNoteOff);
midiA.setHandleStop(handleStop);
midiA.begin(MIDI_CHANNEL_OMNI);
}
void loop() {
midiA.read();
}
void copyColor(int target[], const int source[]) {
for (int i=0; i<3; i++) {
target[i] = source[i];
}
}
void displayColor(const int pin[], const int color[]) {
analogWrite(pin[0], (color[0] * 100) / gain[0]);
analogWrite(pin[1], (color[1] * 100) / gain[1]);
analogWrite(pin[2], (color[2] * 100) / gain[2]);
}
void calcBrightness(int i)
{
if (i < 128) {
interpolate(red, yellow, 128-i);
} else if (i < 256) {
interpolate(yellow, green, 256-i);
} else if (i < 384) {
interpolate(green, aqua, 384-i);
} else if (i < 512) {
interpolate(aqua, blue, 512-i);
} else if (i < 640) {
interpolate(blue, violet, 640-i);
} else if (i < 768) {
interpolate(violet, red, 768-i);
}
}
void interpolate(const int *c1, const int *c2, int i)
{
int c;
for (c = 0; c<3; c++) {
brightness[c] = (c1[c] * i + c2[c] * (128 - i)) / 128;
}
}
void handleNoteOn(byte channel, byte pitch, byte velocity)
{
int p, ch;
if (channel <= 2) {
ch = channel - 1;
if (ch >= 0) {
p = pitch % N_NOTES;
currentNote[ch] = pitch;
displayColor(pins[ch], notecolor[p]);
}
}
}
void handleNoteOff(byte channel, byte pitch, byte velocity)
{
int ch;
if (channel <= 2) {
ch = channel - 1;
if (ch >= 0) {
if (currentNote[ch] == pitch) {
displayColor(pins[ch], black);
}
}
}
}
void handleStop()
{
for (int i=0; i<2; i++) {
displayColor(pins[i], black);
currentNote[i] = 0;
}
}