Re: Calling MIDIPacketListAdd from NSTimer
Re: Calling MIDIPacketListAdd from NSTimer
- Subject: Re: Calling MIDIPacketListAdd from NSTimer
- From: Tom Jeffries <email@hidden>
- Date: Wed, 12 Oct 2011 09:41:24 -0700
Thanks for the information, Brian. I'm glad to know all the time I've
spent on MIDI packets has not been wasted.
A question for you, Doug, and anybody else- the documentation on MIDI
packets seems very sparse! The MIDI services reference has sparse
documentation for MIDIPacketListAdd, MIDIPacketListInit, and
MIDIPacketNext (I'm still not sure how or why you use MIDIPacketNext,
by the way) and there are a few source code examples from various
sources, but it's been pretty much "guess and go" programming trying
to make this program work. I remember last spring there was a book
coming out covering CoreAudio, they hadn't finished the MIDI section
and as far as I've seen the book still hasn't come out.
Is there some piece of solid documentation that I've been missing all
this time? It seems to me that the fact that you need to call
MIDISend for each packet and MIDIPacketInit before sending another
packet should be something that developers can find fairly easily.
Maybe I've just missed something?
Thanks, Tom
On Tue, Oct 11, 2011 at 10:28 PM, Brian Willoughby <email@hidden> wrote:
>
> CoreMIDI scheduling is indeed more accurate than NSTimer, but it's not as if Apple purposely made NSTimer less accurate. There are very logical constraints which make NSTimer significantly less appropriate for MIDI timing compared to the CoreMIDI functionality.
>
> NSTimer is a general-purpose API and is at the mercy of the thread priority in the hosting application. It would not be very efficient for every MIDI application to have kernel priority threads just to handle MIDI timing. Not only are there thread issues, but NSTimer works within a run loop and thus can often be delayed by application user interface events. Apple makes it clear that timers may not fire exactly when scheduled. Keeping multiple threads running within tight timing constraints is not what NSTimer is designed for, but rather NSTimer is a much simpler API for more relaxed timing needs.
>
> Instead of forcing every application to deal with fixed priority, low latency threads for precise MIDI timing, CoreMIDI allows applications to pass data from application space to system space in a way that allows OSX to handle the timing of MIDI data in carefully written code. Another benefit of CoreMIDI is that the implementation of the timing can be changed without application developers needing to alter their code to match available hardware.
>
> One very important factor to keep in mind is that you can only achieve the full accuracy of the CoreMIDI clock if you give a decent margin of advance notice to the API. In other words, you cannot wait until a MIDI event is supposed to occur before sending it to the API, because there won't be enough of an opportunity for CoreMIDI to schedule the MIDI data properly. I do not know, off hand, the exact amount of advance notice that you need, but it should be easy when playing MIDI data from a file because you can predict the data. CoreMIDI cannot go back in time, so you have to make sure your code runs slightly ahead of time if you want full precision in the timing of MIDI events.
>
> A caveat here is that real-time MIDI translation cannot actually take advantage of the CoreMIDI clock accuracy because there is no way to predict live MIDI input. The best you could do in this particular case is to add a static latency to the time stamp of each incoming MIDI message so that your translated output would maintain the same relative timing to full CoreMIDI clock accuracy, albeit with a very slight delay (which would depend upon your translation code's efficiency). This limitation affects not only translation of live MIDI input to MIDI output, but also limits what can be done in interactive, algorithmic MIDI event generation. While you can have interface MIDI generation, there must be some amount of latency to allow for precise timing.
>
> Yet another benefit of CoreMIDI time stamps is that OSX has the ability to offload timing duties to external hardware. Any MIDI interface with advanced timing capabilities, such as MOTU's MTS (MIDI Time Stamping) or EDIROL's custom protocol, can accept the MIDI data from CoreMIDI along with the time stamp and then the hardware interface itself will take responsibility for the timing of the outgoing data (or marking of incoming data). This sort of advanced performance simply isn't possible when using NSTimer. Thankfully, CoreMIDI handles all of the details for you so that your code does not need to adjust to the available hardware and yet you're always guaranteed the maximum accuracy possible (provided that your application provides the MIDI data with sufficient advance notice).
>
> Sorry if this is more detail than you requested, or if my "answer" calls up more questions. Personally, I find that it helps to study all of the advanced capabilities that CoreMIDI offers so as to understand why it works the way that it does.
>
> Brian Willoughby
> Sound Consulting
>
>
> On Oct 11, 2011, at 21:17, Tom Jeffries wrote:
>>
>> This brings up another issue. The reason I want to use MIDI packet lists is because of my understanding (which may be incorrect) that they use the Coreaudio clock, which I have been told is more accurate than NSTimer. The code I posted to the list is simplified, the code I want to use has a (hopefully) accurate time stamp in each call to MIDIPacketListAdd.
>>
>> Do MIDI packet lists use a more accurate clock than NSTimer? My source for that information is not associated with Apple, and it could be that I misunderstood.
>
>
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Coreaudio-api mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden