Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-04-11 Thread Ian Hickson
On Thu, 20 Feb 2014, Ashley Gullen wrote:

 We're building a browser-based P2P multiplayer engine on top of WebRTC 
 DataChannels. You can try out our work-in-progress here: 
 http://www.scirra.com/labs/multiplayer/test1/
 
 The first player in to a room is assigned the host, and all other 
 subsequently joining peers connect to the host with WebRTC DataChannels 
 and start exchanging game data. Like all responsible HTML5 games, it 
 runs based on a requestAnimationFrame loop.

requestAnimationFrame() is for animations, not for logic. For logic, your 
better bet is to use a worker or, at worst, setInterval().


 To prevent multiplayer games commonly hanging, perhaps there could be a 
 new API to request that a page can keep running at full capacity even in 
 the background, such as window.requestBackgroundProcessing().

Workers are the mechanism for running code in the background.

I would strongly recommend not using a peer server architecture, though. 
Doing this requires trusting the client, which is highly dubious. A 
hostile player could just inject arbitrary code into your logic, and 
subtly cheat without being detected. It also means that handling the host 
crashing or closing their laptop or going into a tunnel is different than 
the same for another player, which is a sucky experience for everyone.


On Thu, 20 Feb 2014, Glenn Maynard wrote:
 On Thu, Feb 20, 2014 at 12:35 PM, Rik Cabanier wrote:
 
  Is WebRTC available in a worker?
 
 I don't know, but if not, fixing that is probably closer to the right 
 direction than letting people run fast timers in minimized UI threads.

Yeah. If WebRTC isn't being exposed to workers, I recommend bringing that 
up with the editor of the WebRTC spec.


On Thu, 20 Feb 2014, Ashley Gullen wrote:

 There's a lot of worker features that aren't widely supported yet, like 
 rendering to canvas with WebGL and 2D, Web Audio support, inputs, 
 various APIs like speech and fullscreen, so I don't think that's 
 practical right now.

Presumably your server logic doesn't need to be fullscreen...


On Thu, 20 Feb 2014, Ashley Gullen wrote:

 Since it's a peer-to-peer engine, the user acting as the server is also 
 a participant in the game. This means the server is also running the 
 full game experience with rendering and audio.

That part of the logic should be in the tab. Then the tab just acts as a 
client to the server in the worker, in the same way that the other clients 
for the other players do.


 The game logic is tied to rAF, since we intend to step the world once 
 per screen draw, including for the player acting as a server.

Different players are going to have different frame rates, so it doesn't 
make sense to make one player's frame rate more important than another's.

-- 
Ian Hickson   U+1047E)\._.,--,'``.fL
http://ln.hixie.ch/   U+263A/,   _.. \   _\  ;`._ ,.
Things that are impossible just take longer.   `._.-(,_..'--(,_..'`-.;.'


[whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Ashley Gullen
We're building a browser-based P2P multiplayer engine on top of WebRTC
DataChannels. You can try out our work-in-progress here:
http://www.scirra.com/labs/multiplayer/test1/

The first player in to a room is assigned the host, and all other
subsequently joining peers connect to the host with WebRTC DataChannels and
start exchanging game data. Like all responsible HTML5 games, it runs based
on a requestAnimationFrame loop. When switching tab, the
requestAnimationFrame loop stops, and most browsers also limit timers to 1
Hz in background tabs. This is a sensible strategy to avoid wasting
resources and draining battery from inactive tabs. However in the use case
of a WebRTC-based multiplayer game, the host is effectively acting as the
game server, and this basically hangs the server. If there were 20 peers
connected to the host, the game hangs for all 20 players.

Users regularly switch tabs and probably don't expect that this hangs the
game for everyone. To prevent multiplayer games commonly hanging, perhaps
there could be a new API to request that a page can keep running at full
capacity even in the background, such as
window.requestBackgroundProcessing(). This could show a permission prompt
like 'Do you want to allow this page to run in the background? Allow /
Deny' to help protect against abuse.

The formal definition could be: if background processing is approved, all
timer and requestAnimationFrame callbacks run with the same frequency they
would in visible state even when in hidden state (using the terms from
the Page Visibility API).

Alternatively browsers could automatically perform this if any WebRTC
DataChannel has been created by the page. However there are probably cases
where it doesn't matter if the DataChannel hangs or reduces to 1 Hz
response, and so it would still be good to save resources. Also, there may
be other use cases not involving WebRTC where it would be useful to run a
page in the background.

If this specific proposal does not seem appropriate, please consider
suggesting any other possible solutions to avoid multiplayer games hanging
when put in to a background tab - we've already run in to this with
testing, so it seems likely to affect real-world games too.

Ashley Gullen
Scirra.com


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Tab Atkins Jr.
On Thu, Feb 20, 2014 at 7:25 AM, Ashley Gullen ash...@scirra.com wrote:
 We're building a browser-based P2P multiplayer engine on top of WebRTC
 DataChannels. You can try out our work-in-progress here:
 http://www.scirra.com/labs/multiplayer/test1/

 The first player in to a room is assigned the host, and all other
 subsequently joining peers connect to the host with WebRTC DataChannels and
 start exchanging game data. Like all responsible HTML5 games, it runs based
 on a requestAnimationFrame loop.

I think this is your problem.  rAF isn't a replacement for setTimeout,
it's a variant designed to better solve the timer problem *when you
want to be synced to the screen*.

If you're doing network-management work, that has nothing to do with
the screen refresh rate, and shouldn't be associated with it.  Just
run a normal setTimeout loop instead.

(If people used rAF for what it was *intended* for, we could probably
have stopped firing it *entirely* when the window isn't visible.
Instead, we had to compromise with the 1s refresh rate instead.)

~TJ


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Ashley Gullen
Isn't setTimeout also clamped to 1s in the background? This alone would add
so much latency as to effectively hang the game anyway.




On 20 February 2014 16:18, Tab Atkins Jr. jackalm...@gmail.com wrote:

 On Thu, Feb 20, 2014 at 7:25 AM, Ashley Gullen ash...@scirra.com wrote:
  We're building a browser-based P2P multiplayer engine on top of WebRTC
  DataChannels. You can try out our work-in-progress here:
  http://www.scirra.com/labs/multiplayer/test1/
 
  The first player in to a room is assigned the host, and all other
  subsequently joining peers connect to the host with WebRTC DataChannels
 and
  start exchanging game data. Like all responsible HTML5 games, it runs
 based
  on a requestAnimationFrame loop.

 I think this is your problem.  rAF isn't a replacement for setTimeout,
 it's a variant designed to better solve the timer problem *when you
 want to be synced to the screen*.

 If you're doing network-management work, that has nothing to do with
 the screen refresh rate, and shouldn't be associated with it.  Just
 run a normal setTimeout loop instead.

 (If people used rAF for what it was *intended* for, we could probably
 have stopped firing it *entirely* when the window isn't visible.
 Instead, we had to compromise with the 1s refresh rate instead.)

 ~TJ



Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Tab Atkins Jr.
On Thu, Feb 20, 2014 at 8:23 AM, Ashley Gullen ash...@scirra.com wrote:
 Isn't setTimeout also clamped to 1s in the background? This alone would add
 so much latency as to effectively hang the game anyway.

Ah, I wasn't sure if anyone actually did that; I just tested in
Chrome, though, and it definitely does.

All right, proceed with your request. ^_^

~TJ


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Boris Zbarsky

On 2/20/14 11:18 AM, Tab Atkins Jr. wrote:

(If people used rAF for what it was *intended* for, we could probably
have stopped firing it *entirely* when the window isn't visible.


We do.  At least Chrome and Firefox do.


Instead, we had to compromise with the 1s refresh rate instead.)


That's what Chrome and Firefox do for setTimeout/setInterval.

-Boris


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread James Robinson
On Thu, Feb 20, 2014 at 7:25 AM, Ashley Gullen ash...@scirra.com wrote:

 The host is effectively acting as the
 game server, and this basically hangs the server. If there were 20 peers
 connected to the host, the game hangs for all 20 players.


That's a bug in your application design.  If one web page is performing
operations necessary for things orthogonal to that page's visual display,
those operations should not be tied to a requestAnimationFrame loop.  If
the host is responding to network updates from other clients, for instance,
then it could perform that work in response to the network events coming
in.  The page may also be performing the normal game updates for that one
client in a rAF loop concurrently.

- James


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Ashley Gullen
The host needs to keep simulating the world even when no network events are
occurring. That can't happen if rAF isn't firing and timers only run at 1
Hz.


On 20 February 2014 17:56, James Robinson jam...@google.com wrote:

 On Thu, Feb 20, 2014 at 7:25 AM, Ashley Gullen ash...@scirra.com wrote:

 The host is effectively acting as the
 game server, and this basically hangs the server. If there were 20 peers
 connected to the host, the game hangs for all 20 players.


 That's a bug in your application design.  If one web page is performing
 operations necessary for things orthogonal to that page's visual display,
 those operations should not be tied to a requestAnimationFrame loop.  If
 the host is responding to network updates from other clients, for instance,
 then it could perform that work in response to the network events coming
 in.  The page may also be performing the normal game updates for that one
 client in a rAF loop concurrently.

 - James



Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Rik Cabanier
On Thu, Feb 20, 2014 at 10:32 AM, Glenn Maynard gl...@zewt.org wrote:

 On Thu, Feb 20, 2014 at 12:02 PM, Ashley Gullen ash...@scirra.com wrote:

  The host needs to keep simulating the world even when no network events
 are
  occurring. That can't happen if rAF isn't firing and timers only run at 1
  Hz.
 

 This sounds like work that should be done in a worker.  Worker timers
 aren't throttled when in the background, and this is exactly something
 workers are for.


Is WebRTC available in a worker?


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Glenn Maynard
On Thu, Feb 20, 2014 at 12:35 PM, Rik Cabanier caban...@gmail.com wrote:

 This sounds like work that should be done in a worker.  Worker timers
 aren't throttled when in the background, and this is exactly something
 workers are for.


 Is WebRTC available in a worker?


I don't know, but if not, fixing that is probably closer to the right
direction than letting people run fast timers in minimized UI threads.  If
this is just messaging of game state, he could probably do just relay that
through the UI thread, so the game simulation still takes place in a worker.

-- 
Glenn Maynard


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Maciej Stachowiak


 On Feb 20, 2014, at 9:01 AM, Boris Zbarsky bzbar...@mit.edu wrote:
 
 On 2/20/14 11:18 AM, Tab Atkins Jr. wrote:
 (If people used rAF for what it was *intended* for, we could probably
 have stopped firing it *entirely* when the window isn't visible.
 
 We do.  At least Chrome and Firefox do.

Safari too.

 
 Instead, we had to compromise with the 1s refresh rate instead.)
 
 That's what Chrome and Firefox do for setTimeout/setInterval.

We actually clamp timers even more for background tabs if the page has not done 
anything externally observable (e.g. Send or receive network data) in a while.

Cheers,
Maciej


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Ashley Gullen
There's a lot of worker features that aren't widely supported yet, like
rendering to canvas with WebGL and 2D, Web Audio support, inputs, various
APIs like speech and fullscreen, so I don't think that's practical right
now. I guess that's not a reason to standardise a new feature, but is there
not at least a workaround for the mean time? Are workers able to wake the
UI with postMessage()?



On 20 February 2014 18:50, Glenn Maynard gl...@zewt.org wrote:

 On Thu, Feb 20, 2014 at 12:35 PM, Rik Cabanier caban...@gmail.com wrote:

 This sounds like work that should be done in a worker.  Worker timers
 aren't throttled when in the background, and this is exactly something
 workers are for.


 Is WebRTC available in a worker?


 I don't know, but if not, fixing that is probably closer to the right
 direction than letting people run fast timers in minimized UI threads.  If
 this is just messaging of game state, he could probably do just relay that
 through the UI thread, so the game simulation still takes place in a worker.

 --
 Glenn Maynard




Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread David Young
On Thu, Feb 20, 2014 at 03:25:56PM +, Ashley Gullen wrote:
 Users regularly switch tabs and probably don't expect that this hangs the
 game for everyone. To prevent multiplayer games commonly hanging, perhaps
 there could be a new API to request that a page can keep running at full
 capacity even in the background, such as
 window.requestBackgroundProcessing(). This could show a permission prompt
 like 'Do you want to allow this page to run in the background? Allow /
 Deny' to help protect against abuse.

Hi Ashley,

I have some concerns about this as a user of browsers.

I strongly prefer that when a tab is not displayed, it's
not running down my battery, causing a cooling fan to spin, making my
computer sluggish, or otherwise making a nuisance of itself.

I also dislike being forced into any dialog, such as Allow/Deny, with
the system.

I also strongly prefer not to be a part of the browser's or operating
system's CPU/RAM/power/bandwidth-arbitration loop, however, I will
accept granting or adjusting a share of some resource to some tab if the
trade-offs are fairly clear.  For example, I'm happy to let a tab draw
down the battery a little faster or to run the CPU a little hotter in
order for it to have more up-to-date information (most current weather
report, for example) when I revisit it: more energy in exchange for
lower average latency in the display.

If I grant a program a share of a resource, I would like to be able to
claw that share back at a later time.

I think that if I was going to make engineering suggestions, they would
be for the browser makers, not for you, Ashley.

Dave

-- 
David Young
dyo...@pobox.comUrbana, IL(217) 721-9981


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Glenn Maynard
On Thu, Feb 20, 2014 at 3:29 PM, Ashley Gullen ash...@scirra.com wrote:

 There's a lot of worker features that aren't widely supported yet, like
 rendering to canvas with WebGL and 2D, Web Audio support, inputs, various
 APIs like speech and fullscreen, so I don't think that's practical right
 now. I guess that's not a reason to standardise a new feature, but is there
 not at least a workaround for the mean time? Are workers able to wake the
 UI with postMessage()?


You were talking about running the server of a multiplayer game.  Other
than communicating with other clients, it doesn't need any of that, right?
 Those are all client-side behaviors.

You can send a message to the UI thread.  I didn't suggest that, since it
feels like an arms race of trying to sidestep browser behavior.  It may not
matter, since the common things they're trying to stop are probably things
like never-ending animation timers running when you can't even see it (who
have no reason to drive their timers from a worker to bypass the timer
throttling), but I'd recommend trying to move your actual server logic into
a worker.

-- 
Glenn Maynard


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Ashley Gullen
Since it's a peer-to-peer engine, the user acting as the server is also a
participant in the game. This means the server is also running the full
game experience with rendering and audio. The game logic is tied to rAF,
since we intend to step the world once per screen draw, including for the
player acting as a server. It looks like the server is caught between
running in the UI thread and hanging when in the background, or running in
the worker and not having a straightforward way to provide the rendering
and audio game experience for the host player.

One solution is to make web workers able to access many of the same APIs
the UI thread can, especially with WebGL, Web Audio, WebRTC and rAF. Then
it might be practical to move a full game engine in to a worker. If that is
planned, I guess there is no need for a new feature.

Ashley




On 20 February 2014 21:55, Glenn Maynard gl...@zewt.org wrote:

 On Thu, Feb 20, 2014 at 3:29 PM, Ashley Gullen ash...@scirra.com wrote:

 There's a lot of worker features that aren't widely supported yet, like
 rendering to canvas with WebGL and 2D, Web Audio support, inputs, various
 APIs like speech and fullscreen, so I don't think that's practical right
 now. I guess that's not a reason to standardise a new feature, but is there
 not at least a workaround for the mean time? Are workers able to wake the
 UI with postMessage()?


 You were talking about running the server of a multiplayer game.  Other
 than communicating with other clients, it doesn't need any of that, right?
  Those are all client-side behaviors.

 You can send a message to the UI thread.  I didn't suggest that, since it
 feels like an arms race of trying to sidestep browser behavior.  It may not
 matter, since the common things they're trying to stop are probably things
 like never-ending animation timers running when you can't even see it (who
 have no reason to drive their timers from a worker to bypass the timer
 throttling), but I'd recommend trying to move your actual server logic into
 a worker.

 --
 Glenn Maynard




Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Glenn Maynard
On Thu, Feb 20, 2014 at 4:32 PM, Ashley Gullen ash...@scirra.com wrote:

 Since it's a peer-to-peer engine, the user acting as the server is also a
 participant in the game. This means the server is also running the full
 game experience with rendering and audio.


The user is a client, and also a server for all clients (including
itself).  There should be no need for the client to run in the same
environment as the server.  The user's client is just another client to the
server (that happens to be running in a worker in the same browser).

The game logic is tied to rAF, since we intend to step the world once per
 screen draw, including for the player acting as a server.


That doesn't make sense.  requestAnimationFrame is bound to the refresh
rate of the user's monitor, and each user can have a monitor with a
different refresh rate.  (You can even have different monitors on the same
system with different refresh rates, though I don't know if that happens in
practice today.)  Even if everyone's monitor happens to have the same
refresh rate, the monitors won't all be refreshing in sync.  You also
wouldn't want gameplay behavior to change in subtle ways depending on
whether some user's display was at 50Hz or 60Hz or 120Hz.


 It looks like the server is caught between running in the UI thread and
 hanging when in the background, or running in the worker and not having a
 straightforward way to provide the rendering and audio game experience for
 the host player.


The host player just connects to the server, like any other client does.
(The actual connection layer is likely to be different, of course, since
you can just post messages across and not establish any network connection.)


 One solution is to make web workers able to access many of the same APIs
 the UI thread can, especially with WebGL, Web Audio, WebRTC and rAF. Then
 it might be practical to move a full game engine in to a worker. If that is
 planned, I guess there is no need for a new feature.


Not a full game engine, just the server logic where gameplay state,
physics and so on are handled and communicated to clients.

-- 
Glenn Maynard


Re: [whatwg] Proposal: requestBackgroundProcessing()

2014-02-20 Thread Robert O'Callahan
On Fri, Feb 21, 2014 at 11:32 AM, Ashley Gullen ash...@scirra.com wrote:

 One solution is to make web workers able to access many of the same APIs
 the UI thread can, especially with WebGL, Web Audio, WebRTC and rAF. Then
 it might be practical to move a full game engine in to a worker. If that is
 planned, I guess there is no need for a new feature.


Having (some form of) all these APIs available in a Worker is a long-term
goal, but as Glenn just pointed out, it sounds like you could just run the
server in a Worker and the rest of the engine on the main thread.

Having said that, your server would want WebRTC DataChannels on the worker,
and we don't have that yet. You can work around it by proxying messages to
the main thread; postMessage from a Worker to the main thread is usually
not throttled.

Rob
-- 
Jtehsauts  tshaei dS,o n Wohfy  Mdaon  yhoaus  eanuttehrotraiitny  eovni
le atrhtohu gthot sf oirng iyvoeu rs ihnesa.rt sS?o  Whhei csha iids  teoa
stiheer :p atroa lsyazye,d  'mYaonu,r  sGients  uapr,e  tfaokreg iyvoeunr,
'm aotr  atnod  sgaoy ,h o'mGee.t  uTph eann dt hwea lmka'n?  gBoutt  uIp
waanndt  wyeonut  thoo mken.o w