├── .pr-preview.json ├── tidyconfig.txt ├── w3c.json ├── CODE_OF_CONDUCT.md ├── spec-source.html ├── .github ├── workflows │ ├── tidy.yml │ ├── auto-publish.yml │ └── auto-publish-errata.yml └── PULL_REQUEST_TEMPLATE.md ├── CONTRIBUTING.md ├── errata.html ├── README.md ├── reports └── implementation.html └── index.html /.pr-preview.json: -------------------------------------------------------------------------------- 1 | { 2 | "src_file": "index.html", 3 | "type": "respec" 4 | } 5 | -------------------------------------------------------------------------------- /tidyconfig.txt: -------------------------------------------------------------------------------- 1 | char-encoding: utf8 2 | indent: yes 3 | wrap: 80 4 | tidy-mark: no 5 | newline: LF 6 | custom-tags: yes 7 | -------------------------------------------------------------------------------- /w3c.json: -------------------------------------------------------------------------------- 1 | 2 | { 3 | "group": 43696, 4 | "contacts": [ 5 | "himorin" 6 | ], 7 | "policy": "open", 8 | "repo-type": "rec-track" 9 | } 10 | -------------------------------------------------------------------------------- /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | # Code of Conduct 2 | 3 | All documentation, code and communication under this repository are covered by the [W3C Code of Ethics and Professional Conduct](https://www.w3.org/Consortium/cepc/). 4 | -------------------------------------------------------------------------------- /spec-source.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Moved 5 | 6 | 7 |

This document got moved to index.html

8 | 9 | 10 | -------------------------------------------------------------------------------- /.github/workflows/tidy.yml: -------------------------------------------------------------------------------- 1 | name: Tidy document 2 | on: 3 | workflow_dispatch: {} 4 | push: 5 | branches: 6 | - main 7 | paths: 8 | - index.html 9 | 10 | jobs: 11 | tidy: 12 | name: Tidy up 13 | runs-on: macos-latest 14 | steps: 15 | - uses: actions/checkout@v4 16 | - run: brew install tidy-html5 17 | - run: tidy -config tidyconfig.txt -o index.html index.html 18 | - uses: peter-evans/create-pull-request@v6 19 | with: 20 | title: "Tidied up document using tidy-html5" 21 | commit-message: "chore(tidy): tidy up document" 22 | branch: html-tidy 23 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | Closes #??? 2 | 3 | The following tasks have been completed: 4 | 5 | * [ ] Modified Web platform tests (link to pull request) 6 | 7 | Implementation commitment (and no objections): 8 | 9 | * [ ] WebKit (https://bugs.webkit.org/show_bug.cgi?id=) 10 | * [ ] Chromium (https://bugs.chromium.org/p/chromium/issues/detail?id=) 11 | * [ ] Gecko (https://bugzilla.mozilla.org/show_bug.cgi?id=) 12 | 13 | Documentation (new feature): 14 | 15 | * [ ] Updated implementation report 16 | * [ ] Pinged MDN 17 | * [ ] Added example to README or spec 18 | 19 | For documentation, either create an [issue](https://github.com/mdn/content/issues) or pull request in [MDN's Content](https://github.com/mdn/content) repo - providing as much information as you can. PR is prefered. 20 | -------------------------------------------------------------------------------- /.github/workflows/auto-publish.yml: -------------------------------------------------------------------------------- 1 | name: Node CI 2 | 3 | on: 4 | push: 5 | branches: 6 | - main 7 | paths: 8 | - index.html 9 | - errata.html 10 | pull_request: {} 11 | 12 | jobs: 13 | validate-and-publish: 14 | name: Validate and Publish 15 | runs-on: ubuntu-latest # only linux supported at present 16 | steps: 17 | - uses: actions/checkout@v2 18 | - uses: w3c/spec-prod@v2 19 | with: 20 | TOOLCHAIN: respec 21 | VALIDATE_LINKS: false 22 | VALIDATE_PUBRULES: false 23 | GH_PAGES_BRANCH: gh-pages 24 | W3C_ECHIDNA_TOKEN: ${{ secrets.ECHIDNA_TOKEN }} 25 | W3C_WG_DECISION_URL: "https://lists.w3.org/Archives/Public/public-device-apis/2021May/0008.html" 26 | W3C_NOTIFICATIONS_CC: "${{ secrets.CC }}" 27 | W3C_BUILD_OVERRIDE: | 28 | specStatus: REC 29 | -------------------------------------------------------------------------------- /.github/workflows/auto-publish-errata.yml: -------------------------------------------------------------------------------- 1 | name: Node CI 2 | 3 | on: 4 | push: 5 | branches: 6 | - main 7 | paths: 8 | - errata.html 9 | - reports/implementation.html 10 | pull_request: {} 11 | 12 | jobs: 13 | generate-errata: 14 | name: Generate errata and implementation report 15 | runs-on: ubuntu-latest # only linux supported at present 16 | permissions: 17 | contents: write 18 | strategy: 19 | max-parallel: 1 20 | matrix: 21 | include: 22 | - source: errata.html 23 | - source: reports/implementation.html 24 | steps: 25 | - uses: actions/checkout@v4 26 | - uses: w3c/spec-prod@v2 27 | with: 28 | SOURCE: ${{ matrix.source }} 29 | TOOLCHAIN: respec 30 | VALIDATE_LINKS: false 31 | VALIDATE_PUBRULES: false 32 | GH_PAGES_BRANCH: gh-pages 33 | -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | Spec development happens via [issues in this repository](https://github.com/w3c/geolocation/issues) and [pull requests](https://github.com/w3c/geolocation/pulls). 2 | 3 | For normative changes, a corresponding [web-platform-tests](https://github.com/web-platform-tests/wpt) PR is highly appreciated. Typically, both PRs will be merged at the same time. If testing is not practical, please explain why and if appropriate [file an issue](https://github.com/web-platform-tests/wpt/issues/new) to follow up later. 4 | 5 | Contributions to this repository are intended to become part of Recommendation-track documents 6 | governed by the [W3C Patent Policy](http://www.w3.org/Consortium/Patent-Policy-20040205/) and 7 | [Software and Document License](http://www.w3.org/Consortium/Legal/copyright-software). To contribute, you must 8 | either participate in the relevant W3C Working Group or make a non-member patent licensing 9 | commitment. 10 | 11 | If you are not the sole contributor to a contribution (pull request), please identify all 12 | contributors in the pull request's body or in subsequent comments. 13 | 14 | To add a contributor (other than yourself, that's automatic), mark them one per line as follows: 15 | 16 | ``` 17 | +@github_username 18 | ``` 19 | 20 | If you added a contributor by mistake, you can remove them in a comment with: 21 | 22 | ``` 23 | -@github_username 24 | ``` 25 | 26 | If you are making a pull request on behalf of someone else but you had no part in designing the 27 | feature, you can remove yourself with the above syntax. 28 | 29 | To build a local copy of the specification, please refer to [respec documentation](https://respec.org/docs/#using-command-line). 30 | -------------------------------------------------------------------------------- /errata.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Geolocation Errata 6 | 10 | 46 | 47 | 48 |
49 | ## Abstract 50 | This document catalogues errata for the [[[Geolocation-API]]] W3C Recommendation. 51 |
52 | 53 | ## Process for submitting errata 54 | 55 | Please [file an issue](https://github.com/w3c/geolocation/issues/new) on Github. 56 | 57 | ## Unaddressed errata 58 | [See issues on Github](https://github.com/w3c/geolocation/labels/errata) 59 | 60 | ## Errata approved by the Working Group 61 | 70 | 71 | 72 | 73 | 74 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Geolocation 2 | 3 | Once a user grants permission, Geolocation provides access to geographical location information from device. 4 | 5 | - [Editor's draft](http://w3c.github.io/geolocation/) 6 | 7 | ## Examples of usage 8 | 9 | This HTTPs-only API exposes the `navigator.geolocation` object with a couple of useful methods: 10 | 11 | - `.getCurrentPosition(successCallback, [errorCallback, options])` - "one shot" position request 12 | - `.watchPosition(successCallback, [errorCallback, options])` - Watch a position and get notified of any changes. 13 | - `.clearWatch(someId)` - allows you to stop watching for location changes. 14 | 15 | No location information is made available through this API without the user's permission. 16 | 17 | ### `navigator.geolocation.getCurrentPosition()` method 18 | 19 | Request the user's current location. If the user allows it, you will get back a position object. 20 | 21 | ```JS 22 | navigator.geolocation.getCurrentPosition(position => { 23 | const { latitude, longitude } = position.coords; 24 | // Do something cool with latitude, longitude 25 | }); 26 | ``` 27 | 28 | ### `navigator.geolocation.watchPosition()` method 29 | 30 | Request the ability to watch user's current location. If the user allows it, you will get back continuous updates of the user's position. 31 | 32 | ```JS 33 | const watchId = navigator.geolocation.watchPosition(position => { 34 | const { latitude, longitude } = position.coords; 35 | // Do something cool with latitude, longitude 36 | }); 37 | ``` 38 | 39 | ### `navigator.geolocation.clearWatch()` method 40 | 41 | Finally, stop watching the user's location. 42 | 43 | ```JS 44 | navigator.geolocation.clearWatch(watchId); 45 | ``` 46 | 47 | ### `GeolocationPosition` as JSON 48 | 49 | You can also easily treat `GeolocationPosition` objects as JSON: 50 | 51 | ```JS 52 | async function sendPosition() { 53 | try { 54 | // Get the current position 55 | const position = await new Promise((resolve, reject) => { 56 | navigator.geolocation.getCurrentPosition(resolve, reject); 57 | }); 58 | 59 | // .stringify() calls .toJSON() automatically 60 | const body = JSON.stringify(position, null, 2); 61 | 62 | // Prepare the fetch request options 63 | const options = { 64 | method: 'POST', 65 | headers: { 66 | 'Content-Type': 'application/json' 67 | }, 68 | body 69 | }; 70 | 71 | // Send request 72 | await fetch('https://example.com/api/positions', options); 73 | } catch (error) { 74 | console.error('Error getting or sending position data:', error); 75 | } 76 | } 77 | 78 | sendPosition(); 79 | ``` 80 | 81 | ### More examples 82 | 83 | The specification provides [examples](https://w3c.github.io/geolocation/#examples) covering different use case. 84 | -------------------------------------------------------------------------------- /reports/implementation.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 10 | 25 | 35 | Geolocation - Implementation Report 36 | 37 | 38 |
39 |

