The idea is that a normal control knob (Using Vector, SVG or a regular image) can be connected up to the standard Level Adj module, but the control will behave like a regular dB volume control, and will show the equivalent dB gain in a text entry module.
The GUI value conversion.
The neatest and simplest way to do this uses third party modules. Elena Novaretti has a dB to Volts converter in her module pack, which do the job very nicely. All we need to do is set the Patch Memory Float3’s Min and Max values to some useful levels such as -40 to + 3, which then gives you a gain range between -40 and +3 dB. I have also used the Name plug set to “dB Gain” to use for the control’s title display module The only GUI conversion needed is the float to text module for the readout. This is already scaled for our needs.
This is a question I have seen asked on the Synthedit group, and the Forum, so I thought it would be a useful sub-control & conversion prefab post to save others the hassle of re-inventing the wheel as it were. Whilst it’s a definite advantage in SE, not everyone is a mathematics wizard (including me!)
Converting voltage to time for the ADSR2 module.
The heart of the process of adding a time readout for the Knob is using this small prefab Volts2-ADSR-Time. The conversion takes place in the Waveshaper2B module using the formula (10^(x * 0.4-3))*10 – (note the order of the brackets). This method is not 100% accurate, but is close enough for our purposes. once the input Voltage has been converted to the correct curve it’s then converted to a GUI float value, and from there to on converted to a text string, and displayed in the ED Text Entry box. By connecting the second text box to the PatchMemory Float3 module and changing its name to the appropriate Attack/Decay/Sustain label we have a convenient way of adding a control name to the Knob.
You don’t have to use one of the Vector knobs, you can just as easily use the standard sub control Image2 as a control knob.
I have made the prefab available as a download here but as you can see from the screenshots you will need some third party modules, and the vector control is only for V1.5.
Have you Ever wished that the Moog style Knob control was just a little more versatile? Well it can be and it’s not “rocket science”. If we take the original Knob Sub-control prefab that comes with SynthEdit then its a matter of adding a few extra modules.
With some extra modules (as shown below) we can create a Knob which can be easily re-named, have a value readout, which has a suffix to indicate the type of value (Hz, Volts, dB etc.). I have used the following ED modules: GUI String Append, Fixed_string, and Text Entry (I like this module as it’s easy to control the appearance of the text, and set the background to transparent) We also need to convert DSP Float values to GUI float values for the Hue switching so the QTN Float2GUIFloat is ideal here. The Bool to float modules are used so you can switch the Saturation from colour to mono, and the Brightness from light to dark using a simple tick/untick option. With some basic maths we can re-scale the voltage to give us readouts such as; Volts->Hz, Volts->kHz, Volts->dB etc. The switch with the fixed values allows us to easily select a text colour, or by unchecking the colour/mono option just to have black or white text. The Text and BG (Background) ARGB values are standard, and using 00 for the A value on the BG ARGB setting gives us a fully transparent background. The string Append module allows us to add mode text after the Float To Text value, so there’s a single space in the Fixed String module, and then the third value is set by you for the appropriate Volts, Hz whatever for the control. You can also change the number of decimal places that are used for the value readout using an integer value.
Introduction: Sub controls provide a more customized user interface than standard controls but require more expertise to use effectively. They provide a lower-level access to the various visual elements on your control panel. There are some basic rules that need to be followed to use them with a minimum of problems.
Controls vs. Sub-Controls- Why have Sub Controls?
Before sub-controls, SynthEdit provided only pre-made controls, like the Slider Control. To understand sub-controls, it’s useful to understand how a control works.
For example the Slider: A slider has several interacting components… Lets have a look at the custom made slider below. The original SE slider control is included as a comparison (this control cannot be opened up-it’s one of the old ones, (so it can’t be modified without C++ coding).
Moving the slider updates the numeric text readout and vice-versa. So there’s a bi-directional connection between the two sub-components. Your computer typically updates its graphics 60 times per second yet the output of the is at audio-rate signal (typically 44,100 or more samples per second). So it follows that there’s a rate-conversion happening inside this module. You can’t open up the original slider to see what’s going on inside, but here’s one I put together to demonstrate what goes on:
The current position of the slider is stored in the patch-memory, and the slider will move automatically to reflect the current patch. We need to find a way of displaying the output value of the control. That’s done with the Float to Text, and the ED Text Entry modules. The Output from the module can take various forms. Here I have included three types of data that I think I’ll find useful: 1) DSP Volts out, 2) DSP Floating Point out, and 3) GUI Floating Point out. So you can already see how we can “personalize” and add functions to our controls in this way..
The focal point is the Patch Memory module. This handles the communication between the graphical (GUI) elements (with blue backgrounds) and the audio-processing (DSP) elements (with grey backgrounds). The Patch Memory module also handles any MIDI Automation of the control and handles switching between any presets (patches).
With the traditional Slider the layout of the elements was fixed. There’s no way, say, to put the numeric readout at the top. But now I have this Sub Control slider I can move the elements around at will. However using the Sub Control I just created then I can modify and move elements around as I like.
The purpose behind Sub-Controls.
The purpose of sub-controls is to split up the control into its constituent parts. As you saw with the slider Sub Control, this is a way of giving far you more flexibility over the appearance of your controls.
The first and focal point is the Patch Memory module. It handles the communication between the graphical elements (on the left with blue backgrounds) and the audio-processing elements (on the right with grey backgrounds). The patch mem module also handles any MIDI Automation of the control and handles switching between presets (patches). The second type of module here is the graphics controls. The Bitmap Image and the Text entry boxes. These accept user input and display the control’s current value. Graphical elements use the Patch-Mem module as a ‘hub’. Input to any object is reflected back to the others, keeping them always in sync. The third type of module here is datatype conversion. For example the Text-to-Float module. It’s purpose is to bridge the Patch-Mem module’s numeric (float) value with the Text-entry module (which otherwise would be used perhaps for entering a file-name).
You can see from the arrow heads in the picture below that the GUI Floating Point pins (blue background) are bi-directional. This ties in with the expected behavior.
Updating the numeric-entry box moves the knob and vice-versa. These signals are not sampled like audio signals but are event-driven. Event driven means that the control only sends data and uses the CPU when being moved, at all other times it does nothing. Compared to an audio (DSP) signal, the knob thus generates data at a much slower rate, and only when actually needed.
The signal leaves the Patch-Memory module via the Value Out plug as an audio connection, but it’s still sending data at the slower rate generated by the PC’s graphics system. This is why we include the next stage the Float To Volts module. The Float-to-Volt smooths out, and up-samples our Floating Point data to a true audio-rate signal suitable for controlling SynthEdit’s various audio modules. In SynthEdit these audio rate signals are called Voltages because SynthEdit is simulating an old-school Voltage controlled Synthesizer. The Float-to-Volts module gives you control over how smooth the conversion should be. Less smoothing uses less CPU, but the resulting audio changes (especially with filters) may sound ‘stepped’ or ‘zippered’. There is another reason this module must be included- without it the data rates will be miss-matched and updates in control position lost resulting in jerky or glitchy changes to the audio modules.
The general structure of a Sub-Control patch is: [Graphical Control]<—>[datatype Converter]<—>[Patch Mem]—>[Audio modules]
Customizing. You can see that the numeric input is optional, just delete it if you don’t need it. Same with the rotating knob image. Also you can now place the elements however you like.
Some of the settings available and what they do: Hint:- Provides for ‘Tooltips’, the popup yellow boxes that appear when you mouse-over the control. Menu Items and Menu Selection:- Provides a context menu (right-click menu). Type the menu items as a comma-separated list. e.g. “Set to Center=1, Randomize”. These will appear on the context menu, along with SynthEdit’s menu entries. The ‘Menu Selection’ pin outputs the user’s selection as an integer. e.g. if the user clicks ‘Set to Center’ the pin goes to 1. After any selection the pin returns quickly to zero. Always number your item list from 1 otherwise the first item will always output 0 (which is no different from ‘no-selection’). Editable:- You can use this with Text Entry boxes to stop uses from changing a label by accident, or to prevent values being entered into a control’s value box. Greyed:- You can use this with a Text Entry box to indicate that control is not currently relevant.
Efficiency. GUI Modules: As you know modules with blue backgrounds are ‘GUI Modules’ (Graphical User Interface Modules). These are designed to process user-input (mouse clicks and text entry etc.). These are not intended to process audio signals. On multicore systems they will usually run on a core separate from the audio processing, this allows the audio modules to take priority when the CPU is under load. Hybrid GUI/DSP modules: Modules with both blue and grey pins (like the Patch Memory Modules) are hybrid modules. Internally they consist of two parts running simultaneously in separate processes. Communication between the two parts is complex and is thus more CPU intensive than between other modules.
Don’t use audio modules to process GUI signals
In general aim to keep your use of hybrid modules to the absolute minimum. For example: Suppose you want to increase a knob’s display to range between 0 and 100, your might think to use the standard Multiplier module. Being an Audio module, this requires an extra conversion via a patch-mem or similar. A much more efficient method is to use a ‘pure‘ GUI solution like the Float-Scaler module. This will: 1) keep your circuit simpler and 2) your CPU usage far lower.
Use caution with GUI connections into Containers
Sub Controls are only active when the control panel window is open. When you close the control panel, the sub-controls immediately become inactive. Not only this but GUI plugs communicate only with modules visible in the same window, so if you are passing controls though another container, you must set that containers properties so with the “Controls on Parent” are visible, otherwise the GUI signals will not pass through the container. This behavior is in support of the new VST3 standards.
Example:- A Knob image is inside a Container, which is connected to a Patch Memory outside the control’s container. Unless the Container is set so that the Panel View is visible the knob cannot not respond to mouse movements and appears ‘frozen’, the Volt Meter and Vector Bar won’t respond to any control movements.
However as soon as we change the relevant settings on the Container – Patch Mem the controls spring into life: (see below)
Note: The structure view will always have this issue, but if the knob’s container has ‘Controls on Parent’ set it will work fine on the Panel view. The reason is:- With ‘Control on Parent’ set, the knob is displayed on it’s parent container’s window, which the same container the PatchMem is in. This is confusing- So if possible, always keep your GUI connections within the same container. If you do need GUI connections into a container, you can often get the structure view working too… For this the container’s ‘Show on Module’ needs to be set. This makes the knob visible in the same window as the Patch Mem which means the data connection works, but there’s still a catch. The right-hand window’s knob still won’t work properly. As it’s effectively a sub-container. There’s no way you can get the Patch Memory module visible in that window.
Summary: Sub controls in a container will work fine on the Panel view provided the container has ‘Show on Parent’ set. They control may not always respond in the structure view but you can often (but not always) fix the problem with the ‘Show on Module’ setting.
GUI modules need to be seen
Sub Controls function only while their Container’s Panel is open. i.e. if you close you synth’s panel, those sub controls become inactive. Therefore never rely on GUI modules to process audio signals. The exception is hybrid modules (Patch Memory) which will continue to provide patch-selection and automation functions via their audio pins.
Avoid splitters Due to a design mistake, SynthEdit 1.0 had the Container’s ‘Control on Parent’ pin on the wrong side. This made it impossible to connect it to a Patch Mem module (needed for save/recall of paged panel settings). The ‘Bool Splitter’ was introduced to fix this problem, but the bool splitter causes problems of it’s own. The bool splitter ‘reflects’ any one input signal back out it’s other inputs, this is a bad design because it is not clear which module is in control of the others. The result is modules ‘fighting’ each other for control. Symptoms include ‘flakey’ inconsistent behavior and patches not saved/recalled correctly. 3rd party module developers have sometimes copied SynthEdit’s example and released modules that rely on the use of splitters. This is not their fault, however if at all possible avoid using splitters.
Prefabs worth studying. SynthEdit’s Insert/Controls menu has several good examples. The Joystick module shows how to make any type of horizontal slider, vertical slider, or two-axis Joystick. Hint: For Sliders – use the resize handles to restrict the area of movement to a narrow strip.
Visual Indicators. The LED2 prefab is a template for any type of indicator or meter. Notable is it’s clever use of a transparent overlay image to dim the light, and the use of the Tinted Image module to provide for any color light.
This is a handy little prefab, that’s easy to make. It’s useful if you have a slider with the range of -10 V to + 10 V, it can be fiddly finding the 0 V “null point” with the standard slider.
How the center return slider works.
The control works by having a button or other clickable item send a Mouse Down signal to a Spring module, which then sends a reset value of 0 volts to the Patch Memory, and the Image 2 slider control.
We need to make up the structure below inside a container. When we change the Image2 filename to “vslider_med.png” this will automatically load the instructions for how the control should behave, so leave this property setting as “Auto”. Likewise with the Image2 that has “button.bmp” loaded. By connecting the Mouse Down plug of Text Entry4 to the PatchMemory Float3 if we click on this text label it will also reset the control to 0 Volts. You should untick the Text Entry4’s writeable property so that it can’t be edited from the panel (it keeps it’s mouse down control output though). All we need to do is set the Reset Value for the Spring module to 0, the the prefab is completed ready to save and use The maximum and Minimum slider values can be set as normal in the Prefab properties panel when in use in SynthEdit. Note: Do not try and make the slider return to 0 V “on click” by connecting the Mouse Down plug for the slider control… it won’t work like that. As soon as you move the slider it will send a Mouse Down to the Spring, and as soon as you release the control it will snap back to 0 V.
This Float value stepper uses the Elena Designs ESD Step Increment Float Module to step up and down in GUI and DSP Floating point values, which are also converted to DSP Voltage for controlling DSP Modules. There is no built in Wrap function on this module, so when you reach the upper limit it counts no further. There are four settings taken to an IO Mod: Minimum – sets the lowest float value, Maximum sets the highest float value, Step sets the amount by which the stepper increments/decrements, Display Decimals– sets the number of decimal points in the displayed value.
The GUI-DSP Bool Switch: This is just a slider control changed to Small Button in the properties list, with its DSP output voltage converted to GUI bools, then containerised.
This Pre-Fab steps up and down through a user pre-set range of integers, with the option to wrap or non-wrap the count. Wrapping means that when you reach the maximum or minimum points the count doesn’t stop. At the maximum it starts decrementing, and at the minimum it starts incrementing. In non-wrapping mode the count halts at maximum or minimum. The integer stepping range is set in the Pre-Fab’s properties using the range 0,n Text input plug. The first number does not need to be zero . Note: The first digit in the count must be lower in value than the second Integer, the prefab will not function with the values reversed or with negative values, and this plug will only update the number of steps set in properties when the audio engine is running. The Wrap function is a Boolean input, or can be set in the Prefab properties via the Wrap plug. Note: this plug will only update the Wrap mode when the audio engine is running. The Increment 3 Module does just that, it steps backwards or forwards through the range specified on the Item List plug the format is: range minInt, maxInt, for example range 2,22 will step through the range of Integers starting at 2 and ending at 22. The Patch Memory Text Out and Patch Memory Bool Out modules are required for the Prefab to receive, use, and remember the values set on the range 0,n and Wrap plugs. Without these modules these plugs will not function. There are two Integer outputs, DSP and GUI.
Clickable text labels. The Image2 modules can be replaced with any GUI module that sends/receives a Mouse Down event. So the layout below will work just the same, but with the added feature that clicking on the Up/Down text labels will also step through the count.
Expanding on the functionality: By Adding a few more modules we can add more outputs: GUI/DSP Float and DSP Volts. Note: Even though Float and Volts have decimal places, because our Increment module outputs Integers you will never get decimal places.
The idea behind this is that you can step through the options (for example) of an oscillator with just a single button rather than using a drop-down list box. Once the prefab control is put together it’s self configuring apart from the text label, and text colours. The list is taken from the module you connect up to.
How to step through a list with a single button in SynthEdit.
The idea here is that when we click on the button (Image2) module, it sends a “True” pulse to the ED Step Increment Int module, which connects to the PatchMemory List3 module. The PM List3 module reads the list of options from the DSP module (for example an Oscillator) it’s connected to and converts this to an Enumerated List For the List to Text and ED Step Increment Int module…(this makes life easier…less typing, and less opportunity for errors creeping in). Each time the ED Step Increment Int module receives a True pulse on the Increment plug it advances one step at a time through the list of options by advancing the Integer count by one step. The DAM list size module is used to inform the ED Step Increment Int module how many steps there should be, but for some reason I found you need to subtract 1 from the list co get the correct size. The two ED Text entry modules are used to display the selected value, and add a label to the control. Note: The Wrap option on the ED Step Increment Int module module should be set to “True” by selecting this on the options panel, then we can cycle through the list forever… Note: The RH-Int-Redir module is needed to connect up the ED Step Increment Int module and the List to Text module due to the Outputs being on the LHS of the ED Step Increment Int module… The List to Text module sends the Text name of the option selected to the Text Entry4 module where the selected option is displayed in the text box. If you want to cycle the other way, just send the Boolean pulse to the Decrement plug, it’s as easy as that. Note: If you want to make the Text label into a “click to select” connect the Increment plug on the ED Step Increment Int module module to the Mouse Down plug on the Text Entry4 module, and then you can step through in the same way by clicking on the text box.
Connecting up and using the prefab is easy, as you can see below, as I said the list is automatically generated when you connect the Switch to the Modules “List” plug.
Why have separate control panels? Sometimes when we are designing a Synthesizer, we can end up with a very complex, if not outright cluttered and confusing control panel (we have all seen examples of those!). Wouldn’t it be great if we could have separate control panels for different functions, such as a sequencer panel, an effects panel, etc. Well the good news is that we can, and it’s not over complicated either! Not only this anyone who uses your plug-in will thank you for it too.
How to have separate panels-the push button route.
With a few sub controls we can switch between control panels using a stepper controlled by a single button. Each switch is connected to a Bools to Int module via an QTN_Volt2GUIBool. This module converts as DSP voltage to a GUI Bool signal. When a button is pressed it sends a momentary “True” to the Bools to Int module, which the outputs an integer which corresponds to the plug receiving the pulse. Bool Val 1 outputs a 1, Bool Val 2 outputs a 2 and so on… This is then converted back into individual latched (that is it’s held at “True” until a new integer value is received on the Value plug) Boolean outputs to the integer value received.
Note: When designing this sort of panel switching we need to be disciplined, and give plugs appropriate names wherever possible (annoyingly you can’t rename the plugs on some modules!) otherwise things can rapidly become extremely confusing, and difficult to de-bug.
When this is connected up as shown below, we can switch between the individual panels by clicking on the appropriate button. Each individual control, or panel must be inside a container of it’s own for this to work properly. Note: switching these panels on and off is only visible in the panel view when the audio engine is on, and not in not the structure view, where all the panel containers will be visible.
Admin note: Updated 03/02/24 to reflect changes in the Elena Designs module pack (dsp-gui modules removed).
This is a method of creating a combined control for a coarse and fine voltage setting. It’s quite simple and uses the newer Vector controls. This is the finished control (Sorry that flashy looking knob in the centre is V1.5 only but the principle will work with the plain Vector Knob B in V1.4)
How it looks using Vector Knob B in V1.4
This is the structure below (Inside a container). We are just taking the Animation position of each vector control through a PatchMemory Float 3 to convert it to a DSP float value, this will later be converted to Voltage for DSP modules. The PatchMem connected to the vector ring has its maximum value set to 1 so that we get a range of 0 to 1 for this control, and 0 to 10 for the Knob C. The two values are added together using an ED Add (Float) module, and converted to Volts for controlling DSP modules. This means we get a total range of 0 to 11 for the control (shades of Spinal Tap), so by setting the Knob C’s PatchMem to a maximum of 9, we go back to our usual default of 0 to 10 volts. All you need to do once its working is to create a panel view, size and line up the two controls then lock the container view and save as a prefab control. This enables us to use the main inner knob as a coarse 0 to 10 control, and the outer ring as a fine 0 to 1 control (or any range you wish)
Changing the control ranges:
Changing the ranges for the inner and outer controls is as easy as setting the Max and Min values in the properties panel. This is set up for 0-to-1 for the outer ring, and 0-to-9 for the knob, giving an overall range of 0-to10 Volts out.