comparison DrumTimingLoader_OF/src/RecordedMultipleAudio.cpp @ 2:50ba55abea8c

updating files to newer version
author Andrew N Robertson <andrew.robertson@eecs.qmul.ac.uk>
date Sat, 23 Nov 2013 15:49:27 +0000
parents 82352cfc0b23
children
comparison
equal deleted inserted replaced
1:106bc2d4f702 2:50ba55abea8c
1 /* 1 /*
2 * RecordedMultipleAudio.cpp 2 * RecordedMultipleAudio.cpp
3 * MultipleAudioMathcher 3 * Drum Timing Analyser
4 * 4 *
5 * Created by Andrew on 31/01/2012. 5 * Created by Andrew on 31/01/2012.
6 * Copyright 2012 QMUL. All rights reserved. 6 * Copyright 2012 QMUL. All rights reserved.
7 * 7 *
8 */ 8 */
9 9
10 #include "RecordedMultipleAudio.h" 10 #include "RecordedMultipleAudio.h"
11 11
12 const bool printExportInfo = false;
13
12 RecordedMultipleAudio::RecordedMultipleAudio(){ 14 RecordedMultipleAudio::RecordedMultipleAudio(){
13 15
14 infoFilepath = "../../../data/errorData.txt"; 16 infoFilepath = "../../../data/errorData.txt";
17
18 exactOnsetFilePath = "../../../data/exactOnsetTimes.txt";
19 kickRelativeTempoFilePath = "../../../data/kickRelativeTempoTimes.txt";
20 kickRelativeErrorsFilePath = "../../../data/kickRelativeErrorTimes.txt";
21 kickRelativeClickFilePath = "../../../data/kickRelativeClickTimes.txt";
22
23 drumTimerTempoFilePath = "../../../data/drummerTimerTempoTimes.txt";
24 drumTimerErrorsFilePath = "../../../data/drummerTimerErrorTimes.txt";
25 drumTimerClickFilePath = "../../../data/drummerTimerClickTimes.txt";
26
15 //infoFilepath = "/Users/andrew/errorData.txt"; 27 //infoFilepath = "/Users/andrew/errorData.txt";
16 28
17 timingOffset = 0; 29 timingOffset = 0;
30 playPositionSeconds = 3.4;
18 } 31 }
19 32
20 void RecordedMultipleAudio::loadTestAudio(){ 33 void RecordedMultipleAudio::loadTestAudio(){
21 34
35 int multitrackToLoad = 7;
22 36
23 numberOfAudioTracks = 2; 37 numberOfAudioTracks = 2;
24 38
25 printf("loaded max val is %f\n", loadedAudioFiles[0].fileLoader.onsetDetect.onsetDetector.maximumDetectionValue); 39 printf("loaded max val is %f\n", loadedAudioFiles[0].fileLoader.onsetDetect.onsetDetector.maximumDetectionValue);
26 40
27 int multitrackToLoad = 5; 41
42
28 setDifferentMultitracks(multitrackToLoad);//command to load this set of audio files - see below 43 setDifferentMultitracks(multitrackToLoad);//command to load this set of audio files - see below
29 44
30 drumTimingAnalyser.phaseCost = 1000;//v high - i.e. dont do phase 45 drumTimingAnalyser.phaseCost = 1000;//v high - i.e. dont do phase
46
31 47
32 drawWindow = 1; 48 drawWindow = 1;
33 trackScreenHeight = 0.25; 49 trackScreenHeight = 0.25;
34 50
35 51
80 kickfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/kick_bip.wav"; 96 kickfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/kick_bip.wav";
81 snarefilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/snare_bip.wav"; 97 snarefilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/snare_bip.wav";
82 sonicVizBeatsFilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/PennyArcade_take4_beats.txt"; 98 sonicVizBeatsFilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeOne_4/PennyArcade_take4_beats.txt";
83 break; 99 break;
84 100
101 /*
85 case 5: 102 case 5:
86 roomfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/neuamnn_bip.wav"; 103 roomfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/neuamnn_bip.wav";
87 kickfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/kick_bip.wav"; 104 kickfilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/kick_bip.wav";
88 snarefilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/snare_bip.wav"; 105 snarefilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/snare_bip.wav";
89 sonicVizBeatsFilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/PennyArcade_take5_beats.txt"; 106 sonicVizBeatsFilename = "/Volumes/Supersaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/PennyArcade_take5_beats.txt";
90 break; 107 break;
91 108 */
109 case 5:
110 roomfilename = "/Volumes/MiniSaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/neuamnn_bip.wav";
111 kickfilename = "/Volumes/MiniSaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/kick_bip.wav";
112 snarefilename = "/Volumes/MiniSaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/snare_bip.wav";
113 sonicVizBeatsFilename = "/Volumes/MiniSaurus/TractorsAlbum/tractorsDemo/Bounces/PennyArcade_Multitracks/TakeTwo_5/PennyArcade_take5_beats.txt";
114 break;
115
116
117 case 6:
118 roomfilename = "/Users/andrew/Documents/work/Alignment/FunkyDrummerAnalysis/FunkyDrummerBreak.wav";
119 kickfilename = "/Users/andrew/Documents/work/Alignment/FunkyDrummerAnalysis/FunkyDrummerBreak.wav";
120 snarefilename = "/Users/andrew/Documents/work/Alignment/FunkyDrummerAnalysis/FunkyDrummerBreak.wav";
121 sonicVizBeatsFilename = "/Users/andrew/Documents/work/Alignment/FunkyDrummerAnalysis/FunkyDrummerBeats.txt";
122 break;
123
124 case 7:
125 roomfilename = "/Users/andrew/Music/Logic/Tractors_April13/tractorIsaak2/Bounces/Take23_mono.wav";
126 kickfilename = "/Users/andrew/Music/Logic/Tractors_April13/tractorIsaak2/Bounces/Take23_mono.wav";
127 snarefilename = "/Users/andrew/Music/Logic/Tractors_April13/tractorIsaak2/Bounces/Take23_mono.wav";
128 sonicVizBeatsFilename = "/Users/andrew/Music/Logic/Tractors_April13/tractorIsaak2/Bounces/IsaakTake23MonoBeats.txt";
129 break;
92 130
93 131
94 } 132 }
95 if (kickfilename != NULL){ 133 if (kickfilename != NULL){
96 134 printf("Loading Kick file: %s\n", kickfilename);
97 loadAudioTrack(kickfilename, 0); 135 loadAudioTrack(kickfilename, 0);
98 } 136 }
99 137
100 if (roomfilename != NULL){ 138 if (roomfilename != NULL){
101 printf("roomfilename: %s\n", roomfilename); 139 printf("loading room: %s\n", roomfilename);
102 loadAudioTrack(roomfilename, 1); 140 loadAudioTrack(roomfilename, 1);
103 } 141 }
104 142
105 if (snarefilename != NULL) 143 if (snarefilename != NULL){
144 printf("Loading Snare file: %s\n", kickfilename);
106 loadAudioTrack(snarefilename, 2); 145 loadAudioTrack(snarefilename, 2);
146 }
107 147
108 if (sonicVizBeatsFilename.c_str() != NULL){ 148 if (sonicVizBeatsFilename.c_str() != NULL){
149 printf("Reading sonic viz beats: %s\n", sonicVizBeatsFilename.c_str());
109 readInBeatsFile(sonicVizBeatsFilename); 150 readInBeatsFile(sonicVizBeatsFilename);
110 printBeatTimes(); 151 printBeatTimes();
111 checkFileErrors(0); 152 checkFileErrors(0);
112 checkFileErrors(2); 153 checkFileErrors(2);
113 findBeatOnsets(); 154 findBeatOnsets();
155
156 exportErrorInformation();
157 exportExactOnsetTimes();
158
159 exportKickRelativeTempoTimes();
160 exportKickRelativeErrorTimes();
161 exportKickRelativeClickTimes();
162
163 exportDrumTimerTempoTimes();
164 exportDrumTimerErrorTimes();
165 exportDrumTimerClickTimes();
114 } 166 }
115 } 167 }
116 168
117 void RecordedMultipleAudio::loadAudioTrack(std::string name, const int& channel){ 169 void RecordedMultipleAudio::loadAudioTrack(std::string name, const int& channel){
118 //kick - track type 0 170 //kick - track type 0
175 iss.clear(); 227 iss.clear();
176 228
177 229
178 }//end while 230 }//end while
179 231
180 // printBeatTimes(); 232
181 printf("There are %i BEAT annotations\n", (int)beatTimes.size()); 233 printf("There are %i BEAT annotations\n", (int)beatTimes.size());
182 234
183 } 235 }
184 236
185 void RecordedMultipleAudio::printBeatTimes(){ 237 void RecordedMultipleAudio::printBeatTimes(){
189 } 241 }
190 242
191 243
192 void RecordedMultipleAudio::checkFileErrors(int channel){ 244 void RecordedMultipleAudio::checkFileErrors(int channel){
193 int beatIndex = 0; 245 int beatIndex = 0;
194 int cutoff = 50;//ms width to check 246 int cutoff = 60;//ms width to check
195 for (int i = 0;i < loadedAudioFiles[channel].onsetTimesMillis.size();i++){ 247 for (int i = 0;i < loadedAudioFiles[channel].onsetTimesMillis.size();i++){
248
249 printf("onset time %i ms %i frames ", (int)loadedAudioFiles[channel].onsetTimesMillis[i], (int)loadedAudioFiles[channel].onsetTimesFrames[i]);
250
196 while (beatIndex < beatTimes.size() && 1000.0*beatTimes[beatIndex] < loadedAudioFiles[channel].onsetTimesMillis[i] - cutoff) { 251 while (beatIndex < beatTimes.size() && 1000.0*beatTimes[beatIndex] < loadedAudioFiles[channel].onsetTimesMillis[i] - cutoff) {
197 beatIndex++; 252 beatIndex++;
198 } 253 }
199 double error = (1000.0*beatTimes[beatIndex] - loadedAudioFiles[channel].onsetTimesMillis[i]); 254 double error = (1000.0*beatTimes[beatIndex] - loadedAudioFiles[channel].onsetTimesMillis[i]);
200 if (fabs(error) < cutoff){ 255 if (fabs(error) < cutoff){
203 else 258 else
204 printf("Pos: %i Beat Time %f Snare Time %f Error %f\n", beatIndex%4, 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error); 259 printf("Pos: %i Beat Time %f Snare Time %f Error %f\n", beatIndex%4, 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error);
205 260
206 }else{ 261 }else{
207 if (channel == 0) 262 if (channel == 0)
208 printf("Out of Beat: Kick Time %f beat error %f\n", 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error); 263 printf("Ch.0 Out of Beat: Kick Time %f beat error %f\n", 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error);
209 else 264 else
210 printf("Out of Beat: %f Snare Time %f best error %f\n", 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error); 265 printf("Ch.2 Out of Beat: %f Snare Time %f best error %f\n", 1000.0*beatTimes[beatIndex], loadedAudioFiles[0].onsetTimesMillis[i], error);
211 266
212 } 267 }
213 } 268 }
214 } 269 }
215 270
233 for (int k = 0;k < beatTimes.size();k++){ 288 for (int k = 0;k < beatTimes.size();k++){
234 beatFound = false; 289 beatFound = false;
235 double newBeatTime = beatTimes[k]*1000.0; 290 double newBeatTime = beatTimes[k]*1000.0;
236 int beatPosition = k % 4; 291 int beatPosition = k % 4;
237 OnsetInformation information; 292 OnsetInformation information;
293 double bestBeatDifference = 1000;//i.e. high
238 switch (beatPosition) { 294 switch (beatPosition) {
239 case 0: case 2://check for kick when it is on the `one' or 'three' (0 or 2 in our metrical position) 295 case 0: case 2://check for kick when it is on the `one' or 'three' (0 or 2 in our metrical position)
240 // printf("check %i kindex %i\n", beatPosition, kickIndex); 296 // printf("check %i kindex %i\n", beatPosition, kickIndex);
241 while (kickIndex < loadedAudioFiles[0].onsetTimesMillis.size() && loadedAudioFiles[0].onsetTimesMillis[kickIndex] < newBeatTime - cutoff){ 297 while (kickIndex < loadedAudioFiles[0].onsetTimesMillis.size() && loadedAudioFiles[0].onsetTimesMillis[kickIndex] < newBeatTime - cutoff){
242 kickIndex++; 298 kickIndex++;
243 kickTime = loadedAudioFiles[0].onsetTimesMillis[kickIndex]; 299 kickTime = loadedAudioFiles[0].onsetTimesMillis[kickIndex];
244 // printf("checking beat[%i] %f kick %f error %f\n", k, beatTimes[k]*1000.0, kickTime, (kickTime - beatTimes[k]*1000.0)); 300 // printf("checking beat[%i] %f kick %f error %f\n", k, beatTimes[k]*1000.0, kickTime, (kickTime - beatTimes[k]*1000.0));
245 if (fabs(kickTime - beatTimes[k]*1000.0) < cutoff){ 301 if (fabs(kickTime - beatTimes[k]*1000.0) < cutoff && fabs(kickTime - beatTimes[k]*1000.0) < bestBeatDifference){
246 beatFound = true; 302 beatFound = true;
247 printf("beat[%i] %f kick %f error %f\n", k, beatTimes[k]*1000.0, kickTime, (kickTime - beatTimes[k]*1000.0)); 303 printf("beat[%i] pos %i time %f kick %f error %f\n", k, beatPosition, beatTimes[k]*1000.0, kickTime, (kickTime - beatTimes[k]*1000.0));
248 304
249 information.error = (kickTime - beatTimes[k]*1000.0);//FOR NOW ONLY 305 information.error = (kickTime - beatTimes[k]*1000.0);//FOR NOW ONLY
250 information.metricalPosition = beatPosition; 306 information.metricalPosition = beatPosition;
251 information.type = 0; 307 information.type = 0;
252 information.exactOnsetTime = kickTime; 308 information.exactOnsetTime = kickTime;
309 bestBeatDifference = fabs(kickTime - beatTimes[k]*1000.0);
253 // exactBeatPositions.push_back(kickTime); 310 // exactBeatPositions.push_back(kickTime);
254 } 311 }
255 } 312 }
256 313
257 break; 314 break;
258 case 1: case 3://snare 315 case 1: case 3://snare
259 while (snareIndex < loadedAudioFiles[1].onsetTimesMillis.size() && loadedAudioFiles[1].onsetTimesMillis[snareIndex] < newBeatTime - cutoff ){ 316 while (snareIndex < loadedAudioFiles[1].onsetTimesMillis.size() && loadedAudioFiles[1].onsetTimesMillis[snareIndex] < newBeatTime - cutoff ){
260 snareIndex++; 317 snareIndex++;
261 snareTime = loadedAudioFiles[1].onsetTimesMillis[snareIndex]; 318 snareTime = loadedAudioFiles[1].onsetTimesMillis[snareIndex];
262 if (fabs(snareTime - beatTimes[k]*1000.0) < cutoff){ 319 if (fabs(snareTime - beatTimes[k]*1000.0) < cutoff && fabs(snareTime - beatTimes[k]*1000.0) < bestBeatDifference){
263 beatFound = true; 320 beatFound = true;
264 // snareErrors.push_back((beatTimes[k]*1000.0 - snareTime)); 321 // snareErrors.push_back((beatTimes[k]*1000.0 - snareTime));
265 information.error = (snareTime - beatTimes[k]*1000.0); 322 information.error = (snareTime - beatTimes[k]*1000.0);
266 information.metricalPosition = beatPosition;//.push_back(beatPosition); 323 information.metricalPosition = beatPosition;//.push_back(beatPosition);
267 information.type = 1; 324 information.type = 1;
268 information.exactOnsetTime = snareTime; 325 information.exactOnsetTime = snareTime;
269 printf("beat[%i] %f snare %f error %f\n", k, beatTimes[k]*1000.0, snareTime, (snareTime - beatTimes[k]*1000.0)); 326 bestBeatDifference = fabs(snareTime - beatTimes[k]*1000.0);
327 printf("beat[%i] pos %i tim e%f snare %f error %f\n", k, beatPosition, beatTimes[k]*1000.0, snareTime, (snareTime - beatTimes[k]*1000.0));
270 // exactBeatPositions.push_back(snareTime); 328 // exactBeatPositions.push_back(snareTime);
271 } 329 }
272 } 330 }
273 331
274 break; 332 break;
287 }//end for all beat annotations 345 }//end for all beat annotations
288 346
289 correctExactBeatTiming();//get rid of the first onset time 347 correctExactBeatTiming();//get rid of the first onset time
290 348
291 calculateTimingAnalysis(); 349 calculateTimingAnalysis();
350
351
352 //so our exact beat times are then information.exactOnsetTime
292 353
293 } 354 }
294 355
295 #pragma mark -doTimingAnalysis 356 #pragma mark -doTimingAnalysis
296 void RecordedMultipleAudio::correctExactBeatTiming(){ 357 void RecordedMultipleAudio::correctExactBeatTiming(){
318 379
319 getErrorTimesFromAnalysis(); 380 getErrorTimesFromAnalysis();
320 381
321 alternativeKickRelativeAnalysis(); 382 alternativeKickRelativeAnalysis();
322 383
323 exportErrorInformation();
324
325 displayKickRelativeMedianErrors();//NB messes ther order of these 384 displayKickRelativeMedianErrors();//NB messes ther order of these
326 385
327 //this was how we did it in multimatch program 386 //this was how we did it in multimatch program
328 // timer.processPathHistory(); 387 // timer.processPathHistory();
329 // timer.calculateTempoLimits(); 388 // timer.calculateTempoLimits();
337 //gets the errors from the drum timing analyser (i.e. ISMIR paper code) and attributes these to the onsets 396 //gets the errors from the drum timing analyser (i.e. ISMIR paper code) and attributes these to the onsets
338 for (int i = 0;i < drumTimingAnalyser.timingData.size();i++){ 397 for (int i = 0;i < drumTimingAnalyser.timingData.size();i++){
339 onsetInfo[i].error = drumTimingAnalyser.timingData[i][5]; 398 onsetInfo[i].error = drumTimingAnalyser.timingData[i][5];
340 onsetInfo[i].clickTime = drumTimingAnalyser.timingData[i][1] + timingOffset;//this is where teh timing analyser placed the click times 399 onsetInfo[i].clickTime = drumTimingAnalyser.timingData[i][1] + timingOffset;//this is where teh timing analyser placed the click times
341 errorsByMetricalPosition[onsetInfo[i].metricalPosition].push_back(onsetInfo[i].error); 400 errorsByMetricalPosition[onsetInfo[i].metricalPosition].push_back(onsetInfo[i].error);
342 printf("beat %i metrical posn %i exact beat time %f error %i\n", i, onsetInfo[i].metricalPosition, onsetInfo[i].exactOnsetTime, (int)onsetInfo[i].error); 401 printf("beat %i metrical posn %i exact onset time %f click time %i error %i\n", i, onsetInfo[i].metricalPosition, onsetInfo[i].exactOnsetTime,
402 onsetInfo[i].clickTime, (int)onsetInfo[i].error);
343 } 403 }
344 displayMedianErrors(); 404 displayMedianErrors();
345 } 405 }
346 406
347 407
350 //this sees kicks as ON the beat, looks at relative error of the three other beats if we chop the bar evenly 410 //this sees kicks as ON the beat, looks at relative error of the three other beats if we chop the bar evenly
351 411
352 double recentBeatTime, currentTempo; 412 double recentBeatTime, currentTempo;
353 kickRelativeErrors.clear(); 413 kickRelativeErrors.clear();
354 kickRelativeClickTimes.clear(); 414 kickRelativeClickTimes.clear();
415 kickRelativeTempo.clear();
355 416
356 for (int i = 0;i < drumTimingAnalyser.timingData.size();i++){ 417 for (int i = 0;i < drumTimingAnalyser.timingData.size();i++){
357 int beatPosition = i%4; 418 int beatPosition = i%4;
358 if (beatPosition == 0){ 419 if (beatPosition == 0){//then divide kicks and get even division
359 recentBeatTime = onsetInfo[i].exactOnsetTime; 420 recentBeatTime = onsetInfo[i].exactOnsetTime;
360 if (i+4 < onsetInfo.size()) 421 if (i+4 < onsetInfo.size())
361 currentTempo = (onsetInfo[i+4].exactOnsetTime - onsetInfo[i].exactOnsetTime)/4.0; 422 currentTempo = (onsetInfo[i+4].exactOnsetTime - onsetInfo[i].exactOnsetTime)/4.0;
362 printf("new beat time %f tempo %f\n", recentBeatTime, currentTempo); 423 printf("new beat time %f tempo %f\n", recentBeatTime, currentTempo);
363 } 424 }
364 double error = onsetInfo[i].exactOnsetTime - (recentBeatTime + beatPosition*currentTempo); 425 double error = onsetInfo[i].exactOnsetTime - (recentBeatTime + beatPosition*currentTempo);
365 printf("Beat %i KR Predicted Beat %f Actual exact %f KRerror %f DTerror %i\n", beatPosition, (recentBeatTime + beatPosition*currentTempo), onsetInfo[i].exactOnsetTime, error, (int)onsetInfo[i].error); 426 printf("Beat %i KR Predicted Beat: %f Onset: %f KRerror %f DTerror %i\n", beatPosition, (recentBeatTime + beatPosition*currentTempo), onsetInfo[i].exactOnsetTime, error, (int)onsetInfo[i].error);
366 kickRelativeErrors.push_back(error); 427 kickRelativeErrors.push_back(error);
367 kickRelativeClickTimes.push_back(recentBeatTime + beatPosition*currentTempo); 428 kickRelativeClickTimes.push_back(recentBeatTime + beatPosition*currentTempo);
368 } 429 kickRelativeTempo.push_back(currentTempo);
369 } 430 }
370 431 }
371 #pragma label -exportInfo 432
433 #pragma mark -exportInfo
372 void RecordedMultipleAudio::exportErrorInformation(){ 434 void RecordedMultipleAudio::exportErrorInformation(){
373 printf("Export final timing information\n"); 435 printf("Export final timing information\n");
374 436
375 ofstream ofs(infoFilepath.c_str()); 437 ofstream ofs(infoFilepath.c_str());
376 for (int i = 0;i < onsetInfo.size() && kickRelativeErrors.size();i++){// drumTimingAnalyser.timingData.size() 438 for (int i = 0;i < onsetInfo.size() && kickRelativeErrors.size();i++){// drumTimingAnalyser.timingData.size()
379 ofs << kickRelativeClickTimes[i] << "," << kickRelativeErrors[i];//the click and error for beats evenly between kicks 441 ofs << kickRelativeClickTimes[i] << "," << kickRelativeErrors[i];//the click and error for beats evenly between kicks
380 ofs << endl; 442 ofs << endl;
381 } 443 }
382 444
383 } 445 }
446
447
448 void RecordedMultipleAudio::exportExactOnsetTimes(){
449 printf("Export exact beat times\n");
450
451 ofstream ofs(exactOnsetFilePath.c_str());
452 for (int i = 0;i < onsetInfo.size();i++){// drumTimingAnalyser.timingData.size()
453 ofs << onsetInfo[i].exactOnsetTime/1000.0 << endl;
454 if (printExportInfo)
455 printf("exporting exact beat times %f\n", onsetInfo[i].exactOnsetTime);
456 }
457 }
458
459 void RecordedMultipleAudio::exportKickRelativeTempoTimes(){
460 printf("Export kick relative Tempo times\n");
461
462 ofstream ofs(kickRelativeTempoFilePath.c_str());
463 for (int i = 0;i < kickRelativeTempo.size() && i < onsetInfo.size();i++){
464 ofs << onsetInfo[i].exactOnsetTime << "\t" << kickRelativeTempo[i] << endl;
465 if (printExportInfo)
466 printf("exporting tempo[%i]: onset %f %f\n", i, onsetInfo[i].exactOnsetTime, kickRelativeTempo[i]);
467 }
468 }
469
470 void RecordedMultipleAudio::exportKickRelativeErrorTimes(){
471 printf("Export kick relative Error times\n");
472
473 ofstream ofs(kickRelativeErrorsFilePath.c_str());
474 for (int i = 0;i < kickRelativeErrors.size() && i < onsetInfo.size();i++){
475 ofs << onsetInfo[i].exactOnsetTime << "\t" << kickRelativeErrors[i] << endl;
476 if (printExportInfo)
477 printf("exporting tempo[%i]: onset %f %f\n", i, onsetInfo[i].exactOnsetTime, kickRelativeErrors[i]);
478 }
479 }
480
481 void RecordedMultipleAudio::exportKickRelativeClickTimes(){
482 printf("Export kick relative click times\n");
483
484 ofstream ofs(kickRelativeClickFilePath.c_str());
485 for (int i = 0;i < kickRelativeClickTimes.size();i++){
486 ofs << kickRelativeClickTimes[i]/1000.0 << endl;
487 if (printExportInfo)
488 printf("exporting KD click [%i]:%f\n", i,kickRelativeClickTimes[i]);
489 }
490 }
491
492
493 void RecordedMultipleAudio::exportDrumTimerTempoTimes(){
494 printf("Export drum timing tempo times\n");
495
496 ofstream ofs(drumTimerTempoFilePath.c_str());
497 for (int i = 0;i < drumTimingAnalyser.timingData.size() && i < onsetInfo.size();i++){
498 ofs << onsetInfo[i].exactOnsetTime << "\t" << drumTimingAnalyser.timingData[i][0] << endl;
499 if (printExportInfo)
500 printf("exporting tempo[%i]: onset %f tempo %i\n", i, onsetInfo[i].exactOnsetTime, drumTimingAnalyser.timingData[i][0]);
501 }
502 }
503
504
505 void RecordedMultipleAudio::exportDrumTimerErrorTimes(){
506 printf("Export drum timing Error times\n");
507
508 ofstream ofs(drumTimerErrorsFilePath.c_str());
509 for (int i = 0;i < drumTimingAnalyser.timingData.size() && i < onsetInfo.size();i++){
510 ofs << onsetInfo[i].exactOnsetTime << "\t" << drumTimingAnalyser.timingData[i][5] << endl;
511 if (printExportInfo)
512 printf("exporting [%i]: onset %f error %i\n", i, onsetInfo[i].exactOnsetTime, drumTimingAnalyser.timingData[i][5]);
513 }
514 }
515
516
517 void RecordedMultipleAudio::exportDrumTimerClickTimes(){
518 printf("Export drum timing Click times\n");
519
520 ofstream ofs(drumTimerClickFilePath.c_str());
521 for (int i = 0;i < onsetInfo.size();i++){
522 ofs << onsetInfo[i].clickTime/1000.0 << endl;
523 if (printExportInfo)
524 printf("exporting click[%i] %i\n", i, onsetInfo[i].clickTime);
525 }
526 }
527
528
529
530
531
532
384 533
385 void RecordedMultipleAudio::printKickRelativeErrors(){ 534 void RecordedMultipleAudio::printKickRelativeErrors(){
386 for (int i = 0;i < kickRelativeErrors.size();i++){ 535 for (int i = 0;i < kickRelativeErrors.size();i++){
387 printf("KR error [%i] : %.1f\n", i, kickRelativeErrors[i]); 536 printf("KR error [%i] : %.1f\n", i, kickRelativeErrors[i]);
388 } 537 }
454 loadedAudioFiles[i].draw(); 603 loadedAudioFiles[i].draw();
455 } 604 }
456 } else { 605 } else {
457 drumTimingAnalyser.drawTempoCurve(); 606 drumTimingAnalyser.drawTempoCurve();
458 } 607 }
608
609 // ofDrawBitmapString(ofToString(playPositionSeconds),20, 40);
459 } 610 }
460 611
461 #pragma mark -update 612 #pragma mark -update
462 void RecordedMultipleAudio::updatePosition(){ 613 void RecordedMultipleAudio::updatePosition(){
463 for (int i = 0;i < numberOfAudioTracks;i++) 614 for (int i = 0;i < numberOfAudioTracks;i++)
464 loadedAudioFiles[i].updateToPlayPosition(); 615 loadedAudioFiles[i].updateToPlayPosition();
616
617 playPositionSeconds = samplesToSeconds(loadedAudioFiles[0].fileLoader.audioHolder.playPosition);
618 drumTimingAnalyser.updatePlayIndex(playPositionSeconds);
619
620
621 }
622
623 double RecordedMultipleAudio::samplesToSeconds(const double& samples){
624 return samples/44100.0;
465 } 625 }
466 626
467 void RecordedMultipleAudio::updatePositionToMillis(const double& millis){ 627 void RecordedMultipleAudio::updatePositionToMillis(const double& millis){
468 for (int i = 0;i < numberOfAudioTracks;i++) 628 for (int i = 0;i < numberOfAudioTracks;i++)
469 loadedAudioFiles[i].updateToMillisPosition(millis); 629 loadedAudioFiles[i].updateToMillisPosition(millis);
471 631
472 void RecordedMultipleAudio::updatePlaybackPositionToMillis(const double& millis){ 632 void RecordedMultipleAudio::updatePlaybackPositionToMillis(const double& millis){
473 for (int i = 0;i < numberOfAudioTracks;i++) 633 for (int i = 0;i < numberOfAudioTracks;i++)
474 loadedAudioFiles[i].updatePlaybackPositionToMillis(millis); 634 loadedAudioFiles[i].updatePlaybackPositionToMillis(millis);
475 } 635 }
476
477 void RecordedMultipleAudio::switchScreens(){
478 for (int i = 0;i < numberOfAudioTracks;i++)
479 loadedAudioFiles[i].switchScreens();
480 }
481
482 636
483 void RecordedMultipleAudio::togglePlay(){ 637 void RecordedMultipleAudio::togglePlay(){
484 for (int i = 0;i < numberOfAudioTracks;i++) 638 for (int i = 0;i < numberOfAudioTracks;i++)
485 loadedAudioFiles[i].togglePlay(); 639 loadedAudioFiles[i].togglePlay();
486 } 640 }
494 void RecordedMultipleAudio::printInfo(){ 648 void RecordedMultipleAudio::printInfo(){
495 loadedAudioFiles[0].fileLoader.onsetDetect.printChromaInfo(); 649 loadedAudioFiles[0].fileLoader.onsetDetect.printChromaInfo();
496 loadedAudioFiles[0].printEvents(); 650 loadedAudioFiles[0].printEvents();
497 } 651 }
498 652
653 #pragma mark -ScreenFunctions
499 void RecordedMultipleAudio::windowResized(const int& w, const int& h){ 654 void RecordedMultipleAudio::windowResized(const int& w, const int& h){
500 for (int i = 0;i < numberOfAudioTracks;i++) 655 for (int i = 0;i < numberOfAudioTracks;i++)
501 loadedAudioFiles[i].windowResized(w, h); 656 loadedAudioFiles[i].windowResized(w, h);
502 } 657 }
503 658
520 if (drawWindow == 1) 675 if (drawWindow == 1)
521 drumTimingAnalyser.zoomOut();//numberOfPointsPerPage *= 2; 676 drumTimingAnalyser.zoomOut();//numberOfPointsPerPage *= 2;
522 677
523 } 678 }
524 679
525 680 void RecordedMultipleAudio::switchScreens(){
681 for (int i = 0;i < numberOfAudioTracks;i++)
682 loadedAudioFiles[i].switchScreens();
683 }
684