InfoReport.ar ​

Contract 2.0.0 · package sha256 a857eca95b35921109faf997094bb4192f12527d9d0fcd4be7e97f06425bad6e · generated from configurator-runtime.d.ts by services/onsite-scripter/scripts/build-contract-docs.mjs; edit the source, not this file.

Property of InfoReport · stable · since 2.0.0 · called as session.info().ar

ts
readonly ar: {
  readonly enabled: boolean;
  readonly modes: ReadonlyArray<'scene-viewer' | 'quick-look' | 'webxr' | 'other'>;
  readonly fileModes: ReadonlyArray<'scene-viewer' | 'quick-look' | 'other'>;
  readonly pending: boolean;
};

AR on this device for this account: read it before showing an AR control.

Fields ​

enabled ​

ts
readonly enabled: boolean;

The merged document's AR switch.

modes ​

ts
readonly modes: ReadonlyArray<'scene-viewer' | 'quick-look' | 'webxr' | 'other'>;

The viewers activateAR can open here, in the account's preference order; empty means hide the AR control (activateAR would resolve reason: 'disabled' or 'unsupported'). Scene Viewer and Quick Look are known when boot resolves; Scene Viewer opens for a call with an http(s) glbUrl, or without one for a product with a public plain twin (Session.activateAR). 'scene-viewer' leaves the list only while the committed product is encrypted with no public plain twin (a .holo among several placed models, or one encrypted ModelNode without a plainGlbUrl), where no file of the product can open it; an unencrypted product keeps it, as 1.x lists it. It joins or leaves with the commit that changes that, 'ar:modes' telling it. A page that passes its own http(s) glbUrl (a merged file of the whole product) reads fileModes instead. 'quick-look' is listed where document.createElement('a').relList.supports('ar') is true (Safari, a Home Screen app) and in Chrome, Firefox, Edge and DuckDuckGo on iOS (a hosted or blob: usdzUrl alike); 'scene-viewer' on Android outside WebViews and Firefox. Neither is listed in the Google app, a social in-app browser (Facebook, Instagram, TikTok and the like) or a WebView, where a tap would open nothing (spec section 5.11). 'webxr' names Holostep's in-page viewer on either route (WebXR on Android, the camera tracker on iOS) and is listed only where the next activateAR() without glbUrl would open it (the routing in Session.activateAR, with the tap's activation assumed), or where its escape sheet is the only AR route (a host's deny row, an app shell not yet measured): there it is the only mode, so the AR control shows and its tap opens the sheet. For an Android account that opts in, the runtime loads its AR probe at idle after boot (document.featurePolicy first, then navigator.xr.isSessionSupported('immersive-ar')) and never waits for it, so boot takes no longer; elsewhere no probe runs. 'ar:modes' fires when 'webxr' joins: an AR control decided at install follows that event.

fileModes ​

ts
readonly fileModes: ReadonlyArray<'scene-viewer' | 'quick-look' | 'other'>;

The native viewers an activateAR call with your own file opens here, whatever the product on screen: 'scene-viewer' with an http(s) glbUrl, 'quick-look' (with a usdzUrl, or the runtime's own file), on the devices modes names them for, in the account's order; empty with AR off. Use it to show the AR control on a page that always passes glbUrl, such as an encrypted modular product whose merged file the page uploads; modes stays the list for a plain call.

Default: [] (AR off, or a device with no native viewer)

pending ​

ts
readonly pending: boolean;

True until the in-page route can be answered: the probe answered or timed out, the AR code loaded and the scene's size is known; on an iOS page that opts in, until the in-page code and the scene's size are in. False at boot where nothing is to be answered (an account that doesn't opt in, an Android device without navigator.xr). 'ar:modes' fires once when it turns false, whether or not 'webxr' joined, so a page whose layout depends on 'webxr' (an AR page that launches AR or shows a QR code) holds that layout while it is true. An empty modes alone can't tell "still checking" from "none".

Generic-API test (spec 3.1) ​

Rule Result
1. Neutral name pass: ar names no product
2. A precedent pass: XRSystem.isSessionSupported() (row G61)
3. Two apps, or labs pass: 12 apps (ledger: app-4fd23bc869, app-822bb9d6aa, app-8675b3225c, app-c1384707fc, app-e3b47169bc, app-e9a33606d2, app-f07e9033d9, app-f3598fad77 and 4 more; fleet cross-check: app-fd09090420)
4. The cheaper fix first decided per need in Appendix B: rows G61 at tier stable (a member only where no rule, data, asset or app code serves the need)