Bonjour a tous j'ai découvert l'arduino il y a deux ans .. depuis je réalise quelques montages et j'entame la mécanisation d'un piano acoustique avec des solenoids.
j'ai lu plusieurs sujets divers et la structure de mon projet est bien avancé..
j'utilise la bibliothèque midi pour lire les données recues via le shield midi et les interprétées via 3 Arduino mega.réparties pour les 81 notes de mon piano.
jusque la tout fonctionne presque a part certaines notes qui ne s'éteignent pas.. je pense que cela est du au fameux running status.. qui a été implémenté dans la dernière version de la bibliothèque midi .
malheureusement je n'ai ni trouvé comment utiliser le running status ni l'interprété dans mon code...
je me tourne donc vers vous pour solliciter votre aide.
ci dessous le code que j'utilise actuellement
l'idee serair d'inserer un "case" running status...
#include <MIDI.h>
#include <LiquidCrystal_I2C.h>
static const uint16_t DEBOUNCE_COUNT = 50;
//Déclarations de l'écran
LiquidCrystal_I2C lcd(0x27,16,2);
MIDI_CREATE_DEFAULT_INSTANCE();
byte note;
byte velocity;
byte ctrl;
byte val;
//#define USE_RUNNING_STATUS
void setup()
{
int inMin = 22; // Lowest input pin
int inMax = 53; // Highest input pin
for (int i = inMin; i <= inMax; i++) {
pinMode(i, OUTPUT);
}
// initialisation de l'ecran pour debugage lecture midi
lcd.init();
lcd.init();
lcd.backlight();
lcd.setCursor(0,0);
lcd.print("hello");
delay(1000);
lcd.clear();
// We want to receive messages on all channels
MIDI.begin(MIDI_CHANNEL_OMNI);
MIDI.turnThruOn();
}
void loop()
{
static uint8_t ticks = 0; //je ne sais pas a quoi cela sert
static uint8_t old_ticks = 0; //je ne sais pas a quoi cela sert
// put your main code here, to run repeatedly:
if ( MIDI.read())
{
switch (MIDI.getType())
{
case midi::NoteOn :
{
note=MIDI.getData1();
velocity=MIDI.getData2();
if (note > 20 && note < 53){ //arduino 1 notes 21 à 52
digitalWrite((note + 1), HIGH);
lcd.setCursor(0,1);
lcd.print(note);
lcd.setCursor(5,1);
lcd.print(velocity);
}else{}
note = 0;
velocity = 0;
}
break;
case midi::NoteOff :
{
note=MIDI.getData1();
velocity = MIDI.getData2();
if (note > 20 && note < 53){
digitalWrite((note + 1), LOW);
lcd.setCursor(0,1);
lcd.print(note);
lcd.setCursor(5,1);
lcd.print(velocity);
}else{}
note = 0;
velocity = 0;
}
break;
/* case midi::AfterTouchPoly : // pas encore utilisé
{
lcd.clear();
lcd.setCursor(0,0);
lcd.print("PolyAT:");
lcd.setCursor(8,0);
lcd.print(MIDI.getChannel());
lcd.setCursor(0,1);
lcd.print("Note:");
lcd.setCursor(6,1);
lcd.print(MIDI.getData1());
lcd.setCursor(8,1);
lcd.print("AT:");
lcd.setCursor(12,1);
lcd.println(MIDI.getData2());
}
break;*/
case midi::ControlChange : // sert au canal de pédal douce soustain et note off général
{
ctrl=MIDI.getData1();
val=MIDI.getData2();
peDals(ctrl, val);
ctrl=0;
val=0;
}
break;
/* case midi::ProgramChange :
{
Serial.print("PropChange, chan: ");
Serial.print(MIDI.getChannel());
Serial.print(" program: ");
Serial.println(MIDI.getData1());
}
break;
case midi::AfterTouchChannel :
{
Serial.print("ChanAT, chan: ");
Serial.print(MIDI.getChannel());
Serial.print(" program: ");
Serial.println(MIDI.getData1());
}
break;
case midi::PitchBend :
{
uint16_t val;
Serial.print("Bend, chan: ");
Serial.print(MIDI.getChannel());
// concatenate MSB,LSB
// LSB is Data1
val = MIDI.getData2() << 7 | MIDI.getData1();
Serial.print(" value: 0x");
Serial.println(val, HEX);
}
break;*/
case midi::SystemExclusive : // activé pour débugage mais ne sait pas a quoi cela sert
{
// Sysex is special.
// could contain very long data...
// the data bytes form the length of the message,
// with data contained in array member
uint16_t length;
const uint8_t * data_p;
lcd.setCursor(8,0);
//Serial.print("SysEx, chan: ");
//Serial.print(MIDI.getChannel());
length = MIDI.getSysExArrayLength();
lcd.print("Dx");
data_p = MIDI.getSysExArray();
for (uint16_t idx = 0; idx < length; idx++)
{
lcd.setCursor(10,0);
lcd.print(data_p[idx], HEX);
//Serial.print(" 0x");
}
//Serial.println();
}
break;
/* case midi::TimeCodeQuarterFrame :
{
// MTC is also special...
// 1 byte of data carries 3 bits of field info
// and 4 bits of data (sent as MS and LS nybbles)
// It takes 2 messages to send each TC field,
Serial.print("TC 1/4Frame, type: ");
Serial.print(MIDI.getData1() >> 4);
Serial.print("Data nybble: ");
Serial.println(MIDI.getData1() & 0x0f);
}
break;
case midi::SongPosition :
{
// Data is the number of elapsed sixteenth notes into the song, set as
// 7 seven-bit values, LSB, then MSB.
Serial.print("SongPosition ");
Serial.println(MIDI.getData2() << 7 | MIDI.getData1());
}
break;
case midi::SongSelect :
{
Serial.print("SongSelect ");
Serial.println(MIDI.getData1());
}
break;
case midi::TuneRequest :
{
Serial.println("Tune Request");
}
break;
case midi::Clock :
{
ticks++;
Serial.print("Clock ");
Serial.println(ticks);
}
break;
case midi::Start :
{
ticks = 0;
lcd.clear();
lcd.setCursor(10,0);
lcd.print("Start");
}
break;
case midi::Continue :
{
ticks = old_ticks;
lcd.clear();
lcd.setCursor(10,0);
lcd.print("cont");
}
break;
case midi::Stop :
{
old_ticks = ticks;
lcd.clear();
lcd.setCursor(10,0);
lcd.print("Stop");
}
break;
case midi::ActiveSensing :
{
Serial.println("ActiveSense");
}
break;
case midi::SystemReset :
{
Serial.println("Stopping");
}
break;
case midi::InvalidType :
{
Serial.println("Invalid Type");
}
break;
default:
{
Serial.println();
}
break;
}*/
}
}
}
void peDals(byte ctrl, byte val)
{
lcd.clear();
lcd.setCursor(0,0);
lcd.print(ctrl);
lcd.setCursor(4,0);
lcd.print(val);
int force = LOW;
if (val > 63)
{
force = HIGH;
}
else
{
force = LOW;
}
if (ctrl == 64)
{
digitalWrite(7, force);
} else if (ctrl == 67)
{
digitalWrite(6, force);
} else if (ctrl == 120 || ctrl >= 123 )
{
for (int j = 22; j <= 53; j++) {
digitalWrite(j, LOW);}//all noteoff
}else if (ctrl == 122 && val == 0){
for (int j = 22; j <= 53; j++) {
digitalWrite(j, LOW);}//all noteoff
}else {}
}