This is an implementation report for [[Geolocation]].

40 |
41 |

Tested assertions

42 |

43 | As Geolocation requires explicit permission grant to be used (via a 44 | browser UI), the following assertions were tested manually to assure 45 | interoperability across browser engines. 46 |

47 |

48 | As some of the tests rely on the [[Permissions]] specifications automation 49 | API, which is only partially supported in Chrome, some the test were 50 | modified locally to get them to pass across browser engines. However, the 51 | working group expects that eventually all browser engines will support the 52 | [[Permissions]]'s automation API and wpt.fyi will reflect 53 | 56 | accurate results 58 | for [[Geolocation]]. 59 |

60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 73 | 74 | 75 | 76 | 77 | 78 | 83 | 84 | 85 | 86 | 87 | 88 | 94 | 95 | 96 | 97 | 98 | 99 | 105 | 106 | 107 | 108 | 109 | 110 | 116 | 117 | 118 | 119 | 120 | 121 | 127 | 128 | 129 | 130 | 131 | 132 | 138 | 139 | 140 | 141 | 142 | 143 | 149 | 150 | 151 | 152 | 153 | 154 | 160 | 161 | 162 | 163 | 164 | 165 | 171 | 172 | 173 | 174 | 175 | 176 | 181 | 182 | 183 | 184 | 185 | 186 | 191 | 192 | 193 | 194 | 195 | 196 | 201 | 202 | 203 | 204 | 205 | 206 | 211 | 212 | 213 | 214 | 215 | 216 | 222 | 223 | 224 | 225 | 226 | 227 | 233 | 234 | 235 | 236 | 237 |
TestChromiumGeckoWebKit
69 | PositionOptions.https.html 72 | UNTESTEDUNTESTEDUNTESTED
79 | clearWatch_TypeError.https.html 82 | PASSPASSPASS
89 | disabled-by-permissions-policy.https.sub.html 93 | UNTESTEDUNTESTEDUNTESTED
100 | enabled-by-permission-policy-attribute-redirect-on-load.https.sub.html 104 | UNTESTEDUNTESTEDUNTESTED
111 | enabled-by-permission-policy-attribute.https.sub.html 115 | UNTESTEDUNTESTEDUNTESTED
122 | enabled-by-permissions-policy.https.sub.html 126 | UNTESTEDUNTESTEDUNTESTED
133 | enabled-on-self-origin-by-permissions-policy.https.sub.html 137 | UNTESTEDUNTESTEDUNTESTED
144 | getCurrentPosition_TypeError.https.html 148 | PASSPASSPASS
155 | getCurrentPosition_permission_allow.https.html 159 | UNTESTEDUNTESTEDUNTESTED
166 | getCurrentPosition_permission_deny.https.html 170 | UNTESTEDUNTESTEDUNTESTED
177 | idlharness.https.window.js 180 | UNTESTEDUNTESTEDUNTESTED
187 | non-fully-active.https.html 190 | FAILPASSFAIL
197 | non-secure-contexts.http.html 200 | PASSPASSPASS
207 | permission.https.html 210 | PASSPASSPASS
217 | watchPosition_TypeError.https.html 221 | PASSPASSPASS
228 | watchPosition_permission_deny.https.html 232 | PASSPASSPASS
238 |

239 | Is each feature of the current specification implemented, and how is this 240 | demonstrated? 241 |

242 |

243 | The current specification features are implemented across major browsers 244 | like Chrome, Firefox, and Safari. This is demonstrated through the 245 | aforementioned web platform tests (WPT), which verify the implementation 246 | of the specification's features, such as obtaining the location, handling 247 | permissions, and responding to errors. 248 |

249 |

250 | Are there independent interoperable implementations of the current 251 | specification? 252 |

253 |

254 | Yes, there are independent interoperable implementations of the Major web 255 | browsers such as Chrome, Firefox, and Safari provide their own 256 | implementations, which have been tested to ensure they conform to the 257 | W3C's specifications and work interoperability across different platforms 258 | and operating systems. 259 |

260 |

261 | Are there implementations created by people other than the authors of the 262 | specification? 263 |

264 |

