2016-09-14 2 views
0

수신자 콜백이 MIDI 메시지 및 패킷을 건너 뛰고있는 것 같아서 iOS 앱에 MIDI를 구현하는 데 문제가 있습니다. 내가 누락되거나 건너 뛰는 MIDI 메시지를 확인하기 위해 Midi Monitor을 사용하고 있습니다.iOS CoreMIDI 건너 뛰는 MidiPackets

그래서 iOS가 특정 MIDI 메시지를 건너 뛰는 이유는 무엇입니까? 때로는 MIDI 메시지는 건너 뛰지 않지만 다른 경우에는 건너 뜁니다. 이 시점에서 내 뇌를 다 써 버렸으므로 디버깅에 어떻게 접근해야할지 모르겠습니다.

내 수신기 코드 :

void MidiReceiver(const MIDIPacketList *packets, 
        void *context, void *sourceContext) { 
    dispatch_async(dispatch_get_main_queue(), ^{ 
    if (packets->numPackets > 0) { 
     MIDIPacket *packet = (MIDIPacket *)packets->packet; 

     // Loop through total number of packets 
     for (int i = 0; i < packets->numPackets; i++) { 
      // Go through each packet, iOS sometimes clumps all data into one packet 
      // if the MIDI messages are triggered at the same time 
      for (int j = 0; j < packet->length; j += 3) { 
       NSArray *array = [[NSArray alloc] initWithObjects:[NSNumber numberWithUnsignedInt:packet->data[j]], 
            [NSNumber numberWithUnsignedInt:packet->data[j+1]], 
            [NSNumber numberWithUnsignedInt:packet->data[j+2]], nil]; 

       // Use the data to create do meaningful in the app 
       [myViewController processMidiData:array]; 
      } 

      // Next packet 
      packet = MIDIPacketNext(packet); 
     } 
    } 
}); 

모니터 코드 형식은 다음과 같습니다 (TIME) - (MIDI 명령 형식) - (CC 발 또는 속도)

미디 모니터 디버그 :

12:45:32.697 Control 0 
12:45:32.720 Control 1 
12:45:32.737 Control 1 
12:45:32.740 Control 2 
12:45:32.750 Control 3 
12:45:32.763 Note Off A♯1 0 
12:45:32.763 Note Off F2 0 
12:45:32.763 Note Off D3 0 
12:45:32.763 Control 4 
12:45:32.770 Control 5 
12:45:32.780 Control 6 
12:45:32.790 Control 8 
12:45:32.800 Control 9 
12:45:32.810 Control 11 
12:45:32.820 Control 13 
12:45:32.832 Control 14 
12:45:32.845 Control 16 
12:45:32.850 Control 18 
12:45:32.873 Control 21 
12:45:32.883 Control 22 
12:45:32.898 Control 24 
12:45:32.913 Control 26 
12:45:32.933 Control 27 
12:45:32.948 Control 28 
12:45:33.020 Control 27 
12:45:33.030 Control 26 
12:45:33.040 Control 25 
12:45:33.050 Control 24 
12:45:33.060 Control 22 

내 앱의 디버그 모니터 :

12:45:33.050 Control 0 
12:45:33.051 Control 1 
12:45:33.051 Control 1 
12:45:33.051 Control 2 
12:45:33.051 Control 3 
12:45:33.083 Note Off D3 0  <----- Where's A#1 and F2!!! :(
12:45:33.087 Control 4 
12:45:33.087 Control 4 
12:45:33.097 Control 5 
12:45:33.100 Control 6 
12:45:33.110 Control 8 
12:45:33.120 Control 9 
12:45:33.130 Control 11 
12:45:33.140 Control 13 
12:45:33.153 Control 14 
12:45:33.165 Control 16 
12:45:33.170 Control 18 
12:45:33.193 Control 21 
12:45:33.203 Control 22 
12:45:33.218 Control 24 
12:45:33.233 Control 26 
12:45:33.256 Control 27 
12:45:33.268 Control 28 
12:45:33.341 Control 27 
12:45:33.351 Control 26 
12:45:33.361 Control 25 
12:45:33.374 Control 24 
12:45:33.381 Control 22 

답변

1

Kurt Revis에서 도움을 얻었으며 dispatch_async의 사용으로 인해 패킷을 너무 늦게 보내고있는 것처럼 보였습니다.

void MidiReceiver(const MIDIPacketList *packets, 
       void *context, void *sourceContext) { 

    NSMutableArray *packetData = [[NSMutableArray alloc] init]; 

    if (packets->numPackets > 0 && object != nil) { 
     MIDIPacket *packet = &packets->packet[0]; 
     // Loop through total number of packets 
     for (int i = 0; i < packets->numPackets; ++i) { 
      int idx = 0; 
      while (idx < packet->length) { 
       NSArray *array = [[NSArray alloc] initWithObjects:[NSNumber numberWithUnsignedInt:packet->data[idx]], 
            [NSNumber numberWithUnsignedInt:packet->data[idx+1]], 
            [NSNumber numberWithUnsignedInt:packet->data[idx+2]], nil]; 

       [packetData addObject:array]; 
       idx += 3; 
      } 
      packet = MIDIPacketNext(packet); 
     } 
    } 

    dispatch_async(dispatch_get_main_queue(), ^{ 
     for (NSArray *packet in packetData) { 
      [object receiveMIDIInput:packet]; 
     } 
    }); 
} 
:

내 수정 코드 (I 먼저 패킷을 구문 분석)