andrew@24
|
1 /*
|
andrew@24
|
2 * MidiInputStream.cpp
|
andrew@24
|
3 * MuseScoreMidiFollower
|
andrew@24
|
4 *
|
andrew@24
|
5 * Created by Andrew on 03/12/2011.
|
andrew@24
|
6 * Copyright 2011 QMUL. All rights reserved.
|
andrew@24
|
7 *
|
andrew@24
|
8 */
|
andrew@24
|
9
|
andrew@24
|
10 #include "MidiInputStream.h"
|
andrew@24
|
11
|
andrew@24
|
12
|
andrew@24
|
13 MidiInputStream::MidiInputStream(){
|
andrew@24
|
14 reset();
|
andrew@24
|
15 }
|
andrew@24
|
16
|
andrew@24
|
17
|
andrew@24
|
18 void MidiInputStream::reset(){
|
andrew@26
|
19
|
andrew@24
|
20 midiInputEvents.clear();
|
andrew@26
|
21 midiInputTimes.clear();
|
andrew@26
|
22
|
andrew@24
|
23 eventTimesForNote.clear();
|
andrew@24
|
24 eventTimesForNote.assign (127, 0.0);
|
andrew@26
|
25
|
andrew@26
|
26
|
andrew@26
|
27 totalNotesRecievedByPitch.clear();
|
andrew@26
|
28 totalNotesRecievedByPitch.assign (127, 0);
|
andrew@26
|
29
|
andrew@24
|
30 }
|
andrew@24
|
31
|
andrew@24
|
32 bool MidiInputStream::noteInReceived(ofxMidiEventArgs &args){
|
andrew@24
|
33 // printf("midi input received port %i, channel %i status %i, byteOne %i, byteTwo %i\n", args.port,args.channel, args.status, newPitch, args.byteTwo);
|
andrew@24
|
34 bool noteOn = false;
|
andrew@24
|
35 int newPitch;
|
andrew@24
|
36 switch (args.status) {
|
andrew@24
|
37
|
andrew@24
|
38 case 144:
|
andrew@24
|
39 newPitch = (int)args.byteOne;
|
andrew@24
|
40 newPitch += (*transposeVal);
|
andrew@24
|
41
|
andrew@25
|
42 // printf("note on %i", args.byteOne);
|
andrew@24
|
43 if (args.byteTwo){
|
andrew@25
|
44 // printf("volume is %i\n", args.byteTwo);
|
andrew@24
|
45 double time = ofGetElapsedTimeMillis();
|
andrew@24
|
46 eventTimesForNote[newPitch] = time;
|
andrew@24
|
47 noteOn = true;
|
andrew@26
|
48 newNoteCounted(newPitch);
|
andrew@24
|
49
|
andrew@24
|
50 }else{
|
andrew@24
|
51 double time = ofGetElapsedTimeMillis();
|
andrew@24
|
52 time -= eventTimesForNote[newPitch];
|
andrew@26
|
53 // printf(", NOTE OFF after %f millis %f ticks\n", time, time * (*factor));
|
andrew@24
|
54
|
andrew@24
|
55 int index = endNote(newPitch);
|
andrew@25
|
56 //correct the length of note time
|
andrew@25
|
57 if (midiInputEvents[index].size() > 2)
|
andrew@25
|
58 midiInputEvents[index][3] = (time * (*factor));
|
andrew@24
|
59 }
|
andrew@24
|
60
|
andrew@24
|
61 break;
|
andrew@24
|
62 default:
|
andrew@24
|
63 break;
|
andrew@24
|
64 }
|
andrew@24
|
65
|
andrew@24
|
66 return noteOn;
|
andrew@24
|
67 //cout << "MIDI message [port: " << args.port << ", channel: " << args.channel << ", status: " << args.status << ", byteOne: " << newPitch << ", byteTwo: " << args.byteTwo << ", timestamp: " << args.timestamp << "]" << endl;
|
andrew@24
|
68 }
|
andrew@24
|
69
|
andrew@26
|
70 void MidiInputStream::newNoteCounted(const int& pitch){
|
andrew@26
|
71 totalNotesRecievedByPitch[pitch] += 1;
|
andrew@26
|
72 }
|
andrew@24
|
73
|
andrew@24
|
74 int MidiInputStream::endNote(int notePitch){
|
andrew@24
|
75 int index = midiInputEvents.size()-1;
|
andrew@24
|
76 while (index > 0 && midiInputEvents[index][1] != notePitch){
|
andrew@24
|
77 index--;
|
andrew@24
|
78 }
|
andrew@25
|
79 // printf("found index %i\n", index);
|
andrew@24
|
80 return index;
|
andrew@24
|
81 }
|
andrew@24
|
82
|
andrew@26
|
83 double MidiInputStream::calculateTotalScore(midiEventHolder& midiEvents){
|
andrew@26
|
84 double gameScore = 1.0;
|
andrew@26
|
85 double totalNotes = 1.0;
|
andrew@26
|
86 if (totalNotesRecievedByPitch.size() > 100){
|
andrew@26
|
87 for (int i = 30;i < 90;i++){
|
andrew@26
|
88 gameScore += abs(totalNotesRecievedByPitch[i] - midiEvents.recordedTotalNoteCounterByPitch[i]);
|
andrew@26
|
89 totalNotes += midiEvents.recordedTotalNoteCounterByPitch[i];
|
andrew@26
|
90 }
|
andrew@26
|
91 }
|
andrew@26
|
92 return 1.0 - (gameScore / totalNotes);
|
andrew@26
|
93
|
andrew@26
|
94 }
|
andrew@26
|
95
|
andrew@24
|
96 void MidiInputStream::printNotes(){
|
andrew@24
|
97 printf("live input \n");
|
andrew@24
|
98 for (int i = 0;i < midiInputEvents.size();i++){
|
andrew@24
|
99 printf("ticktime %i :: pitch %i @ millis %f\n", midiInputEvents[i][0], midiInputEvents[i][1], midiInputTimes[i]);
|
andrew@24
|
100 }
|
andrew@24
|
101 }
|
andrew@26
|
102
|
andrew@26
|
103 void MidiInputStream::printTotalCount(){
|
andrew@26
|
104 for (int i = 0;i < totalNotesRecievedByPitch.size();i++){
|
andrew@26
|
105 printf("LIVE PLAYED TOTAL[%i] := %i\n", i, totalNotesRecievedByPitch[i]);
|
andrew@26
|
106 }
|
andrew@26
|
107 }
|
andrew@24
|
108
|