A simple, but fast webfft.js library based on the Cooley-Tukey DIF algorithm. Demo: webfft.net.
There is a basic UI that works with a 3-channel 1024×1024 float32 texture. Slow operations run on 3 background threads, one per texture channel.
The UI doesn't have a button to compute 2D FFT, but it provides a set of simpler operations that can be chained together to make 2D FFT:
- Apply the per-row FFT.
- Transpose the texture.
- Apply the per-row FFT again.
- Transpose the texture again.
The picture can be blurred by applying a gaussian window to high frequencies:
- FFT on rows.
- Gaussian window x 20.
- Transpose.
- FFT on rows.
- Gaussian window x 20.
- Transpose.
Inverse FFT can be done this way:
- Conjugate: (re, im) -> (re, -im).
- FFT on rows.
- Conjugate again.
- Transpose.
- Conjugate.
- FFT on rows.
- Conjugate.
- Transpose.
The texture can be saved as:
- PNG in the RGB×int16 format.
- EXR in the RGB×float32 format.
48 kHz audio is first loaded into an array of samples (aka the waveform) and then interpreted as a 2048×1024 texture. The pair of stereo channels map to (re,im) components. Thus 5.1ch audio maps to the three RGB (re,im) channels. Each row in the texture becomes a 20ms audio frame. Then per-row FFT can be applied.
Here is an example. Download a birdsong from https://xeno-canto.org/927288 and apply the following steps:
- Shift right.
- Gaussian window x 3 times.
- FFT on rows.
- Shift right.
- Transpose.
- Adjust HDR brightness in the top-right corner.
Red and green correspond to the 2 stereo channels in the audio file.
Autocorrelation can be computed from this texture:
- Transpose to restore the original "audio frame per row" layout.
- Square amplitudes: re^2+im^2.
- FFT on rows. This is identical to inverse FFT because at this point each row is symmetrical and purely real.
- Shift right.
- Transpose.
Another option is to compute the Radon transform:
- Map the FFT image to polar coordinates.
- Apply the 2D FFT.
Public Domain