-
-
Notifications
You must be signed in to change notification settings - Fork 27
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Using web worker to keep playing when window is not focused #69
Comments
Actually there seems to be a way to run a constant FPS loop without web worker, using the Web Audio clock: const audioContext = new AudioContext();
const clock = new WAAClock(audioContext);
clock.start();
const event = clock.callbackAtTime(function() { console.log('step') }, 0).repeat(1./60.); // Repeat at 60 FPS
// ...
event.clear(); It seems it can be used as a drop-in replacement for Also interesting blog posts here: And this lib (mentioned here: sebpiq/WAAClock#20 (comment)) seems promising:
Exactly what's needed :) |
Thank you! That's a nice feature to implement when I have more time. |
Using Web Worker seems to be the most reliable solution. |
A minor bug fixed in v1.5.5. |
Just an idea, maybe it's out of scope for this library, so feel free to close this :)
Both
setInterval
andrequestAnimationFrame
have issues for midi playback, they both don't get called often enough when the window is not focused. (requestAnimationFrame
doesn't get called at all in chrome, andsetInterval
gets called only once per second or so.)This is really annoying when switching from the midi-playing/looping browser window to the DAW where the live midi is being processed, it really disturbs the whole workflow :/
Web workers allow running a loop in a separate thread that runs even when the window isn't focused:
https://mortenson.coffee/blog/making-multi-track-tape-recorder-midi-javascript/
In the above blog post, the author had good results with a web worker. But I would write the
tick()
function differently:Instead of hoping that the time between calls stays constant, and trying to adjust the next timeout value based on deviation, I would use
performance.now()
to calculate the number of milliseconds since the last call, and then calculate how many ticks passed based on that, also storing the fractional tick remainder to add it to the number of ticks for the next frame, like this:timeframe_fract
is of typeTimeframeWithFract
to account for fractional tick remainder, defined like this:What do you think? :)
If it's out of scope for this library, would it be possible to let user code handle the timing, so that a user can write their own web worker which sends midi messages to the JZZ player in the main app (currently the Web Midi API is not accessible for web workers, but they can be used for timing, but they have to send messages to the main app which can then send midi out.
If I wanted to do this with JZZ, would it be possible with the JZZ GUI Player? So that I can have its GUI functionality and API, but let the web worker do the timing. Like inversion of control, my app would call JZZ to advance its state, instead of JZZ using
setInterval
, would that be possible somehow? :)I'm asking because this issue is very important to me, I really need midi playback continuing when working in the DAW while the browser window is not focused.
The text was updated successfully, but these errors were encountered: