Mercurial > hg > btrack
diff src/OnsetDetectionFunction.cpp @ 93:4aa362058011
Added Kiss FFT option
author | Adam Stark <adamstark.uk@gmail.com> |
---|---|
date | Sat, 18 Jun 2016 09:24:13 +0100 |
parents | f6708e4c69f1 |
children | 6aea5918992d |
line wrap: on
line diff
--- a/src/OnsetDetectionFunction.cpp Wed May 11 00:19:06 2016 +0100 +++ b/src/OnsetDetectionFunction.cpp Sat Jun 18 09:24:13 2016 +0100 @@ -56,10 +56,7 @@ { if (initialised) { - // destroy fft plan - fftw_destroy_plan (p); - fftw_free (complexIn); - fftw_free (complexOut); + freeFFT(); } } @@ -74,14 +71,6 @@ //======================================================================= void OnsetDetectionFunction::initialise(int hopSize_,int frameSize_,int onsetDetectionFunctionType_,int windowType_) { - if (initialised) // if we have already initialised FFT plan - { - // destroy fft plan - fftw_destroy_plan (p); - fftw_free (complexIn); - fftw_free (complexOut); - } - hopSize = hopSize_; // set hopsize frameSize = frameSize_; // set framesize @@ -131,12 +120,53 @@ prevEnergySum = 0.0; // initialise previous energy sum value to zero - /* Init fft */ - complexIn = (fftw_complex*) fftw_malloc(sizeof(fftw_complex) * frameSize); // complex array to hold fft data - complexOut = (fftw_complex*) fftw_malloc(sizeof(fftw_complex) * frameSize); // complex array to hold fft data - p = fftw_plan_dft_1d (frameSize, complexIn, complexOut, FFTW_FORWARD, FFTW_ESTIMATE); // FFT plan initialisation - - initialised = true; + initialiseFFT(); +} + +//======================================================================= +void OnsetDetectionFunction::initialiseFFT() +{ + if (initialised) // if we have already initialised FFT plan + { + freeFFT(); + } + +#ifdef USE_FFTW + complexIn = (fftw_complex*) fftw_malloc (sizeof(fftw_complex) * frameSize); // complex array to hold fft data + complexOut = (fftw_complex*) fftw_malloc (sizeof(fftw_complex) * frameSize); // complex array to hold fft data + p = fftw_plan_dft_1d (frameSize, complexIn, complexOut, FFTW_FORWARD, FFTW_ESTIMATE); // FFT plan initialisation +#endif + +#ifdef USE_KISS_FFT + complexOut.resize (frameSize); + + for (int i = 0; i < frameSize;i++) + { + complexOut[i].resize(2); + } + + fftIn = new kiss_fft_cpx[frameSize]; + fftOut = new kiss_fft_cpx[frameSize]; + cfg = kiss_fft_alloc (frameSize, 0, 0, 0); +#endif + + initialised = true; +} + +//======================================================================= +void OnsetDetectionFunction::freeFFT() +{ +#ifdef USE_FFTW + fftw_destroy_plan (p); + fftw_free (complexIn); + fftw_free (complexOut); +#endif + +#ifdef USE_KISS_FFT + free (cfg); + delete [] fftIn; + delete [] fftOut; +#endif } //======================================================================= @@ -239,12 +269,13 @@ //======================================================================= void OnsetDetectionFunction::performFFT() { - int fsize2 = (frameSize/2); - + int fsize2 = (frameSize/2); + +#ifdef USE_FFTW // window frame and copy to complex array, swapping the first and second half of the signal for (int i = 0;i < fsize2;i++) { - complexIn[i][0] = frame[i+fsize2] * window[i+fsize2]; + complexIn[i][0] = frame[i + fsize2] * window[i + fsize2]; complexIn[i][1] = 0.0; complexIn[i+fsize2][0] = frame[i] * window[i]; complexIn[i+fsize2][1] = 0.0; @@ -252,6 +283,27 @@ // perform the fft fftw_execute (p); +#endif + +#ifdef USE_KISS_FFT + for (int i = 0; i < fsize2; i++) + { + fftIn[i].r = frame[i + fsize2] * window[i + fsize2]; + fftIn[i].i = 0.0; + fftIn[i + fsize2].r = frame[i] * window[i]; + fftIn[i + fsize2].i = 0.0; + } + + // execute kiss fft + kiss_fft (cfg, fftIn, fftOut); + + // store real and imaginary parts of FFT + for (int i = 0; i < frameSize; i++) + { + complexOut[i][0] = fftOut[i].r; + complexOut[i][1] = fftOut[i].i; + } +#endif } //////////////////////////////////////////////////////////////////////////////////////////////// @@ -314,7 +366,7 @@ // compute first (N/2)+1 mag values for (int i = 0;i < (frameSize/2)+1;i++) { - magSpec[i] = sqrt (pow (complexOut[i][0],2) + pow (complexOut[i][1],2)); + magSpec[i] = sqrt (pow (complexOut[i][0], 2) + pow (complexOut[i][1], 2)); } // mag spec symmetric above (N/2)+1 so copy previous values for (int i = (frameSize/2)+1; i < frameSize; i++) @@ -402,7 +454,7 @@ for (int i = 0;i < frameSize;i++) { // calculate phase value - phase[i] = atan2 (complexOut[i][1],complexOut[i][0]); + phase[i] = atan2 (complexOut[i][1], complexOut[i][0]); // calculate magnitude value magSpec[i] = sqrt (pow (complexOut[i][0],2) + pow (complexOut[i][1],2)); @@ -448,7 +500,7 @@ for (int i = 0;i < frameSize;i++) { // calculate phase value - phase[i] = atan2 (complexOut[i][1],complexOut[i][0]); + phase[i] = atan2 (complexOut[i][1], complexOut[i][0]); // calculate magnitude value magSpec[i] = sqrt (pow (complexOut[i][0],2) + pow(complexOut[i][1],2)); @@ -488,7 +540,7 @@ for (int i = 0;i < frameSize;i++) { // calculate phase value - phase[i] = atan2 (complexOut[i][1],complexOut[i][0]); + phase[i] = atan2 (complexOut[i][1], complexOut[i][0]); // calculate magnitude value magSpec[i] = sqrt (pow (complexOut[i][0],2) + pow(complexOut[i][1],2));