{"action":"created","comment":{"url":"https://api.github.com/repos/w3c/webvr/pulls/comments/145604249","pull_request_review_id":70427068,"id":145604249,"diff_hunk":"@@ -42,43 +42,47 @@ VR provides an interesting canvas for artists looking to explore the possibiliti\n \n The basic steps any WebVR application will go through are:\n \n- 1. Request a list of the available VR devices.\n- 2. Checks to see if the desired device supports the presentation modes the application needs.\n- 3. If so, application advertises VR functionality to the user.\n- 4. User performs an action that indicates they want to enter VR mode.\n- 5. Request a VR session to present VR content with.\n- 6. Begin a render loop that produces graphical frames to be displayed on the VR device.\n- 7. Continue producing frames until the user indicates that they wish to exit VR mode.\n- 8. End the VR session.\n+ 1. Request a VR device.\n+ 1. If a device is available, application advertises VR functionality to the user.\n+ 1. Request a VR session from the device in response to a user activation event.\n+ 1. Use the session to run a render loop that produces graphical frames to be displayed on the VR device.\n+ 1. Continue producing frames until the user indicates that they wish to exit VR mode.\n+ 1. End the VR session.\n \n-### Device enumeration\n+### Acquiring a Device\n \n-The first thing that any VR-enabled page will want to do is enumerate the available VR hardware and, if present, advertise VR functionality to the user.\n+The first thing that any VR-enabled page will want to do is request a `VRDevice` and, if one is available, advertise VR functionality to the user. (For example, by adding a button to the DOM that the user can click to start VR content.)\n \n-`navigator.vr.getDevices` returns a [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) that resolves to a list of available devices. Each `VRDevice` represents a physical unit of VR hardware that can present imagery to the user somehow, referred to here as a \"VR hardware device\". On desktop clients this will usually be a headset peripheral; on mobile clients it may represent the mobile device itself in conjunction with a viewer harness (e.g., Google Cardboard or Samsung Gear VR). It may also represent devices without stereo presentation capabilities but more advanced tracking, such as Tango devices.\n+`navigator.vr.requestDevice` returns a [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise) that resolves to a `VRDevice` if one is available. In no `VRDevice` is available it will resolve to null. The promise will be rejected if an error occurs, such as the the page not having the appropriate permissions to access VR capabilities.\n+\n+A `VRDevice` represents a physical unit of VR hardware that can present imagery to the user somehow, referred to here as a \"VR hardware device\". On desktop clients this will usually be a headset peripheral; on mobile clients it may represent the mobile device itself in conjunction with a viewer harness (e.g., Google Cardboard/Daydream or Samsung GearVR). It may also represent devices without stereo-presentation capabilities but with more advanced tracking, such as ARCore/ARKit-compatible devices.\n \n ```js\n-let vrDevice = null;\n+function checkForVR() {\n+  navigator.vr.requestDevice().then(device => {\n+    if (device) {\n+      onVRAvailable(device);\n+    }\n+  }, err => {\n+    // An error occurred while requesting a VRDevice.\n+    console.error('Unable to request a VR device.');\n+  });\n+}\n+```\n \n-navigator.vr.getDevices().then(devices => {\n-  if (devices.length > 0) {\n-    // Use the first device in the array if one is available. If multiple\n-    // devices are present, you may want to provide the user a way of choosing\n-    // which device to use.\n-    vrDevice = devices[0];\n-    onVRAvailable();\n-  } else {\n-    // Could not find any VR hardware connected.\n-  }\n-}, err => {\n-  // An error occurred querying VR hardware. May be the result of blocked\n-  // permissions by a parent frame.\n-});\n+Future revisions of the API may add filter criteria to `navigator.vr.requestDevice`.\n+\n+> **Non-normative Note:** If there are multiple VR devices available, the UA will need to pick which one to return. The UA is allowed to use any criteria it wishes to select which device is returned, including settings UI that allows users to manage device priority. Calling `navigator.vr.requestDevice` should not trigger device selection UI, however, as this would cause many sites to display VR-specific dialogs early in the document lifecycle without and user activation.\n+\n+It's possible that even if no VR device is available initially one may become available while the application is running, or that a previously available device becomes unavailable. This will be most common with PC peripherals that can be connected at disconnected at any time. To respond to these changes pages can listen to the `devicechange` event on the `navigator.vr` object.","path":"explainer.md","position":62,"original_position":62,"commit_id":"fb2af73b8c1da3dee091808a437b319bc9ad3543","original_commit_id":"fb2af73b8c1da3dee091808a437b319bc9ad3543","user":{"login":"cvan","id":203725,"avatar_url":"https://avatars0.githubusercontent.com/u/203725?v=4","gravatar_id":"","url":"https://api.github.com/users/cvan","html_url":"https://github.com/cvan","followers_url":"https://api.github.com/users/cvan/followers","following_url":"https://api.github.com/users/cvan/following{/other_user}","gists_url":"https://api.github.com/users/cvan/gists{/gist_id}","starred_url":"https://api.github.com/users/cvan/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/cvan/subscriptions","organizations_url":"https://api.github.com/users/cvan/orgs","repos_url":"https://api.github.com/users/cvan/repos","events_url":"https://api.github.com/users/cvan/events{/privacy}","received_events_url":"https://api.github.com/users/cvan/received_events","type":"User","site_admin":false},"body":"`connected at disconnected` -> `connected or disconnected`?","created_at":"2017-10-19T05:46:28Z","updated_at":"2017-10-19T05:56:58Z","html_url":"https://github.com/w3c/webvr/pull/289#discussion_r145604249","pull_request_url":"https://api.github.com/repos/w3c/webvr/pulls/289","author_association":"COLLABORATOR","_links":{"self":{"href":"https://api.github.com/repos/w3c/webvr/pulls/comments/145604249"},"html":{"href":"https://github.com/w3c/webvr/pull/289#discussion_r145604249"},"pull_request":{"href":"https://api.github.com/repos/w3c/webvr/pulls/289"}},"in_reply_to_id":145604210},"pull_request":{"url":"https://api.github.com/repos/w3c/webvr/pulls/289","id":143771563,"html_url":"https://github.com/w3c/webvr/pull/289","diff_url":"https://github.com/w3c/webvr/pull/289.diff","patch_url":"https://github.com/w3c/webvr/pull/289.patch","issue_url":"https://api.github.com/repos/w3c/webvr/issues/289","number":289,"state":"open","locked":false,"title":"Refactor getDevices into requestDevice","user":{"login":"toji","id":805273,"avatar_url":"https://avatars2.githubusercontent.com/u/805273?v=4","gravatar_id":"","url":"https://api.github.com/users/toji","html_url":"https://github.com/toji","followers_url":"https://api.github.com/users/toji/followers","following_url":"https://api.github.com/users/toji/following{/other_user}","gists_url":"https://api.github.com/users/toji/gists{/gist_id}","starred_url":"https://api.github.com/users/toji/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/toji/subscriptions","organizations_url":"https://api.github.com/users/toji/orgs","repos_url":"https://api.github.com/users/toji/repos","events_url":"https://api.github.com/users/toji/events{/privacy}","received_events_url":"https://api.github.com/users/toji/received_events","type":"User","site_admin":false},"body":"Got an initial pull request up, but this is going to take some discussion.\r\n\r\nThe basic idea is to drop `getDevices` in favor of a `requestDevice` call that can take an optional set of filters. Credit where credit is due, this is basically what @cvan suggested we do [way back in January](https://github.com/w3c/webvr/issues/179#issuecomment-275284599). I felt that we should try and keep the API simpler. Jokes on me, I guess. ;)\r\n\r\nSome of the important points:\r\n\r\nThis follows very closely the pattern already happily established by [WebUSB](https://wicg.github.io/webusb/#enumeration) and [WebBluetooth](https://webbluetoothcg.github.io/web-bluetooth/#device-discovery), right down the the exact function name. That immediately puts my mind at ease a bit, in that it means we feel more at home next to those APIs and means we're able to borrow from the expertise that went into establishing those standards.\r\n\r\nOur filters are much more minimal than the other two APIs, however, since there is no perceived benefit and several real downsides to being overly specific in this case. We generally want to encourage developers to take whatever device matches their most coarse requirements (ie: needs to support exclusive presentation, in the future needs to support AR passthrough?). We definitely don't want to allow or encourage \"I want a device with at least a screen resolution of X, FoV no smaller than Y, and that supports at least Z simultaneous layers.\"\r\n\r\nThere was a question on the most recent call about if we should drop the `VRDevice` object, since we could feasibly just request sessions directly from navigator.vr with this pattern. After stewing on it for a bit I think the answer is \"Yes... but there's an issue.\" Specifically, we still need a way to ensure that WebGL contexts are created with a compatible adapter, and I like the pattern we've established of using the `VRDevice` to indicate what adapter the context needs to be compatible with. (I personally feel it's a hard requirement to allow developers to create compatible contexts prior to the creation of a session.) So in my opinion `VRDevice` stays and simply loses the name string.\r\n\r\nThat creates a minor complication when it comes to multiple devices connected to a single PC, though. I had this fanciful idea that the `VRDevice` didn't need to represent a physical piece of hardware, and could instead represent all the potential devices that could satisfy the filters, and only when the user attempted to create a `VRSession` would the system throw up a prompt (if necessary) and say \"Hey, which of these two headsets do you want to present to?\" That breaks the ability to use `VRDevice` as the handle for context compatibility, though, since it's entirely possible those two headsets are connected to different adapters. (It's also just kinda weird when set next to WebUSB and WebBluetooth, both of whom treat their respective devices as a physical piece of hardware.)\r\n\r\nSo I think a `VRDevice` needs to continue representing just one piece of hardware, which then begs the question of how the poor power user with 4 GPUs chooses between their Rift and Vive when viewing WebVR content.\r\n\r\n![](http://i0.kym-cdn.com/photos/images/original/001/093/557/142.gif)\r\n\r\nHowever, I don't think it's a big enough issue for us to try and bend over backwards for. A few things to consider:\r\n\r\n- Most users will only have one possible device, either because it's their phone, it's a standalone HMD, or because headsets are expensive and power hungry so it doesn't make much sense to have more than one per machine.\r\n- Even in the case that you do have N devices available, you'll often have a clear indication that the user wants to use a specific device. (If the user is viewing a VR browser in one HMD, they definitely don't want WebVR content to show up on the other.)\r\n- Hardware trends and basic financial factors seem to be favoring standalone and mobile systems long term anyway.\r\n- In the case that it truly is ambiguous the browser could have some internal settings page where the default VR device is set.\r\n\r\nSomething I don't want to see happen, though, is for pages to pop up a \"Which device do you mean?\" dialog upon calls to `requestDevice`, because I would expect that to happen early on in most pages lifetime as they try to determine if they should advertise VR features. A UA-driven selection dialog at that step would mean that many pages would immediately ask you to pick a headset upon navigation even though you've made no indication you want to use VR. That's severely user-hostile behavior.\r\n\r\nOne thing I'd really appreciate is hearing from @grorg if these changes would satisfy Apple's fingerprinting concerns sufficiently. I think we can work out the above issues, but if this change doesn't get us closer to enabling eventual implementation in WebKit then it's something of a moot point.\r\n\r\nI need to add a section about how to use the filters, so this PR isn't quite complete even if everyone agrees on the functionality, but I wanted to get the conversation going. As a heads up, I'll be unavailable for the entirety of the week of Oct 2nd, but I hope that the rest of the community group can work towards a resolution in the meantime. This is an important change to finalize soon so that we don't get stuck in spec limbo.","created_at":"2017-09-28T22:35:35Z","updated_at":"2017-10-19T05:56:58Z","closed_at":null,"merged_at":null,"merge_commit_sha":"7f361a502d6313343e6f96d347f93961c51bc0cd","assignee":null,"assignees":[],"requested_reviewers":[],"milestone":null,"commits_url":"https://api.github.com/repos/w3c/webvr/pulls/289/commits","review_comments_url":"https://api.github.com/repos/w3c/webvr/pulls/289/comments","review_comment_url":"https://api.github.com/repos/w3c/webvr/pulls/comments{/number}","comments_url":"https://api.github.com/repos/w3c/webvr/issues/289/comments","statuses_url":"https://api.github.com/repos/w3c/webvr/statuses/fb2af73b8c1da3dee091808a437b319bc9ad3543","head":{"label":"w3c:request_device","ref":"request_device","sha":"fb2af73b8c1da3dee091808a437b319bc9ad3543","user":{"login":"w3c","id":379216,"avatar_url":"https://avatars2.githubusercontent.com/u/379216?v=4","gravatar_id":"","url":"https://api.github.com/users/w3c","html_url":"https://github.com/w3c","followers_url":"https://api.github.com/users/w3c/followers","following_url":"https://api.github.com/users/w3c/following{/other_user}","gists_url":"https://api.github.com/users/w3c/gists{/gist_id}","starred_url":"https://api.github.com/users/w3c/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/w3c/subscriptions","organizations_url":"https://api.github.com/users/w3c/orgs","repos_url":"https://api.github.com/users/w3c/repos","events_url":"https://api.github.com/users/w3c/events{/privacy}","received_events_url":"https://api.github.com/users/w3c/received_events","type":"Organization","site_admin":false},"repo":{"id":53899485,"name":"webvr","full_name":"w3c/webvr","owner":{"login":"w3c","id":379216,"avatar_url":"https://avatars2.githubusercontent.com/u/379216?v=4","gravatar_id":"","url":"https://api.github.com/users/w3c","html_url":"https://github.com/w3c","followers_url":"https://api.github.com/users/w3c/followers","following_url":"https://api.github.com/users/w3c/following{/other_user}","gists_url":"https://api.github.com/users/w3c/gists{/gist_id}","starred_url":"https://api.github.com/users/w3c/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/w3c/subscriptions","organizations_url":"https://api.github.com/users/w3c/orgs","repos_url":"https://api.github.com/users/w3c/repos","events_url":"https://api.github.com/users/w3c/events{/privacy}","received_events_url":"https://api.github.com/users/w3c/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/w3c/webvr","description":"Repository for the WebVR Community Group and the WebVR Specification.","fork":false,"url":"https://api.github.com/repos/w3c/webvr","forks_url":"https://api.github.com/repos/w3c/webvr/forks","keys_url":"https://api.github.com/repos/w3c/webvr/keys{/key_id}","collaborators_url":"https://api.github.com/repos/w3c/webvr/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/w3c/webvr/teams","hooks_url":"https://api.github.com/repos/w3c/webvr/hooks","issue_events_url":"https://api.github.com/repos/w3c/webvr/issues/events{/number}","events_url":"https://api.github.com/repos/w3c/webvr/events","assignees_url":"https://api.github.com/repos/w3c/webvr/assignees{/user}","branches_url":"https://api.github.com/repos/w3c/webvr/branches{/branch}","tags_url":"https://api.github.com/repos/w3c/webvr/tags","blobs_url":"https://api.github.com/repos/w3c/webvr/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/w3c/webvr/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/w3c/webvr/git/refs{/sha}","trees_url":"https://api.github.com/repos/w3c/webvr/git/trees{/sha}","statuses_url":"https://api.github.com/repos/w3c/webvr/statuses/{sha}","languages_url":"https://api.github.com/repos/w3c/webvr/languages","stargazers_url":"https://api.github.com/repos/w3c/webvr/stargazers","contributors_url":"https://api.github.com/repos/w3c/webvr/contributors","subscribers_url":"https://api.github.com/repos/w3c/webvr/subscribers","subscription_url":"https://api.github.com/repos/w3c/webvr/subscription","commits_url":"https://api.github.com/repos/w3c/webvr/commits{/sha}","git_commits_url":"https://api.github.com/repos/w3c/webvr/git/commits{/sha}","comments_url":"https://api.github.com/repos/w3c/webvr/comments{/number}","issue_comment_url":"https://api.github.com/repos/w3c/webvr/issues/comments{/number}","contents_url":"https://api.github.com/repos/w3c/webvr/contents/{+path}","compare_url":"https://api.github.com/repos/w3c/webvr/compare/{base}...{head}","merges_url":"https://api.github.com/repos/w3c/webvr/merges","archive_url":"https://api.github.com/repos/w3c/webvr/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/w3c/webvr/downloads","issues_url":"https://api.github.com/repos/w3c/webvr/issues{/number}","pulls_url":"https://api.github.com/repos/w3c/webvr/pulls{/number}","milestones_url":"https://api.github.com/repos/w3c/webvr/milestones{/number}","notifications_url":"https://api.github.com/repos/w3c/webvr/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/w3c/webvr/labels{/name}","releases_url":"https://api.github.com/repos/w3c/webvr/releases{/id}","deployments_url":"https://api.github.com/repos/w3c/webvr/deployments","created_at":"2016-03-14T23:30:00Z","updated_at":"2017-10-19T01:49:50Z","pushed_at":"2017-10-19T05:19:36Z","git_url":"git://github.com/w3c/webvr.git","ssh_url":"git@github.com:w3c/webvr.git","clone_url":"https://github.com/w3c/webvr.git","svn_url":"https://github.com/w3c/webvr","homepage":"https://w3c.github.io/webvr/","size":947,"stargazers_count":575,"watchers_count":575,"language":"HTML","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":91,"mirror_url":null,"open_issues_count":81,"forks":91,"open_issues":81,"watchers":575,"default_branch":"master"}},"base":{"label":"w3c:master","ref":"master","sha":"28aedb95c30d6f973a67c1e7869eee4bc41f8921","user":{"login":"w3c","id":379216,"avatar_url":"https://avatars2.githubusercontent.com/u/379216?v=4","gravatar_id":"","url":"https://api.github.com/users/w3c","html_url":"https://github.com/w3c","followers_url":"https://api.github.com/users/w3c/followers","following_url":"https://api.github.com/users/w3c/following{/other_user}","gists_url":"https://api.github.com/users/w3c/gists{/gist_id}","starred_url":"https://api.github.com/users/w3c/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/w3c/subscriptions","organizations_url":"https://api.github.com/users/w3c/orgs","repos_url":"https://api.github.com/users/w3c/repos","events_url":"https://api.github.com/users/w3c/events{/privacy}","received_events_url":"https://api.github.com/users/w3c/received_events","type":"Organization","site_admin":false},"repo":{"id":53899485,"name":"webvr","full_name":"w3c/webvr","owner":{"login":"w3c","id":379216,"avatar_url":"https://avatars2.githubusercontent.com/u/379216?v=4","gravatar_id":"","url":"https://api.github.com/users/w3c","html_url":"https://github.com/w3c","followers_url":"https://api.github.com/users/w3c/followers","following_url":"https://api.github.com/users/w3c/following{/other_user}","gists_url":"https://api.github.com/users/w3c/gists{/gist_id}","starred_url":"https://api.github.com/users/w3c/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/w3c/subscriptions","organizations_url":"https://api.github.com/users/w3c/orgs","repos_url":"https://api.github.com/users/w3c/repos","events_url":"https://api.github.com/users/w3c/events{/privacy}","received_events_url":"https://api.github.com/users/w3c/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/w3c/webvr","description":"Repository for the WebVR Community Group and the WebVR Specification.","fork":false,"url":"https://api.github.com/repos/w3c/webvr","forks_url":"https://api.github.com/repos/w3c/webvr/forks","keys_url":"https://api.github.com/repos/w3c/webvr/keys{/key_id}","collaborators_url":"https://api.github.com/repos/w3c/webvr/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/w3c/webvr/teams","hooks_url":"https://api.github.com/repos/w3c/webvr/hooks","issue_events_url":"https://api.github.com/repos/w3c/webvr/issues/events{/number}","events_url":"https://api.github.com/repos/w3c/webvr/events","assignees_url":"https://api.github.com/repos/w3c/webvr/assignees{/user}","branches_url":"https://api.github.com/repos/w3c/webvr/branches{/branch}","tags_url":"https://api.github.com/repos/w3c/webvr/tags","blobs_url":"https://api.github.com/repos/w3c/webvr/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/w3c/webvr/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/w3c/webvr/git/refs{/sha}","trees_url":"https://api.github.com/repos/w3c/webvr/git/trees{/sha}","statuses_url":"https://api.github.com/repos/w3c/webvr/statuses/{sha}","languages_url":"https://api.github.com/repos/w3c/webvr/languages","stargazers_url":"https://api.github.com/repos/w3c/webvr/stargazers","contributors_url":"https://api.github.com/repos/w3c/webvr/contributors","subscribers_url":"https://api.github.com/repos/w3c/webvr/subscribers","subscription_url":"https://api.github.com/repos/w3c/webvr/subscription","commits_url":"https://api.github.com/repos/w3c/webvr/commits{/sha}","git_commits_url":"https://api.github.com/repos/w3c/webvr/git/commits{/sha}","comments_url":"https://api.github.com/repos/w3c/webvr/comments{/number}","issue_comment_url":"https://api.github.com/repos/w3c/webvr/issues/comments{/number}","contents_url":"https://api.github.com/repos/w3c/webvr/contents/{+path}","compare_url":"https://api.github.com/repos/w3c/webvr/compare/{base}...{head}","merges_url":"https://api.github.com/repos/w3c/webvr/merges","archive_url":"https://api.github.com/repos/w3c/webvr/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/w3c/webvr/downloads","issues_url":"https://api.github.com/repos/w3c/webvr/issues{/number}","pulls_url":"https://api.github.com/repos/w3c/webvr/pulls{/number}","milestones_url":"https://api.github.com/repos/w3c/webvr/milestones{/number}","notifications_url":"https://api.github.com/repos/w3c/webvr/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/w3c/webvr/labels{/name}","releases_url":"https://api.github.com/repos/w3c/webvr/releases{/id}","deployments_url":"https://api.github.com/repos/w3c/webvr/deployments","created_at":"2016-03-14T23:30:00Z","updated_at":"2017-10-19T01:49:50Z","pushed_at":"2017-10-19T05:19:36Z","git_url":"git://github.com/w3c/webvr.git","ssh_url":"git@github.com:w3c/webvr.git","clone_url":"https://github.com/w3c/webvr.git","svn_url":"https://github.com/w3c/webvr","homepage":"https://w3c.github.io/webvr/","size":947,"stargazers_count":575,"watchers_count":575,"language":"HTML","has_issues":true,"has_projects":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":91,"mirror_url":null,"open_issues_count":81,"forks":91,"open_issues":81,"watchers":575,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/w3c/webvr/pulls/289"},"html":{"href":"https://github.com/w3c/webvr/pull/289"},"issue":{"href":"https://api.github.com/repos/w3c/webvr/issues/289"},"comments":{"href":"https://api.github.com/repos/w3c/webvr/issues/289/comments"},"review_comments":{"href":"https://api.github.com/repos/w3c/webvr/pulls/289/comments"},"review_comment":{"href":"https://api.github.com/repos/w3c/webvr/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/w3c/webvr/pulls/289/commits"},"statuses":{"href":"https://api.github.com/repos/w3c/webvr/statuses/fb2af73b8c1da3dee091808a437b319bc9ad3543"}},"author_association":"COLLABORATOR"}}
{"actor":{"display_login":"cvan"}}