[chuck-users] DSP question: accumulating frequency info using FFT?
Jascha Narveson
jnarveson at wesleyan.edu
Sat Oct 14 12:26:47 EDT 2017
Chuck list! Help!
I have the following idea and I’d like to hear what it sounds like:
- play a sound into an FFT
- as the FFT runs, for each bin:
- - look at the magnitude info
- - take a small fraction of this info and store it in a running total
- - let the phase pass through unchanged
- use the spectral data in the running total for the IFFT
What I was hoping for was a slow emerging smear of all the frequencies from the input sound, kind of like a weird version of some kind of “infinite sustain” reverb.
What I’m getting is the attacks of the original sound coming through, although fading in, and covered with noise.
I think I’m doing something wrong by not doing something with the phase, but I’m not sure what.
I’d love some advice…
cheers,
j
- - - - c o d e e x a m p l e - - - -
SinOsc synth => FFT fft => blackhole;
UAnaBlob blob;
IFFT ifft => dac;
synth.freq(440);
synth.gain(0.1);
// set parameters
2048 => fft.size;
// place to hold the FFT data as it comes in
complex spec[fft.size()/2];
// place to store the accumulated FFT data, preload with zeroes
complex acc[fft.size()/2];
for(0 => int i; i < acc.cap(); i++) {
#(0, 0) => acc[i];
}
// do it!
spork ~ sawTune();
spork ~ accumulateFrequenciesViaFFT();
while (true) {
1::second => now;
}
fun void accumulateFrequenciesViaFFT() {
while( true )
{
fft.upchuck() @=> blob;
// get the data
blob.cvals() @=> spec;
// for every bin...
for(0 => int i; i < spec.cap(); i++) {
// get the mag/phase for each bin by converting to polar
spec[i] $ polar => polar newBin;
// and get our running totals from acc
acc[i] $ polar => polar accBin;
// scale the inocming mag and add it to acc
newBin.mag * 0.001 +=> accBin.mag;
// let phase pass through
newBin.phase => accBin.phase;
/*Math.random2f(0, TWO_PI) => accBin.phase;*/
// convert back to complex and put back in the acc array
accBin $ complex => acc[i];
}
ifft.transform(acc);
fft.size()::samp => now;
}
}
fun void sawTune() {
while (true) {
Math.random2(48, 72) => int midinote;
Math.mtof(midinote) => synth.freq;
333::ms => now;
}
}
More information about the chuck-users
mailing list