265 | Yes, implementations of Geolocation have been created by various browser 266 | vendors who are not necessarily the editors of the specification. This 267 | includes engineers from Google, Mozilla, Microsoft, and Apple, among 268 | others, ensuring a broad base of experience and design input is reflected 269 | in the API. 270 |

271 |

Are implementations publicly deployed?

272 |

273 | Yes, the implementations of Geolocation are publicly deployed and widely 274 | used in web applications. These are accessible in consumer-level browsers, 275 | allowing developers to incorporate geolocation features into their 276 | websites and applications, enhancing user experience with location-based 277 | services. 278 |

279 |

280 | Is there implementation experience at all levels of the specification's 281 | ecosystem (authoring, consuming, publishing…)? 282 |

283 |

284 | There is substantial implementation experience at all levels of the 285 | specification's ecosystem. Developers use the API to author location-based 286 | services, consumers use these features in daily web interactions, and 287 | publishers integrate these capabilities into various applications for 288 | enhanced contextual experiences. 289 |

290 |

Are there reports of difficulties or problems with implementation?

291 |

292 | While the core functionality of Geolocation is well-supported, developers 293 | occasionally report difficulties related to privacy concerns, varying 294 | accuracy levels, and handling user permissions across different browsers 295 | and devices. These issues are typically addressed through updates to the 296 | specification and improvements in browser implementations. 297 |

298 | 299 | 300 | -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Geolocation 8 | 9 | 11 | 50 | 51 | 53 |
54 |

55 | Geolocation provides access to geographical location information 56 | associated with the hosting device. 57 |

58 |
59 |
60 | 67 |

68 | Since this specification became a W3C Recommendation on 01 September 69 | 2022, the following substantive additions and/or corrections have been 70 | proposed: 71 |

73 |

