So, I wondered if I’m way off track and thought I’d try to use a MidiMessageCollector to transpose the MIDI by 5 semitones. Here is the code I tried, for more detail see the aforementioned post:
[code] const int notenum = midi_message.getNoteNumber();
const uint8 velocity = midi_message.getVelocity();
const int channel = midi_message.getChannel();
//Transposing by 5 semitones:
int oldNote = notenum;
int newNote = notenum+5;
//_newNoteNumber = newNote;
MidiMessageCollector* collect = new MidiMessageCollector();
juce::MidiMessage noteOff(juce::MidiMessage::noteOff(channel, oldNote));
juce::MidiMessage noteOn(juce::MidiMessage::noteOn(channel, newNote, velocity));
collect->removeNextBlockOfMessages(output, buffer.getNumSamples());
collect->addMessageToQueue (noteOff);
collect->addMessageToQueue(noteOn);
[/code]
I thought this would ‘kill’ the old note and replace it with the transposed note. It doesn’t work. Which approach should I use for transposition/ why doesn’t this code work? How do I ‘add’ the queue to midimessages or does this happen automatically?
I’d appreciate any helpful answer. Apologies for my NOOBish questions.
Trying to kill a note and adding a new one sounds like a bad idea. A note off is just a note message with velocity 0, and adding note offs like that would also kill any playing notes that were transposed to that same pitch.
I have no experience with this either but I think what you want to do is something like:
create a MidiBuffer
iterate over the input buffer. For example look at MidiOutput cpp file
[code]MidiBuffer::Iterator i (buffer);
const uint8* data;
int len, time;
while (i.getNextEvent (data, len, time))
{
}[/code]
use this data to create MidiMessage instances.
use isNoteOn() / isNoteOff() to find the messages which represent midi note on/off, leaving others in tact
if note message, use getNoteNumber() and setNoteNumber() to read and transpose the pitches
add the messages to your buffer, if messages are not note on/off add them to your buffer unaltered
copy the buffer to the input buffer, overwriting all data.
You probably have to do something with timestamps as well to make sure that you add all the messages to the new buffer with the same timestamp as they were existing in your original buffer.
For future reference for anybody who may struggle while testing an Audio Unit with transposition, the problem was not my code but the AU format. The following code easily changes a note when using a VST in a host but the Audio Unit doesn’t work as it cannot send MIDI to the host.