Midi een noot verhogen.
20 berichten
• Pagina 1 van 2 • 1, 2
Midi een noot verhogen.
Ik ben nieuw op het forum en ook de Arduino is nieuw voor mij.
Een van mijn hobby's is het bouwen van ongewone muziekinstrumenten. De Arduino kan daar een mooie aanvulling voor zijn.
Na een paar weken zoeken en uitproberen is het mij gelukt een stukje code te maken om de midi in op de midi uit te krijgen.
Maar wat ik uiteindelijk wil, is dat de aangeslagen noot op mijn keyboard, b.v C2 (=key 36) , telkens als ik dezelfde C2 weer opnieuw aansla, de key met 1 verhoogd wordt en dat 6 keer. Dus eerst key 36, dan 37, 38, 39, 40, 41.
Daarna moet C2 weer op key 36 beginnen en weer 6 keer met een waarde 1 verhogen.
Dit schijnt Round Robin te heten. Het is bedoeld om een drumpad bij elke aanslag 6 van geluid te veranderen.
Ik ben al dagen bezig geweest om een for instructie in te voegen, maar ik krijg het niet voor elkaar.
Heeft iemand een suggestie.
Dit is de code die ik heb.
byte commandByte;
byte noteByte;
byte velocityByte;
byte noteOn = 144;
void setup(){
Serial.begin(31250);
}
void checkMIDI(){
do{
if (Serial.available()){
commandByte = Serial.read();//read first byte
noteByte = Serial.read();//read next byte
velocityByte = Serial.read();//read final byte
Serial.write(noteOn);
Serial.write(noteByte);
Serial.write(velocityByte);
noteByte=0;
velocityByte=0;
}
}
while (Serial.available() > 24);//when three bytes available
}
void loop(){
checkMIDI();
delay(100);
}
--------------------------------------------------------------------------------------------
Als ik van Serial.write(noteByte); Serial.write(noteByte +1); maak, werkt dat wel. Vandaar dat ik aan een for instructie dacht.
Alvast hartelijk dank voor de te nemen moeite.
Ik zou er erg blij mee zijn.
Een van mijn hobby's is het bouwen van ongewone muziekinstrumenten. De Arduino kan daar een mooie aanvulling voor zijn.
Na een paar weken zoeken en uitproberen is het mij gelukt een stukje code te maken om de midi in op de midi uit te krijgen.
Maar wat ik uiteindelijk wil, is dat de aangeslagen noot op mijn keyboard, b.v C2 (=key 36) , telkens als ik dezelfde C2 weer opnieuw aansla, de key met 1 verhoogd wordt en dat 6 keer. Dus eerst key 36, dan 37, 38, 39, 40, 41.
Daarna moet C2 weer op key 36 beginnen en weer 6 keer met een waarde 1 verhogen.
Dit schijnt Round Robin te heten. Het is bedoeld om een drumpad bij elke aanslag 6 van geluid te veranderen.
Ik ben al dagen bezig geweest om een for instructie in te voegen, maar ik krijg het niet voor elkaar.
Heeft iemand een suggestie.
Dit is de code die ik heb.
byte commandByte;
byte noteByte;
byte velocityByte;
byte noteOn = 144;
void setup(){
Serial.begin(31250);
}
void checkMIDI(){
do{
if (Serial.available()){
commandByte = Serial.read();//read first byte
noteByte = Serial.read();//read next byte
velocityByte = Serial.read();//read final byte
Serial.write(noteOn);
Serial.write(noteByte);
Serial.write(velocityByte);
noteByte=0;
velocityByte=0;
}
}
while (Serial.available() > 24);//when three bytes available
}
void loop(){
checkMIDI();
delay(100);
}
--------------------------------------------------------------------------------------------
Als ik van Serial.write(noteByte); Serial.write(noteByte +1); maak, werkt dat wel. Vandaar dat ik aan een for instructie dacht.
Alvast hartelijk dank voor de te nemen moeite.
Ik zou er erg blij mee zijn.
Advertisement
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Midi een noot verhogen.
Hey, ik weet niets van Midi maar ik heb even een poging gedaan om een routinetje te schrijven.
de routine incr_note() is toegevoegd, het werkt dus voor elke noot, dus niet specifiek voor noot 36.
aanroepen met : noteByte = incr_note(noteByte, 6);
Wat andere opmerkingen betreffende midi protocol:
Volgens mij moet je controleren op groter of gelijk aan 3 bytes in de input buffer: while (Serial.available() >= 24);//when three bytes available
mischien is hier verwarring ontstaan tussen 3Bytes==24bits.
Je kan de ontvangen bytes :status/command/data , nog controleren door bit 7 te testen, dit kan de robuustheid van je systeem verhogen bij communicatie problemen.
als referentie heb ik gebruikt https://ccrma.stanford.edu/~craig/articles/linuxmidi/misc/essenmidi.html
de routine incr_note() is toegevoegd, het werkt dus voor elke noot, dus niet specifiek voor noot 36.
- Code: Alles selecteren
byte incr_note(byte newkey, byte cnt)
{ static byte notecount = 0; <----- bijhouden hoevaak een key langsgekomen is
static byte prevkey = 255; <----- onthouden welke key dit dan is
if ( newkey == prevkey ) <----- als een nieuwe key gedrukt is en gelijk aan de vorige gedrukt key
{ if (++notecount >= cnt) notecount = 0; <----- verhoog keypress counter van 1 tot max cnt-1
}
else// newkey != prevkey <---- nieuwe noot gaat onaangepast door
{ prevkey = newkey; <---- onthoud deze nieuwe noot
notecount = 0; <---- reset als andere key geweest is
}
return (newkey+notecount);// + 1,2,3,4...(cnt-1)
}
aanroepen met : noteByte = incr_note(noteByte, 6);
Wat andere opmerkingen betreffende midi protocol:
Volgens mij moet je controleren op groter of gelijk aan 3 bytes in de input buffer: while (Serial.available() >= 24);//when three bytes available
mischien is hier verwarring ontstaan tussen 3Bytes==24bits.
Je kan de ontvangen bytes :status/command/data , nog controleren door bit 7 te testen, dit kan de robuustheid van je systeem verhogen bij communicatie problemen.
als referentie heb ik gebruikt https://ccrma.stanford.edu/~craig/articles/linuxmidi/misc/essenmidi.html
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
Re: Midi een noot verhogen.
Hoi astrofrostbyte,
Te gek, ik ga er vanavond mee aan de slag en laat weten wat het geworden is.
Alvast heel erg bedankt.
Te gek, ik ga er vanavond mee aan de slag en laat weten wat het geworden is.
Alvast heel erg bedankt.
Re: Midi een noot verhogen.
astrofrostbyte,
Zoals je beschrijft hoe het zou moeten werken is het nog mooier dan ik bedacht had. Dat geeft me zelfs meer mogelijkheden.
Ik ben een paar uur aan de slag geweest om jouw code in de bestaande code in te voegen, maar ik weet er duidelijk veel te weinig van af, want het lukt me niet.
Wat later op de avond ga ik er weer naar kijken, want het begint me nu te duizelen en dat leidt tot niets.
Ik houd je op de hoogte.
Nogmaals bedankt voor het meedenken.
Zoals je beschrijft hoe het zou moeten werken is het nog mooier dan ik bedacht had. Dat geeft me zelfs meer mogelijkheden.
Ik ben een paar uur aan de slag geweest om jouw code in de bestaande code in te voegen, maar ik weet er duidelijk veel te weinig van af, want het lukt me niet.
Wat later op de avond ga ik er weer naar kijken, want het begint me nu te duizelen en dat leidt tot niets.
Ik houd je op de hoogte.
Nogmaals bedankt voor het meedenken.
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Midi een noot verhogen.
hier de volledig code
De checkMIDI kan iets anders geschreven worden, ik gebruik eigenlijk nooit do-while loops , geen idee waarom. er zat ook twee keer een serial.available in.
Ook een check voor commandbyte toegevoegd
- Code: Alles selecteren
byte commandByte;
byte noteByte;
byte velocityByte;
byte noteOn = 144;
void setup()
{ Serial.begin(31250);
}
//-------------------------------------------------------------
byte incr_note(byte newkey, byte cnt)
{ static byte notecount = 0;
static byte prevkey = 255;
if ( newkey == prevkey )
{ if (++notecount >= cnt) notecount = 0;
}
else// newkey != prevkey
{ prevkey = newkey;
notecount = 0;
}
return (newkey+notecount);
}
//-------------------------------------------------------------
void checkMIDI(){
do
{ if (Serial.available()){
commandByte = Serial.read(); //read 1st byte
noteByte = Serial.read(); //read 2nd byte
velocityByte = Serial.read(); //read final byte
noteByte = incr_note(noteByte, 6);
Serial.write(noteOn);
Serial.write(noteByte);
Serial.write(velocityByte);
noteByte=0;
velocityByte=0;
}
} while (Serial.available() >= 3); //at least 3 bytes available
// while (Serial.available() > 24); //when 25 bytes available
}
//-------------------------------------------------------------
void loop(){
checkMIDI();
delay(10); // <-- deze mog wel wat korter
}
//-------------------------------------------------------------
De checkMIDI kan iets anders geschreven worden, ik gebruik eigenlijk nooit do-while loops , geen idee waarom. er zat ook twee keer een serial.available in.
Ook een check voor commandbyte toegevoegd
- Code: Alles selecteren
void checkMIDI()
{ if (Serial.available() >=3 )
{ if (0x80 && Serial.peek() ) // commandByte?
{ commandByte = Serial.read(); //read 1st byte
noteByte = Serial.read(); //read 2nd byte
velocityByte = Serial.read(); //read final byte
noteByte = incr_note(noteByte, 6);
Serial.write(noteOn);
Serial.write(noteByte);
Serial.write(velocityByte);
noteByte=0;
velocityByte=0;
}
else // No Commandbyte detected !
{ Serial.read(); // dummy read to flush non Command byte
}
}
}//checkMIDI
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
Re: Midi een noot verhogen.
Je bent een kanjer, geweldig dat je dit wilt doen.
Ik ga er mee aan de slag.
Zo leer ik ook het nodige. Super.
Ik ga er mee aan de slag.
Zo leer ik ook het nodige. Super.
Re: Midi een noot verhogen.
Hoi astrofrostbyte,
Helemaal super, het werkt op een klein foutje na. De tonen gaan niet 1 toon omhoog maar 2.
Dus van b.v key 36 - 38 - 40 en dan weer terug 36 - 38 - 40.
Maar verder is dIt wel helemaal top. Dat dit kan met elke noot geeft me super mogelijkheden.
Ik heb na Serial.write(velocityByte en delay van 100 ingevoegd, omdat hij soms bij snel aanslaan zich verslikte, maar dat is nu helemaal in orde.
Binnenkort zal ik op dit een fotoreportage zetten van wat ik aan het bouwen ben.
Super, dit maakt mijn weekend goed.
Helemaal super, het werkt op een klein foutje na. De tonen gaan niet 1 toon omhoog maar 2.
Dus van b.v key 36 - 38 - 40 en dan weer terug 36 - 38 - 40.
Maar verder is dIt wel helemaal top. Dat dit kan met elke noot geeft me super mogelijkheden.
Ik heb na Serial.write(velocityByte en delay van 100 ingevoegd, omdat hij soms bij snel aanslaan zich verslikte, maar dat is nu helemaal in orde.
Binnenkort zal ik op dit een fotoreportage zetten van wat ik aan het bouwen ben.
Super, dit maakt mijn weekend goed.
- astrofrostbyte
- Berichten: 229
- Geregistreerd: 20 Jan 2013, 12:01
Re: Midi een noot verhogen.
mooi,
Dat verhogen van een noot met 2 ipv 1 heeft denk ik te maken met het MIDI protocol.
Zou het kunnen dat een slag op de drumpad twee frames verstuurd ?, één met een NOTE-ON commandbyte[0x9_], en daarna één met een NOTE-OFF commandbyte[0x8_] ?.
Ik heb te weinig ervaring met MIDI, om dit goed te kunnen beoordelen.
Als dat zo is zouden we de routine alleen kunnen uitvoeren bij een NOTE-OFF commando
De code blijft toch een beetje raar, als je een NOTE-ON of NOTE-OFF command ontvangt verstuur je altijd een NOTE-ON commando, en blijkbaar werkt dat
Dat verhogen van een noot met 2 ipv 1 heeft denk ik te maken met het MIDI protocol.
Zou het kunnen dat een slag op de drumpad twee frames verstuurd ?, één met een NOTE-ON commandbyte[0x9_], en daarna één met een NOTE-OFF commandbyte[0x8_] ?.
Ik heb te weinig ervaring met MIDI, om dit goed te kunnen beoordelen.
Als dat zo is zouden we de routine alleen kunnen uitvoeren bij een NOTE-OFF commando
- Code: Alles selecteren
void checkMIDI()
{ if (Serial.available() >=3 )
{ if (0x80 && Serial.peek() ) // commandByte?
{ commandByte = Serial.read();
noteByte = Serial.read();
velocityByte = Serial.read();
if ( noteByte&0xF0 == 0x80) // note-Off commandbyte?
{ noteByte = incr_note(noteByte, 6);
}
Serial.write(noteOn);
Serial.write(noteByte);
Serial.write(velocityByte);
noteByte=0;
velocityByte=0;
}
else // No Commandbyte detected !
{ Serial.read(); // dummy read to flush non Command byte
}
}
}//checkMIDI
De code blijft toch een beetje raar, als je een NOTE-ON of NOTE-OFF command ontvangt verstuur je altijd een NOTE-ON commando, en blijkbaar werkt dat
Gear: Arduino- Uno,Due,Ethernet,Mega2560 , OLS LogicAnalyser, TDS1002, Rigol DG1022, J-Link EDU, BusPirate
Re: Midi een noot verhogen.
Je hebt het er maar druk mee,maar super, dat je dit doet.
Ik heb de nieuwe code ingevoerd, maar nu laat de Arduino telkens de aangeslagen noot door zonder deze te verhogen.
Voor jou op afstand is dat natuurlijk heel lastig omdat je niets kunt proberen. Des te meer mijn waardering.
In ieder geval geeft deze hulp me een zeer goed gevoel.
Ik heb de nieuwe code ingevoerd, maar nu laat de Arduino telkens de aangeslagen noot door zonder deze te verhogen.
Voor jou op afstand is dat natuurlijk heel lastig omdat je niets kunt proberen. Des te meer mijn waardering.
In ieder geval geeft deze hulp me een zeer goed gevoel.
Re: Midi een noot verhogen.
Hoi Round,
In de laatste code van de functie checkMIDI van astrofrostbyte zit een typefoutje waardoor de noot waarde niet meer opgehoogd wordt:
if ( noteByte&0xF0 == 0x80) // note-Off commandbyte?
{ noteByte = incr_note(noteByte, 6);
}
noteByte moet hier commandByte zijn.
Ik ben het met astrofrostbyte eens dat het aanmelden en afmelden hier raar is in je code. Als de ene noot afgemeld zou moeten worden, wordt de volgende aangemeld. Dit betekend dat de noten niet goed afgemeld worden. Bij geluiden die vanzelf uitdempen hoor je niet dat ze niet afgemeld worden.
Volgens mij zou het dus zo moeten werken:
aanmelden key 36 (noteByte) in -> aanmelden key 36 (noteByte) uit
afmelden key 36 in -> afmelden key 36 (noteByte) uit en notecounter ophogen met 1
aanmelden key 36 in -> aanmelden key noteByte + notecounter uit
afmelden key 36 in -> afmelden key noteByte + notecounter uit en notecounter ophogen met 1
aanmelden key 36 in -> aanmelden key noteByte + notecounter uit
afmelden key 36 in -> afmelden key noteByte + notecounter uit en notecounter ophogen met 1
enz. tot de zes keer bereikt zijn en dan de notecounter resetten en ook wanneer er een andere key aangemeld wordt notecounter resetten.
In je code gebruik je bij het aanmelden van de noten altijd MIDI kanaal 1 dit komt door de waarde 144 (0x90). Het laagste nibble (4 bits) is hier altijd 0.
Overigens kan het afgemeld van een noot bij MIDI ook door de noot aan te melden met een velocity waarde van 0.
Dus je zou zowel het afmelden als het aanmelden moeten afhandelen en nog een ander punt is dat alle andere MIDI data zoals volume, program change enz. nu niet worden door gestuurd van de ingang naar de uitgang.
In de laatste code van de functie checkMIDI van astrofrostbyte zit een typefoutje waardoor de noot waarde niet meer opgehoogd wordt:
if ( noteByte&0xF0 == 0x80) // note-Off commandbyte?
{ noteByte = incr_note(noteByte, 6);
}
noteByte moet hier commandByte zijn.
Ik ben het met astrofrostbyte eens dat het aanmelden en afmelden hier raar is in je code. Als de ene noot afgemeld zou moeten worden, wordt de volgende aangemeld. Dit betekend dat de noten niet goed afgemeld worden. Bij geluiden die vanzelf uitdempen hoor je niet dat ze niet afgemeld worden.
Volgens mij zou het dus zo moeten werken:
aanmelden key 36 (noteByte) in -> aanmelden key 36 (noteByte) uit
afmelden key 36 in -> afmelden key 36 (noteByte) uit en notecounter ophogen met 1
aanmelden key 36 in -> aanmelden key noteByte + notecounter uit
afmelden key 36 in -> afmelden key noteByte + notecounter uit en notecounter ophogen met 1
aanmelden key 36 in -> aanmelden key noteByte + notecounter uit
afmelden key 36 in -> afmelden key noteByte + notecounter uit en notecounter ophogen met 1
enz. tot de zes keer bereikt zijn en dan de notecounter resetten en ook wanneer er een andere key aangemeld wordt notecounter resetten.
In je code gebruik je bij het aanmelden van de noten altijd MIDI kanaal 1 dit komt door de waarde 144 (0x90). Het laagste nibble (4 bits) is hier altijd 0.
Overigens kan het afgemeld van een noot bij MIDI ook door de noot aan te melden met een velocity waarde van 0.
Dus je zou zowel het afmelden als het aanmelden moeten afhandelen en nog een ander punt is dat alle andere MIDI data zoals volume, program change enz. nu niet worden door gestuurd van de ingang naar de uitgang.
20 berichten
• Pagina 1 van 2 • 1, 2
Wie is er online?
Gebruikers in dit forum: Geen geregistreerde gebruikers en 7 gasten