1
$\begingroup$

I am relatively new to DSP, and I am trying to create a spectral suite plugin using the IPlug2 library for creating vst plugins, and an FFT library I found on GitHub.

So far, I can perform an FFT on a signal, process the spectral data, and perform an IFFT to convert it back to time data. With zero overlap there were lots of clicks, which I learned could be solved using a window function.

I implemented the Hanning window, and am now doing the FFT with 50% overlap. Just to be sure I understand, by that I mean each consecutive FFT frame is only shifted 50% from the previous frame, and applying the Hanning window on each frame so they sum to the full audio sample.

This has significantly reduced the number of clicks in my audio, but when I significantly degrade the audio, I can still hear some clicking, which I have noticed is not present in other plugins that do the same effect.

Is there something else I can do to reduce this spectral leakage?

Should I use another window type if I want less of this effect?

Since some people asked for code, I'll upload some code to briefly explain what I have working so far.

void ProcessFFT(vector<float> &in, vector<float> &out)
{
  hanning(in);
  fft(in.data(), re.data(), im.data());

  // process
  for (Effect* effect : effects)
  {
    effect->process(re, im);
  }
  ifft(out.data(), re.data(), im.data());
}

void hanning(vector<float>& buffer) {
  for (int i = 0; i < FFTSize; i++)
  {
    buffer[i] *= (1 - cosf(2 * i * PI / size)) / 2;
  }
}

The ProcessFFT() function is used every 1024 samples, with vectors containing the last 2048 samples. This way, there is a 50% overlap with each consecutive frame. When they add together, the signal is mostly preserved, but clicks will still happen through significant processing of the spectral data. While it is not crucial that I resolve this, I would like to avoid it if possible.

The plugin that I reference above which does the effect I am looking for is called ASAP Spectral Clip, it will round all frequency bins below a certain user-specified amplitude to zero, and it does it without any clicks whatsoever. That is where I got the term Window Overlapping, and I am wondering if I can learn something from it to improve my own plugin, which will have the same effect. It is free if you care to install it and hear the effect for yourself.

$\endgroup$
6
  • $\begingroup$ You have to define more clearly than "do an FFT on incoming signal". There's more than that what you're doing because what you said has nothing about reconstructing the signal from whatever you did with the FFT. $\endgroup$ Dec 15, 2023 at 7:39
  • $\begingroup$ Agreed, try to provide code if possible. Does the original audio have a lot of clicking, or only after applying an FFT? Are you applying anything else to the FFT? $\endgroup$
    – Baddioes
    Dec 15, 2023 at 8:01
  • $\begingroup$ If you want to do frequency domain LTI filtering, you need to implement overlap add (no hamming etc required). If you want to do time variant frequency domain filter, you should probably take a university level DSP class: that's fairly complicated. It would help to learn more about your specific apploication $\endgroup$
    – Hilmar
    Dec 15, 2023 at 13:14
  • $\begingroup$ I'm sorry, as I said I am new to DSP so I don't know what people might expect with a question like this. I updated the original question with code and clarified what my problem is and what I've tried. $\endgroup$
    – Kallyn
    Dec 15, 2023 at 18:05
  • $\begingroup$ @Baddioes, the original audio could for example be a piano melody, and the output will be the same audio but with the lowest-amplitude bins removed based on a threshold value, as is intended. It starts to click again when raising the threshold to the extreme. $\endgroup$
    – Kallyn
    Dec 15, 2023 at 18:10

2 Answers 2

1
$\begingroup$

You actually want to apply a window both before and after your FFT/processing.

In simple intuitive terms: the FFT assumes that the waveform you give it repeats endlessly. (After all, it's transforming it to the sum of sines/cosines which do repeat like that, matching up at the start and end).

So we apply a window before the FFT analysis, so that the start and end match up nicely - otherwise it will perceive any mismatch as a discontinuity, and that will muddy your spectral analysis.

But if you then change the spectrum, you'll disrupt that tapering, meaning that your start/end are no longer at 0. There's certainly no guarantee they'll match up nicely with other blocks, so you might get clicks at the start and end of your summed-up output.

So we taper our output before summing as well. For a Hann(ing) window, this also means you'll need to your FFT blocks to overlap even more (probably every 512 samples in your case - plus you'll need to scale the output by ⅔).

You can search for "WOLA windows" to get window/overlap combos that add up nicely.

$\endgroup$
1
  • 1
    $\begingroup$ This was the answer! I didn't realize I could use the same window and have the outputs sum together evenly in the end. It took a while to refactor my program but i have it working now. Thank you! $\endgroup$
    – Kallyn
    Dec 19, 2023 at 16:38
0
$\begingroup$

What you’re looking for on the synthesis side is an overlap-add method. Overlap-add is necessary when doing overlapping windows for perfect reconstruction. To properly do this, you need to satisfy the constant overlap-add constraint. This is easiest achieved by using the square root of a window for both your analysis and synthesis windows. A typical process would be window->FFT->spectral processing->IFFT->window->overlap-add. More on the theory can be found here under the “ISTFT with WOLA” section.

$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.