comparison hackday/testApp.cpp @ 27:fa1890efa044

close to final version on HackDay
author Andrew N Robertson <andrew.robertson@eecs.qmul.ac.uk>
date Sun, 04 Dec 2011 14:30:33 +0000
parents 179365726f07
children 49a5b023df1e
comparison
equal deleted inserted replaced
26:179365726f07 27:fa1890efa044
1 #include "testApp.h" 1 #include "testApp.h"
2 2
3
4 testApp::testApp(ofxArgs* args){
5 this->args = args;
6 }
7
3 //-------------------------------------------------------------- 8 //--------------------------------------------------------------
4 void testApp::setup(){ 9 void testApp::setup(){
10
11
12 this->args->printArgs();
13 this->args->printOpts();
5 midiFileName = "../../../data/frerejacques.mid"; 14 midiFileName = "../../../data/frerejacques.mid";
15
16 if (this->args->getCount() > 0){
17 museScoreFilename = this->args->getString(1);
18 //printf("MUSESCORE FILENAME IS %s\n", museScoreFilename);
19 cout << "running!! " << museScoreFilename << endl;
20 midiFileName = museScoreFilename;
21 }
22
6 int retVal = cannamMainFunction(); 23 int retVal = cannamMainFunction();
7 24
8 cout << "MIDI INPUT EXAMPLE" << endl;
9 printf("midi in in in");
10 ofSetVerticalSync(true); 25 ofSetVerticalSync(true);
11 //ofBackground(255,255,255); 26 //ofBackground(255,255,255);
12 27 midiPort = 2;
13 midiIn.listPorts(); 28 midiIn.listPorts();
14 midiIn.openPort(2); 29 midiIn.openPort(midiPort);
30 midiPortName = "";
31 //midiPortName = midiIn.portNames(midiPort);
15 32
16 transpose = 12; 33 transpose = 12;
17 noteInStream.transposeVal = &transpose; 34 noteInStream.transposeVal = &transpose;
18 35
19 noteInStream.startTime = &midiEvents.startTime;//point start time of note in stream to the same time in MIDI events 36 noteInStream.startTime = &midiEvents.startTime;//point start time of note in stream to the same time in MIDI events
27 44
28 45
29 //midiIn.addListener(this); 46 //midiIn.addListener(this);
30 ofAddListener(midiIn.newMessageEvent, this, &testApp::newMessage); 47 ofAddListener(midiIn.newMessageEvent, this, &testApp::newMessage);
31 48
32 49
50 verdana30.loadFont("verdana.ttf", 50, true, true);
51 verdana30.setLineHeight(48.0f);
52 verdana30.setLetterSpacing(1.035);
33 53
34 playing = false; 54 playing = false;
35 55
36 56
37 receiver.setup( PORT ); 57 receiver.setup( PORT );
45 midiEvents.drawTempoMode = false; 65 midiEvents.drawTempoMode = false;
46 ofSetFrameRate(30); 66 ofSetFrameRate(30);
47 67
48 midiEvents.ticksPerScreen += 4000; 68 midiEvents.ticksPerScreen += 4000;
49 lastScoreIndexSent = 0; 69 lastScoreIndexSent = 0;
50 performanceRating = 1.0; 70 performanceRating = 0.0;
71
72 liveInputPlaying = false;
73 lastScoreIndexSent = 0;
74 midiEvents.bestMatchIndex = 0;
51 75
52 } 76 }
53 77
54 //-------------------------------------------------------------- 78 //--------------------------------------------------------------
55 void testApp::update(){ 79 void testApp::update(){
155 179
156 while (lastMeasureSent < midiEvents.measureVector.size() && midiEvents.measureVector[lastMeasureSent] < ticks) { 180 while (lastMeasureSent < midiEvents.measureVector.size() && midiEvents.measureVector[lastMeasureSent] < ticks) {
157 lastMeasureSent++; 181 lastMeasureSent++;
158 } 182 }
159 if (lastMeasureSent != tmpMeasure){ 183 if (lastMeasureSent != tmpMeasure){
160 sendMeasureToMuseScore(); 184 //sendMeasureToMuseScore();
161 performanceRating = noteInStream.calculateTotalScore(midiEvents); 185 performanceRating = noteInStream.calculateTotalScore(midiEvents);
162 } 186 }
163 187
164 188
165 } 189 }
184 string noteString; 208 string noteString;
185 noteString = "blackNotes.js"; 209 noteString = "blackNotes.js";
186 m.addStringArg( noteString); 210 m.addStringArg( noteString);
187 sender.sendMessage( m ); 211 sender.sendMessage( m );
188 */ 212 */
189 213 sendNoteDataByOsc(pitch, ticks);
214
215 // /color-note 60,3440
216
217 //crappy javascript message
218 /*
190 ofxOscMessage m; 219 ofxOscMessage m;
191 m.setAddress( "/plugin" ); 220 m.setAddress( "/plugin" );
192 string noteString; 221 string noteString;
193 noteString = "coloronenote.js"; 222 noteString = "coloronenote.js";
194 noteString += ",myTick,"+ofToString(ticks)+",myPitch,"+ofToString(pitch); 223 noteString += ",myTick,"+ofToString(ticks)+",myPitch,"+ofToString(pitch);
195 // printf("%s\n", noteString); 224 // printf("%s\n", noteString);
196 m.addStringArg( noteString); 225 m.addStringArg( noteString);
197 sender.sendMessage( m ); 226 sender.sendMessage( m ); */
198 /* 227
199 m.addStringArg( "coloronenote.js" );
200 m.addStringArg("mytick");
201 m.addIntArg( ticks );
202 m.addStringArg("mypitch");
203 m.addIntArg( pitch);
204 */
205 228
206 // /plugin coloronenote.js mytick 100 mypitch 56; 229 // /plugin coloronenote.js mytick 100 mypitch 56;
207 } 230 }
208 231
209 232 void testApp::sendNoteDataByOsc(const int& pitch, const int& ticks){
233 ofxOscMessage m;
234 m.setAddress( "/color-note" );
235 string noteString;
236 noteString = ofToString(ticks);
237 noteString += ","+ofToString(pitch);
238 m.addStringArg( noteString);
239 sender.sendMessage( m );
240 }
210 241
211 void testApp::sendMeasureToMuseScore(){ 242 void testApp::sendMeasureToMuseScore(){
212 243
213 printf("sending measure to muse score %i \n", lastMeasureSent); 244 printf("sending measure to muse score %i \n", lastMeasureSent);
214 245
262 string info = "Measure "; 293 string info = "Measure ";
263 info += ofToString(lastMeasureSent); 294 info += ofToString(lastMeasureSent);
264 info += " Last note "; 295 info += " Last note ";
265 info += ofToString(lastScoreIndexSent); 296 info += ofToString(lastScoreIndexSent);
266 297
298 ofSetHexColor(0xFF0000);
299 // ofDrawBitmapString(info, 20, 20);
300 midiEvents.drawMidiFile(noteInStream.midiInputEvents);
301
302 // ofDrawBitmapString("Rating "+ofToString(performanceRating*100), 60, 50);
303 //ofDrawBitmapString("filename "+museScoreFilename, 20, 80);
304 string ratingString = ofToString(performanceRating*100,0)+"%";
305 if (performanceRating > 0.84)
306 ratingString += "!* *";
307 string extraText = "";
308 if (performanceRating > 0.9){
309 extraText += " pretty good, huh?";
310 }
311 if (performanceRating > 0.95)
312 extraText = " blimey! ";
313 if (performanceRating > 0.97)
314 extraText = " maestro!";
315
316 ratingString += extraText;
317 verdana30.drawString(ratingString, 20, 60);
318
267 ofSetHexColor(0x000000); 319 ofSetHexColor(0x000000);
268 ofDrawBitmapString(info, 20, 20); 320 ofDrawBitmapString(midiPortName, 20, ofGetHeight() - 20);
269 midiEvents.drawMidiFile(noteInStream.midiInputEvents); 321
270
271 ofDrawBitmapString("Rating "+ofToString(performanceRating*100), 20, 50);
272 } 322 }
273 323
274 //-------------------------------------------------------------- 324 //--------------------------------------------------------------
275 void testApp::keyPressed(int key){ 325 void testApp::keyPressed(int key){
276 326
327 if (key == '.'){
328 midiPort++;
329 midiIn.openPort(midiPort);
330 }
331
332 if (key == ',' && midiPort > 0){
333 midiPort--;
334 midiIn.openPort(midiPort);
335 }
277 336
278 // if (key == ' '){ 337 // if (key == ' '){
279 // startPlaying(); 338 // startPlaying();
280 // } 339 // }
281 if (key == '-') 340 if (key == '-')
290 timenow *= -1; 349 timenow *= -1;
291 timenow += ofGetElapsedTimeMillis(); 350 timenow += ofGetElapsedTimeMillis();
292 printf("CROSS UPDATE TOOK %f", timenow); 351 printf("CROSS UPDATE TOOK %f", timenow);
293 } 352 }
294 353
354 if (key == 'x')
355 sendNoteDataByOsc(60, 0);
356
295 if (key == OF_KEY_LEFT){ 357 if (key == OF_KEY_LEFT){
296 358
297 } 359 }
298 360
299 if (key == OF_KEY_RIGHT) 361 if (key == OF_KEY_RIGHT)
352 sendBlackNotes(); 414 sendBlackNotes();
353 lastScoreIndexSent = 0; 415 lastScoreIndexSent = 0;
354 416
355 } 417 }
356 418
357 if (key == 'o'){ 419 if (key == 'o' || key == 'O'){
358 //open audio file 420 //open audio file
359 string *filePtr; 421 string *filePtr;
360 filePtr = &midiFileName; 422 filePtr = &midiFileName;
361 423
362 if (getFilenameFromDialogBox(filePtr)){ 424 if (getFilenameFromDialogBox(filePtr)){
474 }//new end of load function 536 }//new end of load function
475 537
476 538
477 539
478 540
479 //trying to port to new class
480 /*
481 MIDIFileReader fr(filename);
482
483 if (!fr.isOK()) {
484 std::cerr << "Error: " << fr.getError().c_str() << std::endl;
485 return 1;
486 }
487
488 MIDIComposition c = fr.load();
489
490 switch (fr.getFormat()) {
491 case MIDI_SINGLE_TRACK_FILE: cout << "Format: MIDI Single Track File" << endl; break;
492 case MIDI_SIMULTANEOUS_TRACK_FILE: cout << "Format: MIDI Simultaneous Track File" << endl; break;
493 case MIDI_SEQUENTIAL_TRACK_FILE: cout << "Format: MIDI Sequential Track File" << endl; break;
494 default: cout << "Format: Unknown MIDI file format?" << endl; break;
495 }
496
497 cout << "Tracks: " << c.size() << endl;
498
499 int td = fr.getTimingDivision();
500 if (td < 32768) {
501 cout << "Timing division: " << fr.getTimingDivision() << " ppq" << endl;
502
503 midiEvents.pulsesPerQuarternote = fr.getTimingDivision();
504 } else {
505 int frames = 256 - (td >> 8);
506 int subframes = td & 0xff;
507 cout << "SMPTE timing: " << frames << " fps, " << subframes << " subframes" << endl;
508 }
509
510 for (MIDIComposition::const_iterator i = c.begin(); i != c.end(); ++i) {
511
512 cout << "Start of track: " << i->first+1 << endl;
513
514 for (MIDITrack::const_iterator j = i->second.begin(); j != i->second.end(); ++j) {
515
516 unsigned int t = j->getTime();
517 int ch = j->getChannelNumber();
518
519 if (j->isMeta()) {
520 int code = j->getMetaEventCode();
521 string name;
522 bool printable = true;
523 switch (code) {
524
525 case MIDI_END_OF_TRACK:
526 cout << t << ": End of track" << endl;
527 break;
528
529 case MIDI_TEXT_EVENT: name = "Text"; break;
530 case MIDI_COPYRIGHT_NOTICE: name = "Copyright"; break;
531 case MIDI_TRACK_NAME: name = "Track name"; break;
532 case MIDI_INSTRUMENT_NAME: name = "Instrument name"; break;
533 case MIDI_LYRIC: name = "Lyric"; break;
534 case MIDI_TEXT_MARKER: name = "Text marker"; break;
535 case MIDI_SEQUENCE_NUMBER: name = "Sequence number"; printable = false; break;
536 case MIDI_CHANNEL_PREFIX_OR_PORT: name = "Channel prefix or port"; printable = false; break;
537 case MIDI_CUE_POINT: name = "Cue point"; break;
538 case MIDI_CHANNEL_PREFIX: name = "Channel prefix"; printable = false; break;
539 case MIDI_SEQUENCER_SPECIFIC: name = "Sequencer specific"; printable = false; break;
540 case MIDI_SMPTE_OFFSET: name = "SMPTE offset"; printable = false; break;
541
542 case MIDI_SET_TEMPO:
543 {
544 int m0 = j->getMetaMessage()[0];
545 int m1 = j->getMetaMessage()[1];
546 int m2 = j->getMetaMessage()[2];
547 long tempo = (((m0 << 8) + m1) << 8) + m2;
548
549 cout << t << ": Tempo: " << 60000000.0 / double(tempo) << endl;
550 midiEvents.tempo = 60000000.0 / double(tempo);
551 midiEvents.period = double(tempo)/1000.0;
552
553 printf("period double is %f\n", midiEvents.period);
554 }
555 break;
556
557 case MIDI_TIME_SIGNATURE:
558 {
559 int numerator = j->getMetaMessage()[0];
560 int denominator = 1 << (int)j->getMetaMessage()[1];
561
562 cout << t << ": Time signature: " << numerator << "/" << denominator << endl;
563 }
564
565 case MIDI_KEY_SIGNATURE:
566 {
567 int accidentals = j->getMetaMessage()[0];
568 int isMinor = j->getMetaMessage()[1];
569 bool isSharp = accidentals < 0 ? false : true;
570 accidentals = accidentals < 0 ? -accidentals : accidentals;
571 cout << t << ": Key signature: " << accidentals << " "
572 << (isSharp ?
573 (accidentals > 1 ? "sharps" : "sharp") :
574 (accidentals > 1 ? "flats" : "flat"))
575 << (isMinor ? ", minor" : ", major") << endl;
576 }
577
578 }
579
580
581 if (name != "") {
582 if (printable) {
583 cout << t << ": File meta event: code " << code
584 << ": " << name << ": \"" << j->getMetaMessage()
585 << "\"" << endl;
586 } else {
587 cout << t << ": File meta event: code " << code
588 << ": " << name << ": ";
589 for (int k = 0; k < j->getMetaMessage().length(); ++k) {
590 cout << (int)j->getMetaMessage()[k] << " ";
591 }
592 }
593 }
594 continue;
595 }
596
597 switch (j->getMessageType()) {
598
599 case MIDI_NOTE_ON:
600 cout << t << ": Note: channel " << ch
601 << " duration " << j->getDuration()
602 << " pitch " << j->getPitch()
603 << " velocity " << j->getVelocity()
604 << "event time " << midiEvents.getEventTimeMillis(t) << endl;
605 v.clear();
606 v.push_back(t);
607 v.push_back(j->getPitch());
608 v.push_back(j->getVelocity());
609 v.push_back(j->getDuration());
610 midiEvents.recordedNoteOnMatrix.push_back(v);
611 midiEvents.recordedEventTimes.push_back(midiEvents.getEventTimeMillis(t));
612 break;
613
614 case MIDI_POLY_AFTERTOUCH:
615 cout << t << ": Polyphonic aftertouch: channel " << ch
616 << " pitch " << j->getPitch()
617 << " pressure " << j->getData2() << endl;
618 break;
619
620 case MIDI_CTRL_CHANGE:
621 {
622 int controller = j->getData1();
623 string name;
624 switch (controller) {
625 case MIDI_CONTROLLER_BANK_MSB: name = "Bank select MSB"; break;
626 case MIDI_CONTROLLER_VOLUME: name = "Volume"; break;
627 case MIDI_CONTROLLER_BANK_LSB: name = "Bank select LSB"; break;
628 case MIDI_CONTROLLER_MODULATION: name = "Modulation wheel"; break;
629 case MIDI_CONTROLLER_PAN: name = "Pan"; break;
630 case MIDI_CONTROLLER_SUSTAIN: name = "Sustain"; break;
631 case MIDI_CONTROLLER_RESONANCE: name = "Resonance"; break;
632 case MIDI_CONTROLLER_RELEASE: name = "Release"; break;
633 case MIDI_CONTROLLER_ATTACK: name = "Attack"; break;
634 case MIDI_CONTROLLER_FILTER: name = "Filter"; break;
635 case MIDI_CONTROLLER_REVERB: name = "Reverb"; break;
636 case MIDI_CONTROLLER_CHORUS: name = "Chorus"; break;
637 case MIDI_CONTROLLER_NRPN_1: name = "NRPN 1"; break;
638 case MIDI_CONTROLLER_NRPN_2: name = "NRPN 2"; break;
639 case MIDI_CONTROLLER_RPN_1: name = "RPN 1"; break;
640 case MIDI_CONTROLLER_RPN_2: name = "RPN 2"; break;
641 case MIDI_CONTROLLER_SOUNDS_OFF: name = "All sounds off"; break;
642 case MIDI_CONTROLLER_RESET: name = "Reset"; break;
643 case MIDI_CONTROLLER_LOCAL: name = "Local"; break;
644 case MIDI_CONTROLLER_ALL_NOTES_OFF: name = "All notes off"; break;
645 }
646 cout << t << ": Controller change: channel " << ch
647 << " controller " << j->getData1();
648 if (name != "") cout << " (" << name << ")";
649 cout << " value " << j->getData2() << endl;
650 }
651 break;
652
653 case MIDI_PROG_CHANGE:
654 cout << t << ": Program change: channel " << ch
655 << " program " << j->getData1() << endl;
656 break;
657
658 case MIDI_CHNL_AFTERTOUCH:
659 cout << t << ": Channel aftertouch: channel " << ch
660 << " pressure " << j->getData1() << endl;
661 break;
662
663 case MIDI_PITCH_BEND:
664 cout << t << ": Pitch bend: channel " << ch
665 << " value " << (int)j->getData2() * 128 + (int)j->getData1() << endl;
666 break;
667
668 case MIDI_SYSTEM_EXCLUSIVE:
669 cout << t << ": System exclusive: code "
670 << (int)j->getMessageType() << " message length " <<
671 j->getMetaMessage().length() << endl;
672 break;
673
674
675 }
676
677
678 }
679
680
681 }
682
683 }//end cannam midi main
684
685 */
686
687