jussi-kalliokoski / audiolib.js

audiolib.js is a powerful audio tools library for javascript.
http://audiolibjs.org/
672 stars 58 forks source link

0.6.1-1 still causes slow script warnings in Firefox after playback stops #61

Closed jdm closed 11 years ago

jdm commented 12 years ago

While I had playback running it was fine (which is an improvement over the previous release), but when I pause playback (by changing the variable that's queried at the start of the refill method), the slow script warning starts appearing.

jussi-kalliokoski commented 12 years ago

Sorry for the late reply.

Yes, the slow script warning is still an issue. It occurs because the timer is triggered from the worker, and the callback it's triggering may not be complete when the next one is triggered. What happens then is that Firefox thinks the page is unresponsive because it's ignoring a message event from the worker.

I recently changed the sink.js default timeout on Firefox to 100ms, to bring in more stability (and less unresponsive script warnings). This had the tradeoff of higher latency, but I think it's OK, you can still manually set the timeout if you need lower latency on high-end computers.

However, the only measure left to circumvent the unresponsive script warning is to turn off the worker timer and use a timer in the same thread. This has the problem that in the background tabs, timers get clamped to 1000ms which with the current Firefox Audio API is too high to write continuous audio. So, basically turning off the worker timer would cause audio in background tabs to break.

If you don't need the feature, you can cheat the feature detection to turn it off, by doing this before creating your sink instance:

Sink.inlineWorker.ready = true;
Sink.inlineWorker.working = false;

I honestly don't know what to do with this problem for now. Let's just hope Firefox gets a better audio API soon. :)

jdm commented 12 years ago

Thanks for the explanation; I'll talk to the teams involved (I'm an FF dev, by chance) and get their thoughts. Could you clarify which callback is being triggered that isn't complete? As far as I understand it, there's a timer in the worker that posts a message to the main thread that triggers the refill callback that gets sent to the audio API output? Why would this only be causing a problem when playback is stopped, when presumably there is far less work being done?

jussi-kalliokoski commented 12 years ago

I'll talk to the teams involved (I'm an FF dev, by chance) and get their thoughts.

Excellent!

Could you clarify which callback is being triggered that isn't complete?

The refill callback. If it's still being executed when the message from the worker arrives, Firefox pops up the warning message, (somewhat) per Web Application APIs spec.

Why would this only be causing a problem when playback is stopped

I'm not quite sure, sounds a bit weird, maybe you could show me some code? Might be related to the dynamic buffer sizes somehow, but I'm not sure. In essence, if the previous callback was finished quickly, the next buffer will be smaller because less data has been played since the previous callback, so more of the callbacks pass the internal tests that determine whether more data is needed. Sounds a bit weird if that would make the page less responsive, but it's possible that Firefox can perceive it as less responsive since the callbacks last longer more often, although the total time spent in the callbacks is about the same.

jdm commented 12 years ago

https://github.com/jdm/domtracker/blob/master/player.js is the source file that creates the refill callback that is triggered. The index.html file in that repo currently loads an old version of audiolib.js that doesn't use workers; if you change audiolib-hacked.js to audiolib.min.js you should see the problem locally if you run a simple HTTP server and load index.html.

jdm commented 12 years ago

Woo, in recent nightlies I no longer see this problem. However, that probably only means that FF 15, perhaps also 14, can safely use the worker code. I'll test an FF 14 beta at some point to see.