Hi, I’m trying to create a multichannel version of this FFT stretching sampler, but getting clicks. The single-channel version works fine, but the multichannel one has issues.
Working single-channel reference:
SynthDef(\fftstretch, {
arg out=0;
var buf=\bufnum.kr(0), overlaps=2, fftSize=16384;
var chain, pos, fftBuf, levels=\levels.kr(1!2, 1/30, fixedLag: true);
pos=\pos.kr(0, 1/30, fixedLag: true)*BufFrames.kr(buf);
fftBuf = LocalBuf(fftSize!overlaps);
chain = BufFFTTrigger(fftBuf, 1/overlaps, (0..(overlaps-1)), overlaps);
chain = BufFFT_BufCopy(chain, buf, pos, BufRateScale.kr(buf));
chain = BufFFT(chain);
chain = PV_Diffuser(chain, chain > -1);
chain = Mix(BufIFFT(chain, 0)).dup * 0.8;
Out.ar(out, chain*levels);
}).add;
My multichannel attempt (with clicks):
// Load test buffer
g = Buffer.read(s, Platform.resourceDir +/+ "sounds/a11wlk01.wav");
// Multichannel version
(
SynthDef(\fftstretchMC, {
arg out=0;
var buf=\bufnum.kr(0), overlaps=2, fftSize=16384;
var chains, pos, numChan=8;
var levels=\levels.kr(1!numChan, 1/30, fixedLag: true);
var rate = \rate.kr(1!numChan, 1/30, fixedLag: true);
pos=\pos.kr(0!numChan, 1/30, fixedLag: true)*BufFrames.kr(buf);
chains = Array.fill(numChan, { |i|
var fftBuf = LocalBuf(fftSize!overlaps);
var chain = BufFFTTrigger(fftBuf, 1/overlaps, [0,1], overlaps);
chain = BufFFT_BufCopy(chain, buf, pos[i], rate[i]*BufRateScale.kr(buf));
chain = BufFFT(chain);
chain = PV_Diffuser(chain, 1);
chain = BufIFFT(chain, 0);
Mix.ar(chain) * 0.8 * levels[i];
});
Out.ar(out, chains);
}).add;
)
// Test
x = Synth(\fftstretchMC, [\bufnum, g]);
x.set(\pos, Array.fill(8, {|i| i/8})); // Different position per channel
The clicks seem related to the overlapping FFT windows in the multichannel version.
As far as i understand, i should have two overlapping signals per channel, and it might be bufFFTTrigger that is triggering this 2 windowed grains that should overlap.
But i’m failing with clearly visualizing the different levels of multichannel-expansion and overlapping needed to make this properly.
I am a low-dimensional guy…
Any help with this would be very much appreciated!!!
Interestingly, when trying this example in supercollider IDE everything seems fine, with no clicks. But fails with clicks when using the generated .scsyndef (via writeDefFile()) on my system (ofxSupercollider with OpenFrameworks (C++)).
At some point in the past i succesfully created a multichannel .scsyndef which i am using a lot with ofxSuperCollider, but (dumb me!) i didnt save the .scd file and now i can’t recover the code to see how i did it… so i’m pretty sure there is a way to do this properly… or at least that works on my case
well… thanks in advance, as usual, for your unvaluable help!