All posts series:
Part 1. Introduction and setupPart 2. Learning CodePart 3. VST and AUPart 4. Digital DistortionPart 5. Presets and GUIPart 6. Signal synthesisPart 7. Receive MIDI MessagesPart 8. Virtual KeyboardPart 9. EnvelopesPart 10. Refinement GUIPart 11. FilterPart 12. Low-frequency oscillatorPart 13. RedesignPart 14. Polyphony 1Part 15. Polyphony 2Part 16. Antialiasing
Let's add some presets for the plugin and create a [relatively] nice interface.
Presets
Preset - this is the setting that allows you to store specific values ​​of the parameters. At the moment, in our code, presets consist of names and values ​​for all parameters, but, as we will see later, other data can be stored here. Presets are sometimes called programs.
First, let's make the GUI window wider. Change the corresponding constant in
resource.h :
')
In
DigitalDistortion.h, we will declare a
private
member function of the class:
private: double mThreshold; void CreatePresets(); DigitalDistortion.cpp void DigitalDistortion::CreatePresets() { MakePreset("clean", 100.0); MakePreset("slightly distorted", 80.0); MakePreset("woooo", 40.0); MakePreset("waaaa", 20.0); MakePreset("buzzz!!!", 0.01); }
MakePreset
takes the preset name and values ​​for all parameters as arguments. The order of the arguments is defined in
enum EParams
at the top of the file.
Note that the parameter values ​​vary from 0 to 100, not from 0 to 1. These values ​​refer to the
kThreshold
parameter, not to the
mThreshold
variable.
Instead of calling the
MakeDefaultPreset
function at the end of the constructor, write a call to
CreatePresets
:
DigitalDistortion::DigitalDistortion(IPlugInstanceInfo instanceInfo) : IPLUG_CTOR(kNumParams, kNumPrograms, instanceInfo), mThreshold(1.) {
Finally, we need to change the constant that is passed when the base class constructor is called (this is somewhere around the 13th line):
const int kNumPrograms = 5;
If the value of this constant is greater than the actual number of presets, the rest will simply be called “Empty”.
Run the build of VST2. You may have to remove the plugin from the track and reload it in order for the freshly written presets to appear. They can be changed using the drop-down list, which is located directly above the plug-in GUI. Try different - the handle rotates according to the value in the preset.
I remind you that
OnParamChange
is called when each parameter changes.
To the right of the drop-down menu there is a button that opens the presets menu:

Try renaming the preset and twisting the knob. Its position will not be remembered if you remove the plugin from the track and load it again. To save this data, click the
“Export VST patch / bank file (.fxp / .fxb) ...” and save the
test.fxb file to your desktop. Now remove the plugin, add it again and load this file with the settings.
VST plug-ins for storing a separate preset use
FXP format, and
FXB for storing a bank of presets.
Run the target AU (you may first have to go to the Edit Scheme so that it runs along with the host). REAPER defaults to “No preset”, but in the drop-down list all the presets are in place and everything works as it should. Saving presets in the plugin works differently - we cannot import and export preset banks. The processes of saving / loading are described by Oli Larkin in more detail in
this post .
It's time to finally start creating a beautiful interface!
GUI
We want to achieve this result:

This is certainly not awesome cool, but we will learn how to add graphics and, even more interesting, how to make a rotating pen.
Download
this tiff with design. Open in Photoshop (or whatever you like) and take a look at the different layers and groups.
As you can see, the only thing that changes is a pen. So the rest can be simply saved in one png:

Add background for Mac builds
Save the picture above to your desktop. In Xcode in Project Navigator, expand the
Resources folder and drag the background image there:

It is necessary to put a tick in front of the
Copy items in folder and add our image for all targets:

Add background for builds on Windows
In Visual Studio, adding resources (such as graphics) is a bit different. Adding for all Targets on Macs means that the image will be included in the
.app ,
.vst and
.component files that you provide to your users. In Visual Studio, to do this, first drop our image into the project
\ resources \ img subfolder, and then edit the
.rc file in the project. In this case,
DigitalDistortion.rc . His hat looks like this:
#include "resource.h" KNOB_ID PNG KNOB_FN
First,
resource.h is connected, so that all
#define
from it are available in this file. The next line announces that a pen will be added. To add a background, add this line:
BACKGROUND_ID PNG BACKGROUND_FN
After a minute, add
BACKGROUND_ID
and
BACKGROUND_FN
to
resource.h .
Every time we add an image to the project, we need to add a similar line.
Background image
Let's pick up our picture in the plugin. Somewhere around the 60th line in the
resource.h file you need to resize the window:
and add a unique ID and image file name:
In
DigitalDistortion.cpp, you need to change the constructor to use our file instead of red:
It was easy. Let's collect the APP and admire the picture:

A pen
The handle is a little tricky. It has a texture and reflections, it consists of several layers. When you twist the knob, the metal rotates, but the lamp on the ceiling does not (hopefully). So some components must rotate, and some related to lighting, should not. Therefore, we can not save the pen as one picture and twist it in the process.
I did this: the pen has a base that does not rotate; on top of it is a metallic texture that rotates; and on top of all this are reflections that do not rotate. All three parts are presented separately (here I added a black background, just so that the borders and light parts could be seen):

For our task there is a very good tool: KnobMan. This is a free program, especially for creating pens.
Download , run, and open the
file I prepared in it:

All I did here was add three layers and slightly change some coordinates so that the metal texture rotates correctly. If you want to understand the program better, read the
manual .
Export this handle (Cmd + E on Mac, Ctrl + E on Windows) and name the file knob.png (or download
mine ). In this png there are 128 frames for different positions of the handle, and only metal with an arrow rotates. That is necessary.
In Xcode, delete the existing
knob.png (right click,
Delete ). In the dialog that appears, select
Move to Trash . Now drag the new
knob.png into the
img folder and do the same as we did with the background image.
Since the file name has not changed, we do not need to change
resource.h . Switch to
DigitalDistortion.cpp right away; change the
enum ELayout
:
enum ELayout { kWidth = GUI_WIDTH, kHeight = GUI_HEIGHT, kThresholdX = 79, kThresholdY = 62, kKnobFrames = 128 };
As you can see, we don’t even have to specify for the WDL that the new pen is bigger. We only need to specify the number of frames and set the coordinates.
Start VST2 and see how the frames change when you turn the knob. However, I was confused by the fact that the plugin is called distortion, and with the handle turned out 100%, we have clear sound.
Handle direction
Somewhere around the 90th row, you need to make changes:
mThreshold = 1 - (GetParam(kThreshold)->Value() / 100.);
To prevent division by zero, which we talked about earlier, you need to change the default value to
0
, and the maximum value to
99.99
(approximately line 30):
GetParam(kThreshold)->InitDouble("Threshold", 0.0, 0.0, 99.99, 0.01, "%");
Now everything should work as it should. From the semantic point of view, it would be good to rename the
Threshold
variable to something like
DistortionAmount
, since the only thing that represents the threshold value is the
mThreshold
variable.
Interim results
With a minimal amount of theoretical bells and whistles, we have created a working distortion with a custom interface. This gave us a general idea of ​​what plugin development involves.
Now that we have this understanding, we can proceed to more interesting things. Next time I will talk about the synthesis of sound waves.
Files with all the results of the work can be
downloaded .
Additional materials
There are many free examples for KnobMan
here and
here .
When creating the GUI, I used
this Photoshop tutorial. Thanks to the author!
And thanks
g200kg for KnobMan!
Original articles:
martin-finke.de/blog/articles/audio-plugins-006-presetsmartin-finke.de/blog/articles/audio-plugins-007-gui