W3C home > Mailing lists > Public > public-audio@w3.org > October to December 2012

Re: [Web MIDI API] send() timestamp

From: Jussi Kalliokoski <jussi.kalliokoski@gmail.com>
Date: Sat, 15 Dec 2012 12:06:59 +0200
Message-ID: <CAJhzemW9bAXxv64Np60rZSM_iM-xROt6FTSQFbfZ7gZEX0E+Ag@mail.gmail.com>
To: Chris Wilson <cwilso@google.com>
Cc: Marcos Caceres <marcos@marcosc.com>, "public-audio@w3.org" <public-audio@w3.org>
On Fri, Dec 14, 2012 at 11:41 PM, Chris Wilson <cwilso@google.com> wrote:

> On Fri, Dec 14, 2012 at 11:33 AM, Marcos Caceres <marcos@marcosc.com>wrote:
>
>> >for example, if you're recording the MIDI messages from a live piano
>> controller, you will want the subtleties of that timing recorded - you may
>> have some lag when passing through to send(), but when playing back that
>> recorded sequence later, your timestamps will be more precise.
>> Hang on… I'm seeing what you are saying, but this seems like a strange
>> way to achieve the desired outcome… if the idea is to hook device A to
>> device B through some communication port (in this case we are using send),
>> then it's better to do this directly. At the moment, we have basically this:
>>
>> input.addEventListener("message",function(e){output.send(e.data)})
>>
>> When what we really want is:
>>
>> input.connect(output);
>>
>> So you can bypass the JS layer and get realtime communication.
>
>
> No, you're misunderstanding what I'm saying - it's rare, IMO, that you
> would want to do this.  That's my point - most of the time, you will be
> recording and processing that data, but frequently you'll be recording it
> relative to a "sequence clock" - so you'll need high precision.
>

Exactly. Consider you had a sequence of MIDI data pre-recorded and
timestamped, and you want to play that back, but you don't want to schedule
everything at once (otherwise pausing or stopping would become impossible):

var song = [{data: [...], time: 0}]
var index = 0
var playStart = performance.now()

void function loop () {
  setTimeout(loop, 1000)
  var offset = performance.now() - playStart + 1005 // a few ms safety
padding

  while (i < song.length && song[i].time < offset) {
    output.send(song[i].data, playStart + song[i++].time)
  }
}()

Now if we had the signature that just sent the data after the specified
time, it would slowly gather more and more jitter and the song would be
played back slightly slower than it should.

Cheers,
Jussi
Received on Saturday, 15 December 2012 10:07:27 UTC

This archive was generated by hypermail 2.3.1 : Tuesday, 6 January 2015 21:50:04 UTC