- Q: How should I communicate between the 'Processing' and the 'User Interface'?
- Q: I want to implement an audio meter in my user interface. How do I do this?
- Q: How does the host send automation data to my VST 3 plug-in?
- Q: How report to the host that the plug-in has new parameter titles?
- Q: How receive MIDI Controllers from the host?
- Q: How are my parameter changes (from UI interaction) sent to the processor if the host does not process?
With the term 'Processing' we mean the code implementing the Steinberg::Vst::IAudioProcessor interface, and with 'User Interface' the editor component implementing the Steinberg::Vst::IEditController interface.
If you need to communicate the changes of parameters to the user interface, such as metering changes and peaks, you need to define the parameter as an exported type. The parameter then is associated with an ID. In the process function you can inform the host of changes by using the outputParameterChanges (from ProcessData). You add the parameter (ID) to a list that will be used by the host to send them back to the user interface at the correct time.
If you should need to exchange more data than just parameter changes, such as tempo, sample rate, FFT, Pitch Analysis, or any other data resulting from your processing, you can use the IMessage interface (see AGain example). However, you need to be careful and send the data from a 'timer' thread and not directly from the process function, for example, when sending from a 'process' call.
Automation data is sent to the audio processing method as part of the data passed as a parameter to the IAudioProcessor::process (processData) method.
IParameterChanges* paramChanges = processData.inputParameterChanges;
Automation data is transmitted as a list of parameter changes. This list always contains enough information to transmit the original automation curve from the host in a sample-accurate way. Check the AGain example to see how it can be implemented.
See also Parameters and Automation.
Due to preset loading or user interaction the plug-in may change its parameters names (title) (but not the number of them or their IDs). To inform the host about this change, the plug-in should call from the editController its component handler function restartComponent with flag kParamTitlesChanged:
The host will rescan the parameter list and update the titles.
With the flag kParamValuesChanged only the parameters values will be updated.
MIDI controllers are not transmitted directly to a VST component. MIDI as a hardware protocol has restrictions that can be avoided in software. Controller data in particular come along with unclear and often ignored semantics. On top of this, they can interfere with regular parameter automation, and the host is unaware of what happens in the plug-in when passing MIDI controllers directly.
So any functionality that is to be controlled by MIDI controllers must be exported as a regular parameter. The host will transform incoming MIDI controller data using this interface and transmit them as a normal parameter change. This allows the host to automate them in the same way as other parameters.
To inform the host about this MIDI CCs to plug-in parameters mapping, the plug-in should implement the IMidiMapping interface. If the mapping has changed, the plug-in should call IComponentHandler::restartComponent (kMidiCCAssignmentChanged) to inform the host about this change.
Q: How are my parameter changes (from UI interaction) sent to the processor if the host does not process?
When a parameter is changed in the plug-in UI by user action, the plug sends this change to the host with performEdit (do not forget to call beginEdit and endEdit), then the host has the responsibility to transfer this parameter change to the processor part:
- if the audio engine is running (playing), this will be done in the next available process call.
- if the audio engine is not running and the plug-in is activated (enabled), the host has to flush parameter changes from time to time by sending them to the processor by calling process (with audio buffer set to nullptr), in this case the plug-in should only update the parameters changes without processing any audio. It is very important that the host supports this flush mechanism; otherwise, when saving plug-ins state (project/preset) the host will not get the correct updated one.