Stereo expander algorithm?
-
- KVRist
- Topic Starter
- 226 posts since 29 Oct, 2005 from Espoo, Finland
Hi!
How do stereo expanders work? I was thinking about this and I could not find a trivial answer. How to find what data in right and left channels are more characteristic to one channel than another? Do you need a fourier transform? On the other hand, a stereo->mono converter can be untrivial because a small phase difference can distort the frequency spectrum if a simple addition is used.
I'm indeed quite new to this. I tried Google but couldn't find info. If I have missed some source that explains this kind of things, please point me to the right direction.
Thanks!
How do stereo expanders work? I was thinking about this and I could not find a trivial answer. How to find what data in right and left channels are more characteristic to one channel than another? Do you need a fourier transform? On the other hand, a stereo->mono converter can be untrivial because a small phase difference can distort the frequency spectrum if a simple addition is used.
I'm indeed quite new to this. I tried Google but couldn't find info. If I have missed some source that explains this kind of things, please point me to the right direction.
Thanks!
-
- KVRAF
- 8389 posts since 11 Apr, 2003 from back on the hillside again - but now with a garden!
chack www.musicdsp.org there are a couple there, some even added recently. A common trick is to delay one channel by a couple of samples, but watch for different samplerates having different effects.
You could employ a few different techniques, such as different freqs expanding by different amounts...
DSP
You could employ a few different techniques, such as different freqs expanding by different amounts...
DSP
-
- KVRist
- 56 posts since 20 Sep, 2006 from Hamburg, Germany
Maybe this thread helps:
http://www.kvraudio.com/forum/viewtopic ... ght=stereo
Especially this algorithm could be exactly, what you want:
http://www.kvraudio.com/forum/viewtopic ... ght=stereo
Especially this algorithm could be exactly, what you want:
Code: Select all
M = (L+R)/sqrt(2); // obtain mid-signal from left and right
S = (L-R)/sqrt(2); // obtain side-signal from left and right
// amplify mid and side signal seperately:
M *= 2*(1-width);
S *= 2*width;
L = (M+S)/sqrt(2); // obtain left signal from mid and side
R = (M-S)/sqrt(2); // obtain right signal from mid and side
-
Music Engineer Music Engineer https://www.kvraudio.com/forum/memberlist.php?mode=viewprofile&u=15959
- KVRAF
- 4317 posts since 8 Mar, 2004 from Berlin, Germany
aha, that's my pseudocode. by now, i've also written a small article on that topic:
http://www.rs-met.com/documents/tutoria ... essing.pdf
http://www.rs-met.com/documents/tutoria ... essing.pdf
- KVRAF
- 6478 posts since 16 Dec, 2002
That's hardly an algorithm. It's a bog standard mid-side summing matrix (hardly a matrix either). The sqrt() will probably confuse many but it does nothing but weight the mixing relationship (and it's terribly unnecessary for optimal code).iGoA wrote:Maybe this thread helps:
http://www.kvraudio.com/forum/viewtopic ... ght=stereo
Especially this algorithm could be exactly, what you want:
Code: Select all
M = (L+R)/sqrt(2); // obtain mid-signal from left and right S = (L-R)/sqrt(2); // obtain side-signal from left and right // amplify mid and side signal seperately: M *= 2*(1-width); S *= 2*width; L = (M+S)/sqrt(2); // obtain left signal from mid and side R = (M-S)/sqrt(2); // obtain right signal from mid and side
For actual stereo expansion/enhancement I would look at haas, and other delay and filter based solutions.
actually, there is a great wealth of stereo expansion to be found on google. just not by the most obvious keywords and sources.jdtrbn wrote:I tried Google but couldn't find info.
I once hit a motherload and stumbled on several modern stereo-to-surround re-panning algos.
White papers and all. Still haven't seen some of them as plugins, probably due to patent restrictions.
-
Music Engineer Music Engineer https://www.kvraudio.com/forum/memberlist.php?mode=viewprofile&u=15959
- KVRAF
- 4317 posts since 8 Mar, 2004 from Berlin, Germany
granted. i think, i pointed that out in the old thread myself (and we babbled quite some bit about its purpose there). but it's a good idea to mention it here again.Kingston wrote:The sqrt() will probably confuse many but it does nothing but weight the mixing relationship (and it's terribly unnecessary for optimal code).
- KVRAF
- 8137 posts since 12 Feb, 2006 from Helsinki, Finland
Actually, by replacing the:Kingston wrote:
That's hardly an algorithm. It's a bog standard mid-side summing matrix (hardly a matrix either). The sqrt() will probably confuse many but it does nothing but weight the mixing relationship (and it's terribly unnecessary for optimal code).
Code: Select all
foo / sqrt(2.0);
Code: Select all
foo * (1.0/sqrt(2.0));
Really good compilers (haven't done an extensive check) will naturally do the above optimization automatically, but it might be worth trying whether there's a speed difference between the two.
-
- KVRian
- 829 posts since 13 Jul, 2002
Or simply pre-calculate the result of sqrt(2):
http://www.math.com/students/calculator ... e-root.htm
//Daniel
http://www.math.com/students/calculator ... e-root.htm
//Daniel
- KVRAF
- 6478 posts since 16 Dec, 2002
Surround sound production is basically the only field that still spends considerable funds on researching stereo enhancement - or more generally - spatial enhancement.
This here is my all-time favourite:
http://www.irisa.fr/prive/kadi/Sujets_C ... endano.pdf
I actually used that as a starting point for my graduation dissertation. highly recommended. It contains plenty of references and keywords for everything one needs to know.
AFAIK, stuff like that is only featured on super expensive post-production surround processors this far.
can be easily (and cheaply) adapted to stereo processing of course.
This here is my all-time favourite:
http://www.irisa.fr/prive/kadi/Sujets_C ... endano.pdf
I actually used that as a starting point for my graduation dissertation. highly recommended. It contains plenty of references and keywords for everything one needs to know.
AFAIK, stuff like that is only featured on super expensive post-production surround processors this far.
can be easily (and cheaply) adapted to stereo processing of course.
-
- KVRist
- Topic Starter
- 226 posts since 29 Oct, 2005 from Espoo, Finland
You're such a great help, guys!
I'm still a bit curious about stereoizing. I remember doing this with small delays in my old tracking(.module) days, but now this seems to be easily associated with reverbs, which can damage the clarity of sounds, I'm afraid. I think Cubase comes with a useful plug-in but this doesn't seem to be a popular subject in freeware VSTs.
I'm still a bit curious about stereoizing. I remember doing this with small delays in my old tracking(.module) days, but now this seems to be easily associated with reverbs, which can damage the clarity of sounds, I'm afraid. I think Cubase comes with a useful plug-in but this doesn't seem to be a popular subject in freeware VSTs.
-
- KVRer
- 1 posts since 7 Aug, 2016
AUTO-ADMIN: Non-MP3, WAV, OGG, SoundCloud, YouTube, Vimeo, Twitter and Facebook links in this post have been protected automatically. Once the member reaches 5 posts the links will function as normal.
I know that this is a very old thread but I felt like I should respond, as I think I see a problem here. Maybe my algebra is wrong, but it looks like the square root falls out altogether. I think it could be simplified to this:iGoA wrote:Code: Select all (#)
M = (L+R)/sqrt(2); // obtain mid-signal from left and right S = (L-R)/sqrt(2); // obtain side-signal from left and right // amplify mid and side signal seperately: M *= 2*(1-width); S *= 2*width; L = (M+S)/sqrt(2); // obtain left signal from mid and side R = (M-S)/sqrt(2); // obtain right signal from mid and side
Code: Select all (#)
// Should be the same result as the above code! (Please check to make sure)
L = L+R-2*R*width;
R = L+R-2*L*width;
Code: Select all (#)
// All this does is subtract out some of the other channel, accentuating the difference between them
L=L-R*width;
R=R-L*width;
-
- KVRer
- 1 posts since 21 Nov, 2012
Hi, given the original algorithm, it the width is 0. Both L and R would be L + R. If L and R is the same, this would be a raise of 6dB. However, today I checked the panning in Ardour. When I adjust the width to 0% (mono), the amplitude raise by 3dB for each channel. So I adjust the two lines of width multiplication, take a squart root for the factor, and leave the rests same, final result should be like this:
M = (L+R)/sqrt(2); // obtain mid-signal from left and right
S = (L-R)/sqrt(2); // obtain side-signal from left and right
// amplify mid and side signal seperately:
M *= sqrt(2*(1-width));
S *= sqrt(2*width);
L = (M+S)/sqrt(2); // obtain left signal from mid and side
R = (M-S)/sqrt(2); // obtain right signal from mid and side
M = (L+R)/sqrt(2); // obtain mid-signal from left and right
S = (L-R)/sqrt(2); // obtain side-signal from left and right
// amplify mid and side signal seperately:
M *= sqrt(2*(1-width));
S *= sqrt(2*width);
L = (M+S)/sqrt(2); // obtain left signal from mid and side
R = (M-S)/sqrt(2); // obtain right signal from mid and side
- KVRAF
- 8137 posts since 12 Feb, 2006 from Helsinki, Finland
This is a very old thread, but the underlying assumption of equal power cross-fade (or panning) is that the original signals (ie. channels) are uncorrelated and similar gain. This holds reasonably well even for panning mono-signals, thanks to the unpredictability of acoustic summing, but it doesn't necessarily hold too well for M/S stereo control.
As it turns out, in the M/S stereo-width adjustment case, the "ideal" choice of the taper is highly signal dependent as more often than not the mid-channel is significantly stronger than the side-channel. For signals with weak side-channel, one could even argue that the ideal choice is to simply adjust the side-channel gain while leaving the mid-channel "as-is" where as for wide unison sounds or signals drowned in stereo reverb the equal power rule might indeed be a good choice.
Either way, the point I'm trying to make is that unlike panning (where equal power is almost always a reasonable choice), in this case the ideal choice is much less clear.
edit: however.. if you CAN make more assumptions for the source signal, then the situation changes... for example, choosing equal power might indeed be the optimal choice for a "width" knob for unison in a synthesiser, because here we can arrange for the original signals to be "uncorrelated" by hard-panning the voices (or spreading them across the stereo field in some other way)
As it turns out, in the M/S stereo-width adjustment case, the "ideal" choice of the taper is highly signal dependent as more often than not the mid-channel is significantly stronger than the side-channel. For signals with weak side-channel, one could even argue that the ideal choice is to simply adjust the side-channel gain while leaving the mid-channel "as-is" where as for wide unison sounds or signals drowned in stereo reverb the equal power rule might indeed be a good choice.
Either way, the point I'm trying to make is that unlike panning (where equal power is almost always a reasonable choice), in this case the ideal choice is much less clear.
edit: however.. if you CAN make more assumptions for the source signal, then the situation changes... for example, choosing equal power might indeed be the optimal choice for a "width" knob for unison in a synthesiser, because here we can arrange for the original signals to be "uncorrelated" by hard-panning the voices (or spreading them across the stereo field in some other way)
- KVRist
- 117 posts since 15 Oct, 2015 from Denmark
I tested both of your simplifications, and none of them works like the original.jeremyedmonds wrote: ↑Sat Aug 06, 2016 5:06 pmI know that this is a very old thread but I felt like I should respond, as I think I see a problem here. Maybe my algebra is wrong, but it looks like the square root falls out altogether. I think it could be simplified to this:iGoA wrote:Code: Select all
M = (L+R)/sqrt(2); // obtain mid-signal from left and right S = (L-R)/sqrt(2); // obtain side-signal from left and right // amplify mid and side signal seperately: M *= 2*(1-width); S *= 2*width; L = (M+S)/sqrt(2); // obtain left signal from mid and side R = (M-S)/sqrt(2); // obtain right signal from mid and side
I think it really is this simple. In fact, the multiplication by two is unnecessary, as "width" is a multiplier. If it were zero, you would get the sum of the left and right channels. If it is getting larger, you are just subtracting a portion of the other channel, which leaves more of the audio components that are unique to that channel. If this is all that it's doing, you might as well use something like this...Code: Select all
// Should be the same result as the above code! (Please check to make sure) L = L+R-2*R*width; R = L+R-2*L*width;
Code: Select all
// All this does is subtract out some of the other channel, accentuating the difference between them L=L-R*width; R=R-L*width;
"Scuba divers work best under pressure!"
https://www.youtube.com/user/DKDiveDude (Original music and hardware videos)
https://www.youtube.com/user/DKDiveDude (Original music and hardware videos)
- KVRAF
- 8137 posts since 12 Feb, 2006 from Helsinki, Finland
You do realize this post you quoted is from 2016?DKDiveDude wrote: ↑Tue Feb 02, 2021 11:59 amI tested both of your simplifications, and none of them works like the original.jeremyedmonds wrote: ↑Sat Aug 06, 2016 5:06 pmI know that this is a very old thread but I felt like I should respond, as I think I see a problem here. Maybe my algebra is wrong, but it looks like the square root falls out altogether. I think it could be simplified to this:iGoA wrote:Code: Select all
M = (L+R)/sqrt(2); // obtain mid-signal from left and right S = (L-R)/sqrt(2); // obtain side-signal from left and right // amplify mid and side signal seperately: M *= 2*(1-width); S *= 2*width; L = (M+S)/sqrt(2); // obtain left signal from mid and side R = (M-S)/sqrt(2); // obtain right signal from mid and side
I think it really is this simple. In fact, the multiplication by two is unnecessary, as "width" is a multiplier. If it were zero, you would get the sum of the left and right channels. If it is getting larger, you are just subtracting a portion of the other channel, which leaves more of the audio components that are unique to that channel. If this is all that it's doing, you might as well use something like this...Code: Select all
// Should be the same result as the above code! (Please check to make sure) L = L+R-2*R*width; R = L+R-2*L*width;
Code: Select all
// All this does is subtract out some of the other channel, accentuating the difference between them L=L-R*width; R=R-L*width;
That said the math is correct, except the last one uses substition width <- 2*width-1.
If they don't work like the original, then you made a mistake. Keep in mind that the two last lines are supposed to be computed in parallel, ie. you need temporary to compute one at a time:
L1 = L-R*(2*width-1)
R1 = R-L*(2*width-1)
L = L1
R = R1