Mercurial > hg > btrack
comparison src/BTrack.h @ 96:c58f01834337
Merge branch 'release/1.0.4'
author | Adam Stark <adamstark.uk@gmail.com> |
---|---|
date | Sat, 18 Jun 2016 10:50:06 +0100 |
parents | 4aa362058011 |
children | 6a4dd7478954 |
comparison
equal
deleted
inserted
replaced
87:496d12635af8 | 96:c58f01834337 |
---|---|
21 | 21 |
22 #ifndef __BTRACK_H | 22 #ifndef __BTRACK_H |
23 #define __BTRACK_H | 23 #define __BTRACK_H |
24 | 24 |
25 #include "OnsetDetectionFunction.h" | 25 #include "OnsetDetectionFunction.h" |
26 #include "CircularBuffer.h" | |
26 #include <vector> | 27 #include <vector> |
27 | 28 |
28 //======================================================================= | 29 //======================================================================= |
29 /** The main beat tracking class and the interface to the BTrack | 30 /** The main beat tracking class and the interface to the BTrack |
30 * beat tracking algorithm. The algorithm can process either | 31 * beat tracking algorithm. The algorithm can process either |
40 BTrack(); | 41 BTrack(); |
41 | 42 |
42 /** Constructor assuming frame size will be double the hopSize | 43 /** Constructor assuming frame size will be double the hopSize |
43 * @param hopSize the hop size in audio samples | 44 * @param hopSize the hop size in audio samples |
44 */ | 45 */ |
45 BTrack(int hopSize_); | 46 BTrack (int hopSize_); |
46 | 47 |
47 /** Constructor taking both hopSize and frameSize | 48 /** Constructor taking both hopSize and frameSize |
48 * @param hopSize the hop size in audio samples | 49 * @param hopSize the hop size in audio samples |
49 * @param frameSize the frame size in audio samples | 50 * @param frameSize the frame size in audio samples |
50 */ | 51 */ |
51 BTrack(int hopSize_,int frameSize_); | 52 BTrack (int hopSize_, int frameSize_); |
53 | |
54 /** Destructor */ | |
55 ~BTrack(); | |
52 | 56 |
53 //======================================================================= | 57 //======================================================================= |
54 /** Updates the hop and frame size used by the beat tracker | 58 /** Updates the hop and frame size used by the beat tracker |
55 * @param hopSize the hop size in audio samples | 59 * @param hopSize the hop size in audio samples |
56 * @param frameSize the frame size in audio samples | 60 * @param frameSize the frame size in audio samples |
57 */ | 61 */ |
58 void updateHopAndFrameSize(int hopSize_,int frameSize_); | 62 void updateHopAndFrameSize (int hopSize_, int frameSize_); |
59 | 63 |
60 //======================================================================= | 64 //======================================================================= |
61 /** Process a single audio frame | 65 /** Process a single audio frame |
62 * @param frame a pointer to an array containing an audio frame. The number of samples should | 66 * @param frame a pointer to an array containing an audio frame. The number of samples should |
63 * match the frame size that the algorithm was initialised with. | 67 * match the frame size that the algorithm was initialised with. |
64 */ | 68 */ |
65 void processAudioFrame(double *frame); | 69 void processAudioFrame (double* frame); |
66 | 70 |
67 /** Add new onset detection function sample to buffer and apply beat tracking | 71 /** Add new onset detection function sample to buffer and apply beat tracking |
68 * @param sample an onset detection function sample | 72 * @param sample an onset detection function sample |
69 */ | 73 */ |
70 void processOnsetDetectionFunctionSample(double sample); | 74 void processOnsetDetectionFunctionSample (double sample); |
71 | 75 |
72 //======================================================================= | 76 //======================================================================= |
73 /** @returns the current hop size being used by the beat tracker */ | 77 /** @returns the current hop size being used by the beat tracker */ |
74 int getHopSize(); | 78 int getHopSize(); |
75 | 79 |
84 | 88 |
85 //======================================================================= | 89 //======================================================================= |
86 /** Set the tempo of the beat tracker | 90 /** Set the tempo of the beat tracker |
87 * @param tempo the tempo in beats per minute (bpm) | 91 * @param tempo the tempo in beats per minute (bpm) |
88 */ | 92 */ |
89 void setTempo(double tempo); | 93 void setTempo (double tempo); |
90 | 94 |
91 /** Fix tempo to roughly around some value, so that the algorithm will only try to track | 95 /** Fix tempo to roughly around some value, so that the algorithm will only try to track |
92 * tempi around the given tempo | 96 * tempi around the given tempo |
93 * @param tempo the tempo in beats per minute (bpm) | 97 * @param tempo the tempo in beats per minute (bpm) |
94 */ | 98 */ |
95 void fixTempo(double tempo); | 99 void fixTempo (double tempo); |
96 | 100 |
97 /** Tell the algorithm to not fix the tempo anymore */ | 101 /** Tell the algorithm to not fix the tempo anymore */ |
98 void doNotFixTempo(); | 102 void doNotFixTempo(); |
99 | 103 |
100 //======================================================================= | 104 //======================================================================= |
103 * @param frameNumber the index of the current frame | 107 * @param frameNumber the index of the current frame |
104 * @param hopSize the hop size in audio samples | 108 * @param hopSize the hop size in audio samples |
105 * @param fs the sampling frequency in Hz | 109 * @param fs the sampling frequency in Hz |
106 * @returns a beat time in seconds | 110 * @returns a beat time in seconds |
107 */ | 111 */ |
108 static double getBeatTimeInSeconds(long frameNumber,int hopSize,int fs); | 112 static double getBeatTimeInSeconds (long frameNumber, int hopSize, int fs); |
109 | 113 |
110 /** Calculates a beat time in seconds, given the frame number, hop size and sampling frequency. | 114 /** Calculates a beat time in seconds, given the frame number, hop size and sampling frequency. |
111 * This version uses an int to represent the frame number | 115 * This version uses an int to represent the frame number |
112 * @param frameNumber the index of the current frame | 116 * @param frameNumber the index of the current frame |
113 * @param hopSize the hop size in audio samples | 117 * @param hopSize the hop size in audio samples |
114 * @param fs the sampling frequency in Hz | 118 * @param fs the sampling frequency in Hz |
115 * @returns a beat time in seconds | 119 * @returns a beat time in seconds |
116 */ | 120 */ |
117 static double getBeatTimeInSeconds(int frameNumber,int hopSize,int fs); | 121 static double getBeatTimeInSeconds (int frameNumber, int hopSize, int fs); |
118 | 122 |
119 | 123 |
120 private: | 124 private: |
121 | 125 |
122 /** Initialises the algorithm, setting internal parameters and creating weighting vectors | 126 /** Initialises the algorithm, setting internal parameters and creating weighting vectors |
123 * @param hopSize_ the hop size in audio samples | 127 * @param hopSize_ the hop size in audio samples |
124 * @param frameSize_ the frame size in audio samples | 128 * @param frameSize_ the frame size in audio samples |
125 */ | 129 */ |
126 void initialise(int hopSize_,int frameSize_); | 130 void initialise (int hopSize_, int frameSize_); |
127 | 131 |
128 /** Initialise with hop size and set all array sizes accordingly | 132 /** Initialise with hop size and set all array sizes accordingly |
129 * @param hopSize_ the hop size in audio samples | 133 * @param hopSize_ the hop size in audio samples |
130 */ | 134 */ |
131 void setHopSize(int hopSize_); | 135 void setHopSize (int hopSize_); |
132 | 136 |
133 /** Resamples the onset detection function from an arbitrary number of samples to 512 */ | 137 /** Resamples the onset detection function from an arbitrary number of samples to 512 */ |
134 void resampleOnsetDetectionFunction(); | 138 void resampleOnsetDetectionFunction(); |
135 | 139 |
136 /** Updates the cumulative score function with a new onset detection function sample | 140 /** Updates the cumulative score function with a new onset detection function sample |
137 * @param odfSample an onset detection function sample | 141 * @param odfSample an onset detection function sample |
138 */ | 142 */ |
139 void updateCumulativeScore(double odfSample); | 143 void updateCumulativeScore (double odfSample); |
140 | 144 |
141 /** Predicts the next beat, based upon the internal program state */ | 145 /** Predicts the next beat, based upon the internal program state */ |
142 void predictBeat(); | 146 void predictBeat(); |
143 | 147 |
144 /** Calculates the current tempo expressed as the beat period in detection function samples */ | 148 /** Calculates the current tempo expressed as the beat period in detection function samples */ |
147 /** Calculates an adaptive threshold which is used to remove low level energy from detection | 151 /** Calculates an adaptive threshold which is used to remove low level energy from detection |
148 * function and emphasise peaks | 152 * function and emphasise peaks |
149 * @param x a pointer to an array containing onset detection function samples | 153 * @param x a pointer to an array containing onset detection function samples |
150 * @param N the length of the array, x | 154 * @param N the length of the array, x |
151 */ | 155 */ |
152 void adaptiveThreshold(double *x,int N); | 156 void adaptiveThreshold (double* x, int N); |
153 | 157 |
154 /** Calculates the mean of values in an array between index locations [startIndex,endIndex] | 158 /** Calculates the mean of values in an array between index locations [startIndex,endIndex] |
155 * @param array a pointer to an array that contains the values we wish to find the mean from | 159 * @param array a pointer to an array that contains the values we wish to find the mean from |
156 * @param startIndex the start index from which we would like to calculate the mean | 160 * @param startIndex the start index from which we would like to calculate the mean |
157 * @param endIndex the final index to which we would like to calculate the mean | 161 * @param endIndex the final index to which we would like to calculate the mean |
158 * @returns the mean of the sub-section of the array | 162 * @returns the mean of the sub-section of the array |
159 */ | 163 */ |
160 double calculateMeanOfArray(double *array,int startIndex,int endIndex); | 164 double calculateMeanOfArray (double* array, int startIndex, int endIndex); |
161 | 165 |
162 /** Normalises a given array | 166 /** Normalises a given array |
163 * @param array a pointer to the array we wish to normalise | 167 * @param array a pointer to the array we wish to normalise |
164 * @param N the length of the array | 168 * @param N the length of the array |
165 */ | 169 */ |
166 void normaliseArray(double *array,int N); | 170 void normaliseArray (double* array, int N); |
167 | 171 |
168 /** Calculates the balanced autocorrelation of the smoothed onset detection function | 172 /** Calculates the balanced autocorrelation of the smoothed onset detection function |
169 * @param onsetDetectionFunction a pointer to an array containing the onset detection function | 173 * @param onsetDetectionFunction a pointer to an array containing the onset detection function |
170 */ | 174 */ |
171 void calculateBalancedACF(double *onsetDetectionFunction); | 175 void calculateBalancedACF (double* onsetDetectionFunction); |
172 | 176 |
173 /** Calculates the output of the comb filter bank */ | 177 /** Calculates the output of the comb filter bank */ |
174 void calculateOutputOfCombFilterBank(); | 178 void calculateOutputOfCombFilterBank(); |
175 | 179 |
176 //======================================================================= | 180 //======================================================================= |
179 OnsetDetectionFunction odf; | 183 OnsetDetectionFunction odf; |
180 | 184 |
181 //======================================================================= | 185 //======================================================================= |
182 // buffers | 186 // buffers |
183 | 187 |
184 std::vector<double> onsetDF; /**< to hold onset detection function */ | 188 CircularBuffer onsetDF; /**< to hold onset detection function */ |
185 std::vector<double> cumulativeScore; /**< to hold cumulative score */ | 189 CircularBuffer cumulativeScore; /**< to hold cumulative score */ |
186 | 190 |
187 double resampledOnsetDF[512]; /**< to hold resampled detection function */ | 191 double resampledOnsetDF[512]; /**< to hold resampled detection function */ |
188 | |
189 double acf[512]; /**< to hold autocorrelation function */ | 192 double acf[512]; /**< to hold autocorrelation function */ |
190 | |
191 double weightingVector[128]; /**< to hold weighting vector */ | 193 double weightingVector[128]; /**< to hold weighting vector */ |
192 | |
193 double combFilterBankOutput[128]; /**< to hold comb filter output */ | 194 double combFilterBankOutput[128]; /**< to hold comb filter output */ |
194 double tempoObservationVector[41]; /**< to hold tempo version of comb filter output */ | 195 double tempoObservationVector[41]; /**< to hold tempo version of comb filter output */ |
195 | |
196 double delta[41]; /**< to hold final tempo candidate array */ | 196 double delta[41]; /**< to hold final tempo candidate array */ |
197 double prevDelta[41]; /**< previous delta */ | 197 double prevDelta[41]; /**< previous delta */ |
198 double prevDeltaFixed[41]; /**< fixed tempo version of previous delta */ | 198 double prevDeltaFixed[41]; /**< fixed tempo version of previous delta */ |
199 | |
200 double tempoTransitionMatrix[41][41]; /**< tempo transition matrix */ | 199 double tempoTransitionMatrix[41][41]; /**< tempo transition matrix */ |
201 | |
202 | 200 |
203 //======================================================================= | 201 //======================================================================= |
204 // parameters | 202 // parameters |
205 | 203 |
206 | |
207 double tightness; /**< the tightness of the weighting used to calculate cumulative score */ | 204 double tightness; /**< the tightness of the weighting used to calculate cumulative score */ |
208 | |
209 double alpha; /**< the mix between the current detection function sample and the cumulative score's "momentum" */ | 205 double alpha; /**< the mix between the current detection function sample and the cumulative score's "momentum" */ |
210 | |
211 double beatPeriod; /**< the beat period, in detection function samples */ | 206 double beatPeriod; /**< the beat period, in detection function samples */ |
212 | |
213 double tempo; /**< the tempo in beats per minute */ | 207 double tempo; /**< the tempo in beats per minute */ |
214 | |
215 double estimatedTempo; /**< the current tempo estimation being used by the algorithm */ | 208 double estimatedTempo; /**< the current tempo estimation being used by the algorithm */ |
216 | |
217 double latestCumulativeScoreValue; /**< holds the latest value of the cumulative score function */ | 209 double latestCumulativeScoreValue; /**< holds the latest value of the cumulative score function */ |
218 | |
219 double tempoToLagFactor; /**< factor for converting between lag and tempo */ | 210 double tempoToLagFactor; /**< factor for converting between lag and tempo */ |
220 | |
221 int m0; /**< indicates when the next point to predict the next beat is */ | 211 int m0; /**< indicates when the next point to predict the next beat is */ |
222 | |
223 int beatCounter; /**< keeps track of when the next beat is - will be zero when the beat is due, and is set elsewhere in the algorithm to be positive once a beat prediction is made */ | 212 int beatCounter; /**< keeps track of when the next beat is - will be zero when the beat is due, and is set elsewhere in the algorithm to be positive once a beat prediction is made */ |
224 | |
225 int hopSize; /**< the hop size being used by the algorithm */ | 213 int hopSize; /**< the hop size being used by the algorithm */ |
226 | |
227 int onsetDFBufferSize; /**< the onset detection function buffer size */ | 214 int onsetDFBufferSize; /**< the onset detection function buffer size */ |
228 | |
229 bool tempoFixed; /**< indicates whether the tempo should be fixed or not */ | 215 bool tempoFixed; /**< indicates whether the tempo should be fixed or not */ |
230 | |
231 bool beatDueInFrame; /**< indicates whether a beat is due in the current frame */ | 216 bool beatDueInFrame; /**< indicates whether a beat is due in the current frame */ |
217 int FFTLengthForACFCalculation; /**< the FFT length for the auto-correlation function calculation */ | |
218 | |
219 #ifdef USE_FFTW | |
220 fftw_plan acfForwardFFT; /**< forward fftw plan for calculating auto-correlation function */ | |
221 fftw_plan acfBackwardFFT; /**< inverse fftw plan for calculating auto-correlation function */ | |
222 fftw_complex* complexIn; /**< to hold complex fft values for input */ | |
223 fftw_complex* complexOut; /**< to hold complex fft values for output */ | |
224 #endif | |
225 | |
226 #ifdef USE_KISS_FFT | |
227 kiss_fft_cfg cfgForwards; /**< Kiss FFT configuration */ | |
228 kiss_fft_cfg cfgBackwards; /**< Kiss FFT configuration */ | |
229 kiss_fft_cpx* fftIn; /**< FFT input samples, in complex form */ | |
230 kiss_fft_cpx* fftOut; /**< FFT output samples, in complex form */ | |
231 #endif | |
232 | 232 |
233 }; | 233 }; |
234 | 234 |
235 #endif | 235 #endif |