In this bit
Code:
for (uint8_t voiceNumber = voice1; voiceNumber <= voice4; ++voiceNumber) {
allNotesOff(voiceNumber);
}
The synth may not have completed silencing all notes in voice1 before allNotesOff(voice2) is sent so a delay may be worth playing with.
Ears pricked up after wrestling code for a sequencer for days, just got it working so posting the guts as food for thought.
Code:
void Seq2(int trkIndex) {
// Called by a Timer
// Prepare the sequence
if (TrackData[trkIndex].IsRunning != false) {
if (TrackData[trkIndex].NoteSent == false) {
TrackData[trkIndex].NoteSent = true; // so we don't come back here if the seq is started
if (TrackNoteData[trkIndex][CurrStep[trkIndex]].Active == true) { // the step might have been muted
// this chooses per Track vel or per step vel
if (TrackData[trkIndex].VelByTrack == true) {
byte vel = TrackData[trkIndex].Vel;
MIDI.sendNoteOn(TrackNoteData[trkIndex][CurrStep[trkIndex]].NoteNum, vel, TrackData[trkIndex].MidiChannel);
}
else if (TrackData[trkIndex].VelByTrack != true) {
byte vel = TrackNoteData[trkIndex][CurrStep[trkIndex]].NoteVel;
MIDI.sendNoteOn(TrackNoteData[trkIndex][CurrStep[trkIndex]].NoteNum, vel, TrackData[trkIndex].MidiChannel);
}
}
}
TrackData[trkIndex].TickCount++;
if (TrackData[trkIndex].TickCount == TrackData[trkIndex].NoteLength) {
// yet to add per Track or per Step Note Length
if (TrackNoteData[trkIndex][CurrStep[trkIndex]].Active == true) { // the step might have been muted
MIDI.sendNoteOff(TrackNoteData[trkIndex][CurrStep[trkIndex]].NoteNum, 0, TrackData[trkIndex].MidiChannel);
}
}
}
if (TrackData[trkIndex].TickCount >= 95) { // thinking of 96 ticks per note
TrackData[trkIndex].NoteSent = false;
TrackData[trkIndex].TickCount = 0;
StepCount[trkIndex]++;
CurrStep[trkIndex] = StepCount[trkIndex];
//CurrStep and StepCount have same value here, playing around with FirstStep, LastStep
//and variable Start step. The goal is to be able to create a base to implement Euclidean
//or "normal" linear sequences like eg. Beatstep Pro
// Now, this bit makes us deaf to the Halt command until the current Step is complete
if (TrackData[trkIndex].Halt == true) {
TrackData[trkIndex].IsRunning = false;
}
if (StepCount[trkIndex] > TrackData[trkIndex].LastStep) {
// Now, the Sequence has completed then repeat
TrackData[trkIndex].TickCount = 0;
StepCount[trkIndex] = TrackData[trkIndex].FirstStep;
CurrStep[trkIndex] = StepCount[trkIndex];
}
}
}