How do I route MIDI events to effect plugin?

I’m developing a plugin that has to behave as an effect plugin, thus I have

#define JucePlugin_IsSynth                          0

defined in JucePluginCharacteristics.h

I noticed that I am not able to receive MIDI messages on many hosts, while I miss none of them if I do configure the plugin as a synth.
Is this the default behaviour for all the hosts out there, or am I just unlucky and I’ve played only with those that seem not to route any MIDI event to effect plugins?

Obviously my configuration already defines the following

#define JucePlugin_WantsMidiInput                   1

but that seem to have no effect on host’s behaviour. Is there some other trick I can play to let the host route events to my effect plugin?

Funny thing is that, although I’m not able to receive any MIDI event, those generated within effect plugin are correctly routed and received from the host.

Howdy! :slight_smile:

Which host are you using…?


At the moment, Cubase 4, Ableton Live 6 and ProTools 7.3, all under Windows.
Only ProTools seemed to work after this trick: after having added the effect to my audio track, I added a MIDI track and redirect its output to the plugin. That way it started working, and even after deleting the MIDI track, events kept to be routed correctly to the plugin the way I meant them to. On the other hosts, I had no such “luck”.

Right, just to make sure I understand correctly, can I please ask what your plug-in wants to do with the MIDI events it receives?

You say “I’m developing a plugin that has to behave as an effect plugin”; does that mean:

  • you want your plug-in to work as a DSP effect (e.g. reverb or whatever) that responsds to incoming MIDI events to e.g. control parameters of your DSP effect? AFAIK, this means that you must have this defined:
    #define JucePlugin_WantsMidiInput 1
    otherwise the host doesn’t bother passing you any MIDI data at all.
  • you want your plug-in to act as a “pure” MIDI effect, i.e. taking MIDI events in, and passing-out only MIDI events (that might or might not have been modified or generated by your plugin)? This requires a different sort of plug-in (a “MIDI Effect”) that I’m currently creating Juce adaptors for…
  • something else?



The case is the first you mentioned, i.e. DSP plugin with MIDI input for “auxiliary” control of parameters.

As written in the first post, the #define you mentioned is already there, but seems to be ignored by VST hosts (that’s why I can do that with ProTools, that uses RTAS format for plugins, and not with Cubase and Ableton).

After having done some searches, the procedure for correctly feeding MIDI events (on all hosts I’m using) to an effect plugin is the same described for ProTools: additional MIDI track whose output should be routed to the audio track/audio effect. The problem now is that my plugin made with JUCE isn’t selectable as a destination for the MIDI track output. I know this is possible to be done because other plugins (MIDI Gate shipped with Cubase, for example) allow that.

It seems that defining JucePlugin_WantsMidiInput doesn’t trigger all the necessary code for VST effect to be seen as potential MIDI receivers.

I solved the problem. Closely looking at the wrapper code (juce_VstWrapper.cpp) revealed the following code:

        if (strcmp (text, "receiveVstEvents") == 0
            || strcmp (text, "receiveVstMidiEvents") == 0)
#if JucePlugin_WantsMidiInput
            result = 1;
            result = -1;
        else if (strcmp (text, "sendVstEvents") == 0
                 || strcmp (text, "sendVstMidiEvent") == 0)
#if JucePlugin_ProducesMidiOutput
            result = 1;
            result = -1;

Sure enough, the string receiveVstMidiEvents should have been receiveVstMidiEvent instead. A little bit of googling aroud revealed the latter to be the correct one.
That’s the reason that made the wrapper fail to report its MIDI receiving capability.
Now everything works fine, but that piece of code needs to be fixed.

Excellent - well spotted!! Hopefully Jules can fix this soon!


Wow - how strange that that one’s never come up before! Maybe some hosts do use the plural version (I bet tracktion does, because I wrote it…), so best to leave that in there - I’ll change it to:

if (strcmp (text, "receiveVstEvents") == 0 || strcmp (text, "receiveVstMidiEvent") == 0 || strcmp (text, "receiveVstMidiEvents") == 0) {

Could it be that some host need the existence of both singular and plural version for sendVstMidiEvent/s too?
Just in case a similar problem happens in the future, better to think about it now than re-dig into the code later…

Yes, certainly doesn’t do any harm to add that one as well.