Has anybody figured out exactly how midpoint and skew work on knobs?
I keep my knobs linear and do my own math transforms but there appears to be a choice of two different built-in non-linear functions for knobs. Or is it one? I find it very confusing as in VMD there's a choice between Linear, Custom Midpoint and Custom Skew yet the SDK docs says this...
public void SetMidpointValue(double value)
Sets the mid point of the knob.
Parameters:
value - the middle point of the knob.
public void SetRangeSkewValue(double value, boolean skewFromCenter)
Sets how this knob skews.
Parameters:
value - the skew value adjusts how the knob adjusts from the midpoint value. if less than 1.0 will fill more value into the lower range. Otherwise, it will place more value into the higher range.
skewFromCenter - should it skew from the center?
So are skew factor, skew from center and midpoint all aspects of one transform or are there two different transforms?
I'm not interested in using either directly but I want to be able to control those rare knobs that do use these functions. So I need to figure out the math they use so that I can construct inverse functions to directly set the position of a knob rather than it being mangled.
There's a SkewNormalizedValue() method but this doesn't seem to do the job.
Any input would be most welcome as I would prefer not to have to figure it all out by experimentation. Also I can't be the only one who is confused.
Midpoint and skew
Re: Midpoint and skew
here's the explanation from the manual:
skew factor applies somewhat exponential or logarithmic scaling to the knob values which stretch either lower values (in the knob range) or higher values (in the knob range). this can be useful for cutoff controls on filters where you usually want more control over the lower frequencies than the higher frequencies.
skew and midpoint are different knob scaling options. skew from center kind of combines the two as it applies the skew scaling from the midpoint value instead of the minimum value.
or as the manual puts it:
so in essence midpoint quite literally sets value for the middle position of the knob and scales the left and right linearly in their respective regions. that's very useful for drive knobs for instance where you might want to 1.0 in the middle and then go down to 0.25 on the left and to a maximum of 4 on the right.Range Type: This lets you control how a knob’s value changes as its position changes. In the
default mode, Linear, moving the knob by a given amount anywhere in its range will always
change the knob’s value by the same amount. If a knob has a range from 0 to 1, for instance,
when the knob’s at its midpoint, it’ll have a value of 0.5. In Custom Midpoint mode, you can set a
value for the knob’s midpoint. With a range of 0 to 1 and a midpoint of 0.1, for instance, moving
the knob from its minimum value to its midpoint will change its value from 0 to 0.1, and then
moving the knob from the midpoint over to the far right will change the value from 0.1 to 1. In
Custom Skew Factor mode, you can set a skew factor that allows you to change the knob’s
response from linear to increasingly logarithmic. With a skew factor of 1, the response will be
linear. Skew factors < 1 will make the knob’s range increasingly favor the lower end of the
knob’s value range, while skew factors > 1 will increasingly favor the higher end of the knob’s
value range. This will probably be easier to understand by just experimenting with skew values
and seeing how the knob-value tooltip changes as you rotate the knob.
skew factor applies somewhat exponential or logarithmic scaling to the knob values which stretch either lower values (in the knob range) or higher values (in the knob range). this can be useful for cutoff controls on filters where you usually want more control over the lower frequencies than the higher frequencies.
skew and midpoint are different knob scaling options. skew from center kind of combines the two as it applies the skew scaling from the midpoint value instead of the minimum value.
or as the manual puts it:
Midpoint Value: When the range type is “Custom Midpoint” (see “Range Type” just above), this
allows you to set the midpoint value.
Skew Value: When the range type is “Custom Skew Factor” (see “Range Type” above), this
control sets the custom skew factor.
Skew From Center: When the range type is “Custom Skew Factor”, this option allows you to
set the knob to skew from its midpoint instead of from its minimum value.
Re: Midpoint and skew
"Custom Midpoint" is a function I use quite often. Some parameters make more sense to control in an exponential (or logarithmic) fashion.
Off the top of my head, the ADSR time values make more sense to have fine control for short values and coarser control for long values. This is particularly true when your longest value could be 60 seconds! Yes, you could have a 'Fast / Slow' Range switch but that takes up valuable panel space.
On Pink Flight and Micro Stringer, I decided to use the following values for Attack, Decay & Release:
Minimum Value (7 o'clock) = 0.0 sec
Maximum Value (5 o'clock) = 20.0 sec
Midpoint Value (12 o'clock) = 1.0 sec
I found these values to be more natural when tweaking a patch, and does away with the clutter of a 'Fast / Slow' switch.
I could have used a linear knob which went from 0.0 to 10.0 or 0 to 100. That value could then be transformed into a time value through some kind of formula internally.
However, for my money, having everything work straight out the box by just using a Custom Midpoint works best for developers AND users 99% of the time.
______________________
Dome Music Technologies
Dome Music Technologies
Re: Midpoint and skew
Thanks Chris that helps a bit. I was looking at the API comments rather than the VMD help. I also found an old post on the forum that says roughly the same thing.
As far as I can tell the basic transform is min + ( max - min ) * pow( position, 1 / skewFactor ) where position is the knob position normalized so 0 == fully CCW and 1 = fully CW.
But the midpoint value adjusts this as does the skewFromCenter flag. Unfortunately I'm having to experiment to figure out exactly how.
But it doesn't work like this. It's not linear. If you set midpoint to 0.1 with min = 0 max = 1 then at 12 o'clock you get 0.1 as expected but if it was linear you'd expect 9:30 (halfway between 7 and 12 ) to be 0.05 but it's in fact about 0.01.so in essence midpoint quite literally sets value for the middle position of the knob and scales the left and right linearly in their respective regions. that's very useful for drive knobs for instance where you might want to 1.0 in the middle and then go down to 0.25 on the left and to a maximum of 4 on the right.
This confuses me. So center isn't 12 o'clock?skew and midpoint are different knob scaling options. skew from center kind of combines the two as it applies the skew scaling from the midpoint value instead of the minimum value.
As far as I can tell the basic transform is min + ( max - min ) * pow( position, 1 / skewFactor ) where position is the knob position normalized so 0 == fully CCW and 1 = fully CW.
But the midpoint value adjusts this as does the skewFromCenter flag. Unfortunately I'm having to experiment to figure out exactly how.
Re: Midpoint and skew
I agree Grant that one often wants non-linear behaviour. My modules have loads of knobs that map to values in a non-linear fashion but I don't use the built-in functions instead I do it "by hand" as I have complete control over the transform then.
For instance MIN_FREQ * Math.pow( 2.0, rate * NUM_OCTAVES_RANGE ) in one direction and log2( freq / MIN_FREQ ) / NUM_OCTAVES_RANGE in the other direction.
I am actually using the attack knob on your Micro Stringer as a case study as it's one of the rare knobs that mangles the mapping and I know it uses min = 0, max = 20, midpoint = 1.
I'm trying to get a tandem operation working so that I can link your attack knob to one of my knobs with positional linearlity.
Re: Midpoint and skew
Ok so if the basic transform really is min + ( max - min ) * pow( position, 1 / skewFactor ) then I think given a midpoint between min and max we can convert the midpoint into a skew factor with...
skewFactor = 1 / ( log( ( midpoint - min ) / ( max - min ) ) / log( 0.5 ) )
in other words the midpoint transform is theoretically...
min + ( max - min ) * pow( position, log( ( midpoint - min ) / ( max - min ) ) / log( 0.5 ) )
Any mathematicians out there who can check my working while I dig deeper?
skewFactor = 1 / ( log( ( midpoint - min ) / ( max - min ) ) / log( 0.5 ) )
in other words the midpoint transform is theoretically...
min + ( max - min ) * pow( position, log( ( midpoint - min ) / ( max - min ) ) / log( 0.5 ) )
Any mathematicians out there who can check my working while I dig deeper?
Re: Midpoint and skew
I'm glad to report that my math worked when I coded it up - at least on Grant's attack knob.
So that gives me more confidence.
The mystery now is the skew from center thingy...
So that gives me more confidence.
The mystery now is the skew from center thingy...
Re: Midpoint and skew
I seem to have burnt out the part of my brain that can usually half cope with maths. There's something blindingly obvious but I'm struggling.
The story so far...
Given range = max - min just to simplify things and position = the normalized [0,1] input from the the knob or slider.
There are only two transforms involved - the main skew one and the skew from center one.
The main skew transform is
outputValue = min + range * Math.pow( position, 1 / skewFactor )
The midpoint thing isn't a separate transform at all, SetMidpointValue() is just another way of setting the skewFactor. It answers the question what skewFactor is required to produce a certain outputValue when position = 0.5.
So SetMidpointValue( midpoint )
is equivalent to
SetRangeSkewValue( 1 / ( Math.log( ( midpoint - min ) / range ) / Math.log( 0.5 ) ), false )
From if x = b^e then e = logb( x ).
Linear is just a special case where skewFactor is 1 or midpoint is 0.5.
Which leaves us with the skew from center transform which mirrors the transform about position = 0.5 so when position = 0.5 the outputValue is always min + 0.5 * range and in either direction from 0.5 the skew increases. Useful in a bipolar modulation situation for instance.
BUT for some reason I can't figure out the exact math having tried countless options. It should be simple but I can't find the solution!
As I said in opening it will probably be something blindingly obvious and I might solve it whle sleeping tonight but if someone can put me out of my misery I'd appreciate it.
The story so far...
Given range = max - min just to simplify things and position = the normalized [0,1] input from the the knob or slider.
There are only two transforms involved - the main skew one and the skew from center one.
The main skew transform is
outputValue = min + range * Math.pow( position, 1 / skewFactor )
The midpoint thing isn't a separate transform at all, SetMidpointValue() is just another way of setting the skewFactor. It answers the question what skewFactor is required to produce a certain outputValue when position = 0.5.
So SetMidpointValue( midpoint )
is equivalent to
SetRangeSkewValue( 1 / ( Math.log( ( midpoint - min ) / range ) / Math.log( 0.5 ) ), false )
From if x = b^e then e = logb( x ).
Linear is just a special case where skewFactor is 1 or midpoint is 0.5.
Which leaves us with the skew from center transform which mirrors the transform about position = 0.5 so when position = 0.5 the outputValue is always min + 0.5 * range and in either direction from 0.5 the skew increases. Useful in a bipolar modulation situation for instance.
BUT for some reason I can't figure out the exact math having tried countless options. It should be simple but I can't find the solution!
As I said in opening it will probably be something blindingly obvious and I might solve it whle sleeping tonight but if someone can put me out of my misery I'd appreciate it.
Re: Midpoint and skew
I think that last sentence nails the purpose of Skew From Center. It seems bonkers otherwise!ColinP wrote: ↑Sun Apr 30, 2023 4:40 pm Which leaves us with the skew from center transform which mirrors the transform about position = 0.5 so when position = 0.5 the outputValue is always min + 0.5 * range and in either direction from 0.5 the skew increases. Useful in a bipolar modulation situation for instance.
Great detective work, Colin. Thanks.
______________________
Dome Music Technologies
Dome Music Technologies
Re: Midpoint and skew
Cheers Grant.
I've spent at at least ten hours tracking this sh*t down and am going slightly bonkers now. At least by writing it up hopefully nobody else will need to go through the same ordeal.
I can see exactly what skew from center is doing but can't derive the math. Maybe I need to take a break from the problem and do something else for a day!
I've spent at at least ten hours tracking this sh*t down and am going slightly bonkers now. At least by writing it up hopefully nobody else will need to go through the same ordeal.
I can see exactly what skew from center is doing but can't derive the math. Maybe I need to take a break from the problem and do something else for a day!