ryukau/VSTPlugins

Move UpSampling Cutoff Frequency into BasicLimiter at Nyquist

Closed this issue · 3 comments

Hey ryukau! Your work is awesome!

However The TP limiter is removing too much material on high frequencies.. I've tried to contribute using scipy for new coefficients but it seems that the code
'

 nTaps = 64
nPhase = 8
fir = signal.firwin(nTaps * nPhase - 1, 20000, window=("dpss", 4), fs=8 * 48000)
fir = np.hstack((fir, [0]))[::1]
poly = fir.reshape((nTaps, nPhase)).T
for i, p in enumerate(poly):
    poly[i] = p[::-1]

was not used for the design of the struct UpSamplerFir8Fold. it throws up other coefficients. Instead is good for the downsample

also the behavior get solved if I use the plug-in at 88.2 because filters coeffs are calculated for 48k, but this gets worse at 44.1

Hi, @metriccompute. Thanks for your interest.

Filte Design Code

I'll address the Python code first. Below is the correct one.

nTaps = 64
nPhase = 8
fir = signal.firwin(nTaps * nPhase - 1, 20000, window=("dpss", 4), fs=8 * 48000)
fir *= nPhase  # This scaling was missing.
fir = np.hstack((fir, [0]))[::1]
poly = fir.reshape((nTaps, nPhase)).T[::-1]  # Order of polyphase is flipped to match C++ code.
for i, p in enumerate(poly):
    poly[i] = p[::-1]

About New Filter

I won't change the coefficients of BasicLimiter to not break existing project. I'm okay to make another plugin with new coefficients, but only if it's good. Good here means that:

  • Higher cutoff.
  • Flat gain response on pass-band.
  • Better true peak amplitude after down-sampling. (See discussion below)
  • Faster computation. (Optional)

A problem is that a true peak (TP) limited signal exceeds 0 dB sometimes. There are 2 reasons:

  • Reconstruction of true-peak near Nyquist frequencies can't be exact.
  • Limiter modulates amplitude, and the added distortion remains after down-sampling.

I measured exceeding amplitude by:

  1. Generating a signal randomly filled with -1 and 1.
  2. Processing (1) with TP limiter.
  3. 16-fold up-sampling (2) by using FFT.

This measurement is not some rigorous method, but it's better than nothing. Peak amplitude of current implementation is somewhere around +0.05 dB. The new coefficients should produce the same or lower peak amplitude.

Another thing to note is that current implementation uses HighEliminationFir to eliminate frequencies near Nyquist.

The plots of the measurement could be found in link below. Also, the text in "トゥルーピークモード" section is a more detailed documentation about the problem. I'd recommend to use some machine translation, but if you really care about it, I can provide a translation.

For context, I'm doing all of this because I sometimes make wall-of-noise style music (like early 2000s Merzbow) for fun, and thought it's good to have a limiter that works for it.

@metriccompute Would you test the new coefficients? Below is a newly designed polyphase.hpp which can be replaced to the current one. I'd like to know if it works for you.

polyphase.zip

Both up and down sampler cutoff are set to Nyquist frequency. HighEliminationFir is changed. Overshoot is increased by roughly 50% in my measurement, but still below 0.1 dB.

The new HighEliminationFir is based on the "graph-paper" method mentioned in ITU-R BS.1770 Appendix 1 to Annex 2 (p.18). The gain response is drawn from the inverse of "maximum under-read" equation in Appendix 1, then IDFT is used to obtain FIR.

Closed due to no response.