Re: [w3c/gamepad] gamepadconnected/disconnected events & non-"fully active" documents (#149)

Ok, here is a fun test (code below):
https://marcoscaceres.github.io/playground/gamepad_test.html

You can steal `.getGamepads()` and pull Gamepad objects from inactive documents.

Thankfully, "gamepadconnected" and "gamepadconnected" events won't fire on non-fully active documents. 

So, I think we just need to add a check on `.getGamepads()` and we should be good. 

However, it's not something we can test via WPT, because it requires an actual Gamepad... but this should be super easy to patch in each browser. I can take WebKit and Gecko. 

```HTML
<h2>Gamepad</h2>
<script>
  const bad = (ev) => console.log("Event on non-fully active frame!", ev);
  const good = (ev) => console.log("This is ok!", ev);
  async function attachIframe() {
    const iframe = document.createElement("iframe");
    iframe.src = "empty.html";
    document.body.appendChild(iframe);
    console.log("loading iframe");
    await new Promise((r) => {
      iframe.onload = r;
    });
    return iframe;
  }

  // Check events!
  attachIframe().then((iframe) => {
    document.body.appendChild(iframe);
    const win = iframe.contentWindow;
    win.addEventListener("gamepadconnected", bad);
    win.addEventListener("gamepaddisconnected", bad);
    iframe.remove();
  });

  // This is ok
  window.addEventListener("gamepadconnected", good);
  window.addEventListener("gamepaddisconnected", good);

  async function runTest() {
    const iframe = await attachIframe();
    // Prevent invalidation of Navigator
    const win = iframe.contentWindow;
    const gamepadGetter =
      iframe.contentWindow.navigator.getGamepads.bind(navigator);
    console.log("Still active, we get", gamepadGetter());
    // make doc no longer fully active
    iframe.remove();

    // try to use gamepad

    try {
      console.log("Inactive document", gamepadGetter());
    } catch (err) {
      console.log(err);
    }

    // re-attach
    document.body.appendChild(iframe);

    // and we are back!
    console.log("re-attached", iframe.contentWindow.navigator.getGamepads());

    //remove it again...
    iframe.contentWindow.addEventListener("gamepadconnected", console.log);

    iframe.contentWindow.addEventListener("gamepaddisconnected", console.log);
    iframe.remove();
    console.log("done");
  }
</script>

<button onclick="runTest()">Activate the gamepad - then press me</button>
```




-- 
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/w3c/gamepad/issues/149#issuecomment-859245088

Received on Friday, 11 June 2021 03:59:52 UTC