74 | A more detailed list of changes can be found in section 75 | [[[#changelog]]]. Reviewers of the document can identify candidate 76 | additions and/or corrections by their distinctive styling in the 77 | document. 78 |

79 |
80 |
81 |

82 | Introduction 83 |

84 |

85 | Geolocation defines a high-level interface to location 86 | information associated only with the device hosting the implementation. 87 | Common sources of location information include Global Positioning 88 | System (GPS) and location inferred from network signals such as IP 89 | address, RFID, WiFi and Bluetooth MAC addresses, and GSM/CDMA cell IDs, 90 | as well as user input. The API itself is agnostic of the underlying 91 | location information sources, and no guarantee is given that the API 92 | returns the device's actual location. 93 |

94 |

95 | If an end user [=check permission|grants permission=], 96 | Geolocation: 97 |

98 | 122 |
123 |

124 | Scope 125 |

126 |

127 | This specification is limited to providing a scripting API for 128 | retrieving geographic position information associated with a hosting 129 | device. The geographic position information is provided in terms of 130 | World Geodetic System coordinates [[WGS84]]. It does not include 131 | providing a markup language of any kind, nor does it include defining 132 | a new URL scheme for building URLs that identify geographic 133 | locations. 134 |

135 |
136 |
137 |
138 |

139 | Examples 140 |

141 |

142 | The API is designed to enable both "one-shot" position requests and 143 | repeated position updates. The following examples illustrate common use 144 | cases. 145 |

146 |
147 |

148 | Get current position 149 |

150 |

151 | Request the user's current location. If the user allows it, you will 152 | get back a position object. 153 |

154 | 162 |
163 |
164 |

165 | Watch a position 166 |

167 |

168 | Request the ability to watch user's current location. If the user 169 | allows it, you will get back continuous updates of the user's 170 | position. 171 |

172 | 181 |
182 |
183 |

184 | Stop watching a position 185 |

186 |

187 | Stop watching for position changes by calling the 188 | {{Geolocation/clearWatch()}} method. 189 |

190 | 210 |
211 |
212 |

213 | Handling errors 214 |

215 |

216 | When an error occurs, the second argument of the 217 | {{Geolocation/watchPosition()}} or 218 | {{Geolocation/getCurrentPosition()}} method gets called with a 219 | {{GeolocationPositionError}} error, which can help you figure out 220 | what might have gone wrong. 221 |

222 | 251 |
252 |
253 |

254 | Using `maximumAge` as cache control 255 |

256 |

257 | By default, the API always attempts to return a cached position so 258 | long as it has a previously acquired position. In this example, we 259 | accept a position whose age is no greater than 10 minutes. If the 260 | user agent does not have a fresh enough cached position object, it 261 | automatically acquires a new position. 262 |

263 | 277 |
278 |
279 |

280 | Using `timeout` 281 |

282 |

283 | If you require location information in a time sensitive manner, you 284 | can use the {{PositionOptions}} {{PositionOptions/timeout}} member to 285 | limit the amount of time you are willing to wait to [=acquire a 286 | position=]. 287 |

288 | 320 |
321 |
322 |

323 | Enabling the API in third-party contexts 324 |

325 |

326 | The [=policy-controlled feature/default allowlist=] of `'self'` 327 | allows API usage in same-origin nested frames but prevents 328 | third-party content from using the API. 329 |

330 |

331 | Third-party usage can be selectively enabled by adding the 332 | [^iframe/allow^]`="geolocation"` attribute to an [^iframe^] element: 333 |

334 | 342 |

343 | Alternatively, the API can be disabled in a first-party context by 344 | specifying an HTTP response header: 345 |

346 | 351 |

352 | See [[[permissions-policy]]] for more details about the 353 | `Permissions-Policy` HTTP header. 354 |

355 |
356 |
357 |
358 |

359 | Privacy considerations 360 |

361 |

362 | The API defined in this specification is used to retrieve the 363 | geographic location of a hosting device. In almost all cases, this 364 | information also discloses the location of the user of the device, 365 | thereby potentially compromising the user's privacy. 366 |

367 |
368 |

369 | User consent 370 |

371 |

372 | Geolocation is a [=powerful feature=] that requires 373 | [=express permission=] from an end-user before any location data is 374 | shared with a web application. This requirement is normatively 375 | enforced by the [=check permission=] steps on which the 376 | {{Geolocation/getCurrentPosition()}} and 377 | {{Geolocation/watchPosition()}} methods rely. 378 |

379 |

380 | An end-user will generally give [=express permission=] through a user 381 | interface, which usually presents a range of permission 382 | [=permission/lifetimes=] that the end-user can choose from. The 383 | choice of [=permission/lifetimes=] vary across user agents, but they 384 | are typically time-based (e.g., "a day"), or until browser is closed, 385 | or the user might even be given the choice for the permission to be 386 | granted indefinitely. The permission [=permission/lifetimes=] dictate 387 | how long a user agent [=permission/granted|grants=] a permission 388 | before that permission is automatically reverted back to its default 389 | [=permission state=], prompting the end-user to make a new choice 390 | upon subsequent use. 391 |

392 |

393 | Although the granularity of the permission [=permission/lifetime=] 394 | varies across user-agents, this specification urges user agents to 395 | limit the lifetime to a single browsing session by default (see 396 | [[[#check-permission]]] for normative requirements). 397 |

398 |
399 |
400 |

401 | Privacy considerations for recipients of location information 402 |

403 |

405 | This section applies to "recipients", which generally means 406 | developers utilizing Geolocation. Although it's 407 | impossible for the user agent, or this specification, to enforce 408 | these requirements, developers need to read this section carefully 409 | and do their best to adhere to the suggestions below. Developers need 410 | to be aware that there might be privacy laws in their jurisdictions 411 | that can govern the usage and access to users' location data. 412 |

413 |

414 | Recipients ought to only request position information when necessary, 415 | and only use the location information for the task for which it was 416 | provided to them. Recipients ought to dispose of location information 417 | once that task is completed, unless expressly permitted to retain it 418 | by the user. Recipients need to also take measures to protect this 419 | information against unauthorized access. If location information is 420 | stored, users need to be allowed to update and delete this 421 | information. 422 |

423 |

424 | The recipients of location information need to refrain from 425 | retransmitting the location information without the user’s express 426 | permission. Care needs to be taken when retransmitting and the use of 427 | encryption is encouraged. 428 |

429 |

430 | Recipients ought to clearly and conspicuously disclose the fact that 431 | they are collecting location data, the purpose for the collection, 432 | how long the data is retained, how the data is secured, how the data 433 | is shared if it is shared, how users can access, update and delete 434 | the data, and any other choices that users have with respect to the 435 | data. This disclosure needs to include an explanation of any 436 | exceptions to the guidelines listed above. 437 |

438 |
439 |
440 |

441 | Implementation considerations 442 |

443 |

444 | Implementers are advised to consider the following aspects that can 445 | negatively affect the privacy of their users: in certain cases, users 446 | can inadvertently grant permission to the user agent to disclose 447 | their location to websites. In other cases, the content hosted at a 448 | certain URL changes in such a way that the previously granted 449 | location permissions no longer apply as far as the user is concerned. 450 | Or the users might simply change their minds. 451 |

452 |

453 | Predicting or preventing these situations is inherently difficult. 454 | Mitigation and in-depth defensive measures are an implementation 455 | responsibility and not prescribed by this specification. However, in 456 | designing these measures, implementers are advised to enable user 457 | awareness of location sharing, and to provide access to user 458 | interfaces that enable revocation of permissions. 459 |

460 |
461 |
462 |

463 | Checking permission to use the API 464 |

465 |

466 | Geolocation is a [=default powerful feature=] identified 467 | by the [=powerful feature/name=] "geolocation". 469 |

470 |

471 | When checking permission 472 | to use the API, a user agent MAY suggest time-based [=permission=] 473 | [=permission/lifetimes=], such as "24 hours", "1 week", or choose to 474 | remember the permission [=permission/grant=] indefinitely. However, 475 | it is RECOMMENDED that a user agent prioritize restricting the 476 | [=permission=] [=permission/lifetime=] to a single session: This can 477 | be, for example, until the [=environment settings object/realm=] is 478 | destroyed, the end-user [=navigates=] away from the [=origin=], or 479 | the relevant browser tab is closed. 480 |

481 |
482 |
483 |
484 |

485 | Security considerations 486 |

487 |

488 | There are no security considerations associated with Geolocation at the 489 | time of publication. However, readers are advised to read the 490 | [[[#privacy]]]. 491 |

492 |
493 | 510 |
511 |

512 | `Geolocation` interface and callbacks 513 |

514 |
 515 |         [Exposed=Window]
 516 |         interface Geolocation {
 517 |           undefined getCurrentPosition (
 518 |             PositionCallback successCallback,
 519 |             optional PositionErrorCallback? errorCallback = null,
 520 |             optional PositionOptions options = {}
 521 |           );
 522 | 
 523 |           long watchPosition (
 524 |             PositionCallback successCallback,
 525 |             optional PositionErrorCallback? errorCallback = null,
 526 |             optional PositionOptions options = {}
 527 |           );
 528 | 
 529 |           undefined clearWatch (long watchId);
 530 |         };
 531 | 
 532 |         callback PositionCallback = undefined (
 533 |           GeolocationPosition position
 534 |         );
 535 | 
 536 |         callback PositionErrorCallback = undefined (
 537 |           GeolocationPositionError positionError
 538 |         );
 539 |       
540 |
541 |

542 | Internal slots 543 |

544 |

545 | Instances of {{Geolocation}} are created with the internal slots in 546 | the following table: 547 |

548 | 549 | 550 | 553 | 556 | 557 | 558 | 561 | 567 | 568 | 569 | 572 | 576 | 577 |
551 | Internal slot 552 | 554 | Description 555 |
559 | [[\cachedPosition]] 560 | 562 | A {{GeolocationPosition}}, initialized to null. It's a reference 563 | to the last acquired position and serves as a cache. A user agent 564 | MAY evict {{Geolocation/[[cachedPosition]]}} by resetting it to 565 | null at any time for any reason. 566 |
570 | [[\watchIDs]] 571 | 573 | Initialized as an empty [=list=] of {{unsigned long}} 574 | [=list/item|items=]. 575 |
578 |
579 |
580 |

581 | `getCurrentPosition()` method 582 |

583 |

585 | The getCurrentPosition(|successCallback:PositionCallback|, 586 | |errorCallback:PositionErrorCallback?|, |options:PositionOptions|) 587 | method steps are: 588 |

589 |
    590 |
  1. 591 | If the [=current settings object=]'s 596 | [=relevant global object=]'s [=associated `Document`=] is not 597 | [=Document/fully active=]: If [=this=]'s 598 | [=relevant global object=]'s [=associated `Document`=] is not 599 | [=Document/fully active=]: 600 |
      601 |
    1. [=Call back with error=] |errorCallback| and 602 | {{GeolocationPositionError/POSITION_UNAVAILABLE}}. 603 |
    2. 604 |
    3. Terminate this algorithm. 605 |
    4. 606 |
    607 |
  2. 608 |
  3. [=Request a position=] passing [=this=], |successCallback|, 609 | |errorCallback|, and |options|. 610 |
  4. 611 |
612 |
613 |
614 |

615 | `watchPosition()` method 616 |

617 |

619 | The watchPosition(|successCallback:PositionCallback|, 620 | |errorCallback:PositionErrorCallback?|, |options:PositionOptions|) 621 | method steps are: 622 |

623 |
    624 |
  1. 625 | If the [=current settings object=]'s 630 | [=relevant global object=]'s [=associated `Document`=] is not 631 | [=Document/fully active=]: If [=this=]'s 632 | [=relevant global object=]'s [=associated `Document`=] is not 633 | [=Document/fully active=]: 634 |
      635 |
    1. [=Call back with error=] passing |errorCallback| and 636 | {{GeolocationPositionError/POSITION_UNAVAILABLE}}. 637 |
    2. 638 |
    3. Return 0. 639 |
    4. 640 |
    641 |
  2. 642 |
  3. Let |watchId:unsigned long| be an [=implementation-defined=] 643 | {{unsigned long}} that is greater than zero. 644 |
  4. 645 |
  5. [=List/Append=] |watchId| to [=this=]'s 646 | {{Geolocation/[[watchIDs]]}}. 647 |
  6. 648 |
  7. [=Request a position=] passing [=this=], |successCallback|, 649 | |errorCallback|, |options|, and |watchId|. 650 |
  8. 651 |
  9. Return |watchId|. 652 |
  10. 653 |
654 |
655 |
656 |

657 | `clearWatch()` method 658 |

659 |

660 | When clearWatch() is invoked, the user agent MUST: 661 |

662 |
    663 |
  1. [=List/Remove=] |watchId| from [=this=]'s 664 | {{Geolocation/[[watchIDs]]}}. 665 |
  2. 666 |
667 |
668 |
669 |

670 | Request a position 671 |

672 |

673 | To request a position, pass a {{Geolocation}} 674 | |geolocation:Geolocation|, a {{PositionCallback}} 675 | |successCallback:PositionCallback|, a {{PositionErrorCallback?}} 676 | |errorCallback:PositionErrorCallback?|, a {{PositionOptions}} 677 | |options:PositionOptions|, and an optional |watchId:unsigned long|: 678 |

679 | 683 | 690 |
    691 |
  1. Let |watchIDs:List| be |geolocation|'s 692 | {{Geolocation/[[watchIDs]]}}. 693 |
  2. 694 |
  3. Let |document:Document| be the |geolocation|'s [=relevant global 695 | object=]'s [=associated `Document`=]. 696 |
  4. 697 |
  5. If |document| is not [=allowed to use=] the 698 | "geolocation" feature: 699 |
      700 |
    1. If |watchId| was passed, [=List/remove=] |watchId| from 701 | |watchIDs|. 702 |
    2. 703 |
    3. [=Call back with error=] passing |errorCallback| and 704 | {{GeolocationPositionError/PERMISSION_DENIED}}. 705 |
    4. 706 |
    5. Terminate this algorithm. 707 |
    6. 708 |
    709 |
  6. 710 |
  7. 711 | If |geolocation|'s [=environment settings object=] 712 | is a [=non-secure context=]: 713 |
      714 |
    1. If |watchId| was passed, [=List/remove=] |watchId| from 715 | |watchIDs|. 716 |
    2. 717 |
    3. [=Call back with error=] passing |errorCallback| and 718 | {{GeolocationPositionError/PERMISSION_DENIED}}. 719 |
    4. 720 |
    5. Terminate this algorithm. 721 |
    6. 722 |
    723 |
  8. 724 |
  9. If |document:Document|'s [=Document/visibility state=] is 725 | "hidden", wait for the following [=page visibility change steps=] to 726 | run: 727 |
      728 |
    1. Assert: |document|'s [=Document/visibility state=] is 729 | "visible". 730 |
    2. 731 |
    3. Continue to the next steps below. 732 |
    4. 733 |
    734 |
  10. 735 |
  11. Let |descriptor| be a new {{PermissionDescriptor}} whose 736 | {{PermissionDescriptor/name}} is "geolocation". 737 |
  12. 738 |
  13. 739 | [=In parallel=]: 740 |
      741 |
    1. Set |permission| to [=request permission to use=] 742 | |descriptor|. 743 |
    2. 744 |
    3. 746 | If |permission| is "denied", then: 747 |
        748 |
      1. If |watchId| was passed, [=list/remove=] |watchId| from 749 | |watchIDs|. 750 |
      2. 751 |
      3. [=Call back with error=] passing |errorCallback| and 752 | {{GeolocationPositionError/PERMISSION_DENIED}}. 753 |
      4. 754 |
      5. Terminate this algorithm. 755 |
      6. 756 |
      757 |
    4. 758 |
    5. Wait to [=acquire a position=] passing |successCallback|, 759 | |errorCallback|, |options|, and |watchId|. 760 |
    6. 761 |
    7. If |watchId| was not passed, terminate this algorithm. 762 |
    8. 763 |
    9. While |watchIDs| [=list/contains=] |watchId|: 764 |
        765 |
      1. 766 | Wait for a significant change of 767 | geographic position. What constitutes a significant 768 | change of geographic position is left to the 769 | implementation. User agents MAY impose a rate limit on how 770 | frequently position changes are reported. User agents MUST consider invoking [=set emulated 772 | position data=] as a significant change. 773 |
      2. 774 |
      3. If |document| is not [=Document/fully active=] or 775 | [=Document/visibility state=] is not "visible", go back to 776 | the previous step and again wait 777 | for a significant change of geographic position. 778 | 790 |
      4. 791 |
      5. Wait to [=acquire a position=] passing |successCallback|, 792 | |errorCallback|, |options|, and |watchId|. 793 |
      6. 794 |
      795 |
    10. 796 |
    797 |
  14. 798 |
799 |
800 |
801 |

802 | Acquire a position 803 |

804 |

805 | To acquire a position, 807 | passing {{PositionCallback}} |successCallback:PositionCallback|, a 808 | {{PositionErrorCallback?}} |errorCallback:PositionErrorCallback?|, 809 | {{PositionOptions}} |options:PositionOptions|, and an optional 810 | |watchId:unsigned long|. 811 |

812 |
    813 |
  1. If |watchId| was passed and [=this=]'s 814 | {{Geolocation/[[watchIDs]]}} does not [=list/contain=] |watchId|, 815 | terminate this algorithm. 816 |
  2. 817 |
  3. Let |acquisitionTime:EpochTimeStamp| be a new {{EpochTimeStamp}} 818 | that represents now. 819 |
  4. 820 |
  5. Let |timeoutTime| be the sum of |acquisitionTime| and 821 | |options|.{{PositionOptions/timeout}}. 822 |
  6. 823 |
  7. Let |cachedPosition:GeolocationPosition| be [=this=]'s 824 | {{Geolocation/[[cachedPosition]]}}. 825 |
  8. 826 |
  9. Create an implementation-specific |timeout| task that elapses at 827 | |timeoutTime|, during which it tries to acquire the device's position 828 | by running the following steps: 829 |
      830 |
    1. Let |permission| be [=get the current permission state=] of 831 | "geolocation". 832 |
    2. 833 |
    3. If |permission| is "denied": 834 |
        835 |
      1. Stop |timeout|. 836 |
      2. 837 |
      3. Do the user or system denied 838 | permission failure case step. 839 |
      4. 840 |
      841 |
    4. 842 |
    5. If |permission| is "granted": 843 |
        844 |
      1. 845 | Check if an emulated position should be 846 | used by running the following steps: 847 |
          848 |
        1. Let |emulatedPositionData| be [=get emulated position 849 | data=] passing [=this=]. 850 |
        2. 851 |
        3. If |emulatedPositionData| is not null: 852 |
            853 |
          1. If |emulatedPositionData| is a 854 | {{GeolocationPositionError}}: 855 |
              856 |
            1. [=Call back with error=] passing 857 | |errorCallback| and 858 | |emulatedPositionData|.{{GeolocationPositionError/code}}. 859 |
            2. 860 |
            3. Terminate this algorithm. 861 |
            4. 862 |
            863 |
          2. 864 |
          3. Let |position| be [=a new `GeolocationPosition`=] 865 | passing |emulatedPositionData|, |acquisitionTime| and 866 | |options|.{{PositionOptions/enableHighAccuracy}}. 867 |
          4. 868 |
          5. [=Queue a task=] on the [=geolocation task 869 | source=] with a step that [=invokes=] 870 | |successCallback| with « |position| » and "`report`". 871 |
          6. 872 |
          7. Terminate this algorithm. 873 |
          8. 874 |
          875 |
        4. 876 |
        877 |
      2. 878 |
      3. Let |position| be null. 879 |
      4. 880 |
      5. If |cachedPosition| is not null, and 881 | |options|.{{PositionOptions/maximumAge}} is greater than 0: 882 |
          883 |
        1. Let |cacheTime:long| be |acquisitionTime| minus the 884 | value of the |options|.{{PositionOptions/maximumAge}} 885 | member. 886 |
        2. 887 |
        3. 888 | If |cachedPosition|'s 894 | {{GeolocationPosition/timestamp}}'s value is greater 895 | than |cacheTime|, and 896 | |cachedPosition|.{{GeolocationPosition/[[isHighAccuracy]]}} 897 | equals 898 | |options|.{{PositionOptions/enableHighAccuracy}}, 899 | set |position| to |cachedPosition|. : 901 |
            902 |
          1. [=Queue a task=] on the [=geolocation task 903 | source=] with a step that [=invokes=] 904 | |successCallback| with « |cachedPosition| » and 905 | "`report`". 906 |
          2. 907 |
          3. Terminate this algorithm. 908 |
          4. 909 |
          910 |
        4. 911 |
        912 |
      6. 913 |
      7. Otherwise, if |position| is not |cachedPosition|, try to 914 | acquire position data from the underlying system, optionally 915 | taking into consideration the value of 916 | |options|.{{PositionOptions/enableHighAccuracy}} during 917 | acquisition. 918 |
      8. 919 |
      9. If the |timeout| elapses during acquisition, or acquiring 920 | the device's position results in failure: 921 |
          922 |
        1. Stop the |timeout|. 923 |
        2. 924 |
        3. Go to dealing with 925 | failures. 926 |
        4. 927 |
        5. Terminate this algorithm. 928 |
        6. 929 |
        930 |
      10. 931 |
      11. If acquiring the position data from the 932 | system succeeds: 933 | 943 |
          944 |
        1. Let |positionData| be a [=map=] with the following 945 | name/value pairs based on the acquired position data: 946 |
          947 |
          948 | "latitude" 949 |
          950 |
          951 | A {{double}} that represents the latitude 952 | coordinates on the Earth's surface in degrees, 953 | using the [[WGS84]] coordinate system. Latitude 954 | measures how far north or south a point is from the 955 | Equator. 956 |
          957 |
          958 | "longitude" 959 |
          960 |
          961 | A {{double}} that represents the longitude 962 | coordinates on the Earth's surface in degrees, 963 | using the [[WGS84]] coordinate system. Longitude 964 | measures how far east or west a point is from the 965 | Prime Meridian. 966 |
          967 |
          968 | "altitude" 969 |
          970 |
          971 | A {{double?}} that represents the altitude in 972 | meters above the [[WGS84]] ellipsoid, or `null` if 973 | not available. Altitude measures the height above 974 | sea level. 975 |
          976 |
          977 | "accuracy" 978 |
          979 |
          980 | A non-negative {{double}} that represents the 981 | accuracy value indicating the 95% confidence level 982 | in meters. Accuracy measures how close the measured 983 | coordinates are to the true position. 984 |
          985 |
          986 | "altitudeAccuracy" 987 |
          988 |
          989 | A non-negative {{double?}} that represents the 990 | altitude accuracy, or `null` if not available, 991 | indicating the 95% confidence level in meters. 992 | Altitude accuracy measures how close the measured 993 | altitude is to the true altitude. 994 |
          995 |
          996 | "speed" 997 |
          998 |
          999 | A non-negative {{double?}} that represents the 1000 | speed in meters per second, or `null` if not 1001 | available. Speed measures how fast the device is 1002 | moving. 1003 |
          1004 |
          1005 | "heading" 1006 |
          1007 |
          1008 | A {{double?}} that represents the heading in 1009 | degrees, or `null` if not available or the device 1010 | is stationary. Heading measures the direction in 1011 | which the device is moving relative to true north. 1012 |
          1013 |
          1014 |
        2. 1015 |
        3. Set |position| to [=a new `GeolocationPosition`=] 1016 | passing |positionData|, |acquisitionTime| and 1017 | |options|.{{PositionOptions/enableHighAccuracy}}. 1018 |
        4. 1019 |
        5. Set [=this=]'s {{Geolocation/[[cachedPosition]]}} to 1020 | |position|. 1021 |
        6. 1022 |
        1023 |
          1024 |
        1. Set |position| to [=a new `GeolocationPosition`=] 1025 | passing |acquisitionTime| and 1026 | |options|.{{PositionOptions/enableHighAccuracy}}. 1027 |
        2. 1028 |
        3. Set [=this=]'s {{Geolocation/[[cachedPosition]]}} to 1029 | |position|. 1030 |
        4. 1031 |
        1032 |
      12. 1033 |
      13. Stop the |timeout|. 1034 |
      14. 1035 |
      15. [=Queue a task=] on the [=geolocation task source=] with 1036 | a step that [=invokes=] |successCallback| with « |position| » 1037 | and "`report`". 1038 |
      16. 1039 |
      1040 |
    6. 1041 |
    1042 |
    1043 |
    1044 | Dealing with failures: 1045 |
    1046 |
    1047 |
      1048 |
    • If acquiring a position fails, do one of the following 1049 | based on the condition that matches the failure: 1050 |
      1051 |
      1052 | User or system denied permission: 1053 |
      1054 |
      1055 |

      1056 | [=Call back with error=] passing |errorCallback| and 1057 | {{GeolocationPositionError/PERMISSION_DENIED}}. 1058 |

      1059 | 1069 |
      1070 |
      1071 | Timeout elapsed: 1072 |
      1073 |
      1074 | [=Call back with error=] with |errorCallback| and 1075 | {{GeolocationPositionError/TIMEOUT}}. 1076 |
      1077 |
      1078 | Data acquisition error or any other reason: 1079 |
      1080 |
      1081 | [=Call back with error=] passing |errorCallback| and 1082 | {{GeolocationPositionError/POSITION_UNAVAILABLE}}. 1083 |
      1084 |
      1085 |
    • 1086 |
    1087 |
    1088 |
    1089 |
  10. 1090 |
1091 |
1092 |
1093 |

1094 | Call back with error 1095 |

1096 |

1097 | When instructed to call back with error, given an 1098 | {{PositionErrorCallback?}} |callback:PositionErrorCallback?| and an 1099 | {{unsigned short}} |code:unsigned short|: 1100 |

1101 |
    1102 |
  1. If |callback| is null, return. 1103 |
  2. 1104 |
  3. Let |error:GeolocationPositionError| be a newly created 1105 | {{GeolocationPositionError}} instance whose 1106 | {{GeolocationPositionError/code}} attribute is initialized to |code|. 1107 |
  4. 1108 |
  5. [=Queue a task=] on the [=geolocation task source=] with a step 1109 | that [=invokes=] |callback| with « |error| » and "`report`". 1110 |
  6. 1111 |
1112 |
1113 |
1114 |
1115 |

1116 | PositionOptions dictionary 1117 |

1118 |
1119 |         dictionary PositionOptions {
1120 |           boolean enableHighAccuracy = false;
1121 |           [Clamp] unsigned long timeout = 0xFFFFFFFF;
1122 |           [Clamp] unsigned long maximumAge = 0;
1123 |         };
1124 |         
1125 |
1126 |

1127 | `enableHighAccuracy` member 1128 |

1129 |

1130 | The enableHighAccuracy member provides a hint that the 1131 | application would like to receive the most accurate location data. 1132 | The intended purpose of this member is to allow applications to 1133 | inform the implementation that they do not require high accuracy 1134 | geolocation fixes and, therefore, the implementation MAY avoid using 1135 | geolocation providers that consume a significant amount of power 1136 | (e.g., GPS). 1137 |

1138 | 1146 |
1147 |
1148 |

1149 | `timeout` member 1150 |

1151 |

1152 | The timeout member denotes the maximum length of time, 1153 | expressed in milliseconds, before [=acquiring a position=] expires. 1154 |

1155 |

1156 | The time spent waiting for the document to become visible and for 1157 | [=check permission|obtaining permission to use the API=] is not 1158 | included in the period covered by the {{PositionOptions/timeout}} 1159 | member. The {{PositionOptions/timeout}} member only applies when 1160 | [=acquiring a position=] begins. 1161 |

1162 | 1168 |
1169 |
1170 |

1171 | `maximumAge` member 1172 |

1173 |

1174 | The maximumAge member indicates that the web application 1175 | is willing to accept a cached position whose age is no greater than 1176 | the specified time in milliseconds. 1177 |

1178 |
1179 |
1180 |
1181 |

1182 | `GeolocationPosition` interface 1183 |

1184 |
1185 |         [Exposed=Window, SecureContext]
1186 |         interface GeolocationPosition {
1187 |           readonly attribute GeolocationCoordinates coords;
1188 |           readonly attribute EpochTimeStamp timestamp;
1189 |           [Default] object toJSON();
1190 |         };
1191 |       
1192 |
1193 |

1194 | `coords` attribute 1195 |

1196 |

1197 | The coords attribute contains geographic coordinates. 1198 |

1199 |
1200 |
1201 |

1202 | `timestamp` attribute 1203 |

1204 |

1205 | The timestamp attribute represents the time when the 1206 | geographic position of the device was acquired. 1207 |

1208 |
1209 |
1210 |

1211 | `toJSON()` method 1212 |

1213 | 1219 |

1220 | The toJSON() method returns a JSON 1221 | representation of the {{GeolocationPosition}} object. 1222 |

1223 |
1224 |
1225 |

1226 | Internal slots 1227 |

1228 |

1229 | Instances of {{GeolocationPosition}} are created with the internal 1230 | slots in the following table: 1231 |

1232 | 1233 | 1234 | 1237 | 1240 | 1241 | 1242 | 1245 | 1250 | 1251 |
1235 | Internal slot 1236 | 1238 | Description 1239 |
1243 | [[\isHighAccuracy]] 1244 | 1246 | A {{boolean}} that records the value of the 1247 | {{PositionOptions/enableHighAccuracy}} member when this 1248 | {{GeolocationPosition}} is [=a new GeolocationPosition|created=]. 1249 |
1252 |
1253 |
1254 |

1255 | Task sources 1256 |

1257 |

1258 | The following [=task source=] is defined by this specification. 1259 |

1260 |
1261 |
1262 | The geolocation task source 1263 |
1264 |
1265 | Used by this specification to queue up non-blocking 1266 | {{PositionCallback}} and {{PositionErrorCallback}} when performing 1267 | [=request a position|position requests=]. 1268 |
1269 |
1270 |
1271 |
1272 |
1273 |

1274 | GeolocationCoordinates interface 1275 |

1276 |
1277 |         [Exposed=Window, SecureContext]
1278 |         interface GeolocationCoordinates {
1279 |           readonly attribute double accuracy;
1280 |           readonly attribute double latitude;
1281 |           readonly attribute double longitude;
1282 |           readonly attribute double? altitude;
1283 |           readonly attribute double? altitudeAccuracy;
1284 |           readonly attribute double? heading;
1285 |           readonly attribute double? speed;
1286 |           [Default] object toJSON();
1287 |         };
1288 |       
1289 |
1290 |

1291 | `latitude`, `longitude`, and `accuracy` attributes 1292 |

1293 | 1300 | 1305 |

1306 | The latitude and 1307 | longitude attributes are geographic coordinates 1308 | specified in decimal degrees. The 1309 | latitude and longitude attributes denote the 1310 | position, specified as a real number of degrees, in the [[WGS84]] 1311 | coordinate system. 1312 |

1313 |

1314 | The accuracy attribute denotes the 1315 | accuracy level of the latitude and longitude coordinates in meters 1316 | (e.g., `65` meters). The accuracy 1317 | attribute denotes the position accuracy radius in meters. 1318 |

1319 |
1320 |
1321 |

1322 | `altitude` and `altitudeAccuracy` attributes 1323 |

1324 |

1325 | The altitude attribute denotes the height of the position, 1326 | specified in meters above the [[WGS84]] ellipsoid. 1327 |

1328 |

1329 | The altitudeAccuracy attribute represents the altitude 1330 | accuracy in meters (e.g., `10` meters). 1331 |

1332 |
1333 |
1334 |

1335 | `heading` attribute 1336 |

1337 |

1338 | The heading attribute denotes the direction of travel of 1339 | the hosting device and is specified in degrees, where 0° ≤ heading 1340 | < 360°, counting clockwise relative to the true north. 1341 |

1342 |
1343 |
1344 |

1345 | `speed` attribute 1346 |

1347 |

1348 | The speed attribute denotes the magnitude of the 1349 | horizontal component of the hosting device's current velocity in 1350 | meters per second. 1351 |

1352 |
1353 |
1354 |

1355 | `toJSON()` method 1356 |

1357 | 1363 |

1364 | The toJSON() method returns a JSON 1365 | representation of the {{GeolocationCoordinates}} object. 1366 |

1367 |
1368 |
1369 |

1370 | Constructing a `GeolocationPosition` 1371 |

1372 | 1378 |

1379 | A new `GeolocationPosition` is constructed with [=map=] 1380 | |positionData|, {{EpochTimeStamp}} |timestamp:EpochTimeStamp| and 1381 | boolean |isHighAccuracy| by performing the following steps: 1382 |

1383 |
    1384 |
  1. Let |coords:GeolocationCoordinates| be a newly created 1385 | {{GeolocationCoordinates}} instance. 1386 |
  2. 1387 |
  3. [=map/For each=] |key| → |value| in |positionData|: 1388 |
      1389 |
    1. Set |coords|'s attribute named |key| to |value|. 1390 |
    2. 1391 |
    1392 |
  4. 1393 |
  5. Return a newly created {{GeolocationPosition}} instance with its 1394 | {{GeolocationPosition/coords}} attribute initialized to |coords| and 1395 | {{GeolocationPosition/timestamp}} attribute initialized to 1396 | |timestamp|, and its {{GeolocationPosition/[[isHighAccuracy]]}} 1397 | internal slot set to |isHighAccuracy|. 1398 |
  6. 1399 |
1400 |

1401 | A new `GeolocationPosition` is constructed with 1402 | {{EpochTimeStamp}} |timestamp:EpochTimeStamp| and boolean 1403 | |isHighAccuracy| by performing the following steps: 1404 |

1405 |
    1406 |
  1. Let |coords:GeolocationCoordinates| be a newly created 1407 | {{GeolocationCoordinates}} instance: 1408 |
      1409 |
    1. Initialize |coord|'s {{GeolocationCoordinates/latitude}} 1410 | attribute to a geographic coordinate in decimal degrees. 1411 |
    2. 1412 |
    3. Initialize |coord|'s {{GeolocationCoordinates/longitude}} 1413 | attribute to a geographic coordinate in decimal degrees. 1414 |
    4. 1415 |
    5. Initialize |coord|'s {{GeolocationCoordinates/accuracy}} 1416 | attribute to a non-negative real number. The value SHOULD 1417 | correspond to a 95% confidence level with respect to the 1418 | longitude and latitude values. 1419 |
    6. 1420 |
    7. Initialize |coord|'s {{GeolocationCoordinates/altitude}} 1421 | attribute in meters above the [[WGS84]] ellipsoid, or `null` if 1422 | the implementation cannot provide altitude information. 1423 |
    8. 1424 |
    9. Initialize |coord|'s 1425 | {{GeolocationCoordinates/altitudeAccuracy}} attribute as 1426 | non-negative real number, or to `null` if the implementation 1427 | cannot provide altitude information. If the altitude accuracy 1428 | information is provided, it SHOULD correspond to a 95% confidence 1429 | level. 1430 |
    10. 1431 |
    11. Initialize |coord|'s {{GeolocationCoordinates/speed}} 1432 | attribute to a non-negative real number, or as `null` if the 1433 | implementation cannot provide speed information. 1434 |
    12. 1435 |
    13. Initialize |coord|'s {{GeolocationCoordinates/heading}} 1436 | attribute in degrees, or `null` if the implementation cannot 1437 | provide heading information. If the hosting device is stationary 1438 | (i.e., the value of the {{GeolocationCoordinates/speed}} 1439 | attribute is 0), then initialize the 1440 | {{GeolocationCoordinates/heading}} to `NaN`. 1441 |
    14. 1442 |
    1443 |
  2. 1444 |
  3. Return a newly created {{GeolocationPosition}} instance with its 1445 | {{GeolocationPosition/coords}} attribute initialized to |coords| and 1446 | {{GeolocationPosition/timestamp}} attribute initialized to 1447 | |timestamp|, and its {{GeolocationPosition/[[isHighAccuracy]]}} 1448 | internal slot set to |isHighAccuracy|. 1449 |
  4. 1450 |
1451 |
1452 |
1453 |
1455 |

1456 | GeolocationPositionError interface 1457 |

1458 |
1459 |         [Exposed=Window]
1460 |         interface GeolocationPositionError {
1461 |           const unsigned short PERMISSION_DENIED = 1;
1462 |           const unsigned short POSITION_UNAVAILABLE = 2;
1463 |           const unsigned short TIMEOUT = 3;
1464 |           readonly attribute unsigned short code;
1465 |           readonly attribute DOMString message;
1466 |         };
1467 |         
1468 |
1469 |

1470 | Constants 1471 |

1472 |
1473 |
1474 | PERMISSION_DENIED (numeric value 1) 1475 |
1476 |
1477 | [=Request a position=] failed because the user denied 1483 | permission to use the API or the request was made 1484 | from an [=non-secure context=]. 1485 |
1486 |
1487 | POSITION_UNAVAILABLE (numeric value 2) 1488 |
1489 |
1490 | [=Acquire a position=] failed. 1491 |
1492 |
1493 | TIMEOUT (numeric value 3) 1494 |
1495 |
1496 | The length of time specified by the {{PositionOptions/timeout}} 1497 | member has elapsed before the user agent could successfully 1498 | [=acquire a position=]. 1499 |
1500 |
1501 |
1502 |
1503 |

1504 | `code` attribute 1505 |

1506 |

1507 | The code attribute returns the value it was [=call back 1508 | with error|initialized to=] (see [[[#constants]]] for possible 1509 | values). 1510 |

1511 |
1512 |
1513 |

1514 | `message` attribute 1515 |

1516 |

1517 | The message attribute is a developer-friendly textual 1518 | description of the {{GeolocationPositionError/code}} attribute. 1519 |

1520 | 1531 |
1532 |
1533 |
1534 |

1535 | Permissions policy 1536 |

1537 |

1538 | This specification defines a [=policy-controlled feature=] identified 1539 | by the token string "geolocation". Its [=policy-controlled 1540 | feature/default allowlist=] is [=default allowlist/'self'=]. 1541 |

1542 |
1543 |
1544 |

1545 | Emulation 1546 |

1547 | 1551 |

1552 | For the purposes of user-agent automation and application testing, this 1553 | document defines geolocation emulations. 1554 |

1555 |

1556 | Each [=top-level traversable=] has an associated emulated position 1557 | data, which is data representing {{GeolocationCoordinates}}, 1558 | {{GeolocationPositionError}} or null, initially null. 1559 |

1560 |

1561 | To set emulated position data, given 1562 | [=navigable=] |navigable| and an |emulatedPositionData|: 1563 |

1564 |
    1565 |
  1. Assert |emulatedPositionData| is either null, a 1566 | {{GeolocationCoordinates}}, or a {{GeolocationPositionError}}. 1567 |
  2. 1568 |
  3. Let |traversable| be |navigable|’s [=navigable/top-level 1569 | traversable=]. 1570 |
  4. 1571 |
  5. If |traversable| is not null: 1572 |
      1573 |
    1. Set |traversable|'s associated [=emulated position data=] to 1574 | |emulatedPositionData|. 1575 |
    2. 1576 |
    3. User agents MUST consider this as a "significant change" in the 1577 | wait for a significant change of 1578 | geographic position step. 1579 |
    4. 1580 |
    1581 |
  6. 1582 |
1583 |

1584 | To get emulated position data, given {{Geolocation}} 1585 | |geolocation|: 1586 |

1587 |
    1588 |
  1. Let |navigable| be |geolocation|'s [=relevant global object=]'s 1589 | [=associated `Document`=]'s [=node navigable=]. 1590 |
  2. 1591 |
  3. If |navigable| is null, return null. 1592 |
  4. 1593 |
  5. Let |traversable| be |navigable|’s [=navigable/top-level 1594 | traversable=]. 1595 |
  6. 1596 |
  7. If |traversable| is null, return null. 1597 |
  8. 1598 |
  9. Return |traversable|'s associated [=emulated position data=]. 1599 |
  10. 1600 |
1601 |
1602 |
1603 |
1604 | 1605 |
1606 |
1607 |
1608 |

1609 | Acknowledgments 1610 |

1611 |

1612 | This specification builds upon earlier work in the industry, including 1613 | research by Aza Raskin, Google Gears Geolocation API, and 1614 | LocationAware.org. 1615 |

1616 |

1617 | Thanks also to Alec Berntson, Alissa Cooper, Steve Block, Greg 1618 | Bolsinga, Lars Erik Bolstad, Aaron Boodman, Dave Burke, Chris Butler, 1619 | Max Froumentin, Shyam Habarakada, Marcin Hanclik, Ian Hickson, Brad 1620 | Lassey, Angel Machin, Cameron McCormack, Daniel Park, Stuart Parmenter, 1621 | Olli Pettay, Chris Prince, Arun Ranganathan, Carl Reed, Thomas 1622 | Roessler, Dirk Segers, Allan Thomson, Martin Thomson, Doug Turner, Erik 1623 | Wilde, Matt Womer, and Mohamed Zergaoui. 1624 |

1625 |
1626 |
1627 |

1628 | Change log 1629 |

1630 |

1631 | Since publication as a W3C Recommendation in 2022, 1632 | Geolocation has received the following normative changes: 1633 |

1634 |

1635 | Since First Public Working Draft in 2021, until it was published as a 1636 | W3C Recommendation in 2022, Geolocation received the 1637 | following normative changes: 1638 |

1639 | 1649 |

1650 | Since publication of the Second Edition in 2016, this specification 1651 | received the following substantive changes: 1652 |

1653 | 1681 |

1682 | See the commit history 1684 | for a complete list of changes. 1685 |

1686 |
1687 | 1688 | 1689 | --------------------------------------------------------------------------------