@webspatial/react-sdk 1.6.1 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. package/README.md +270 -0
  2. package/dist/Model-DO5ps8NA.d.ts +35 -0
  3. package/dist/Reality-BDyKL6th.d.ts +256 -0
  4. package/dist/Reality-DO-itiWW.d.ts +33 -0
  5. package/dist/SceneGraph-DxH74y6-.d.ts +214 -0
  6. package/dist/chunk-6JSRUX7P.js +2 -0
  7. package/dist/chunk-6JSRUX7P.js.map +1 -0
  8. package/dist/chunk-BTLTBCA7.js +2 -0
  9. package/dist/chunk-BTLTBCA7.js.map +1 -0
  10. package/dist/chunk-GG2QK5MA.js +2 -0
  11. package/dist/chunk-GG2QK5MA.js.map +1 -0
  12. package/dist/chunk-IOLNY4GP.js +2 -0
  13. package/dist/chunk-IOLNY4GP.js.map +1 -0
  14. package/dist/chunk-NWVQY6CN.js +2 -0
  15. package/dist/chunk-NWVQY6CN.js.map +1 -0
  16. package/dist/chunk-NXEOIP4Z.js +2 -0
  17. package/dist/chunk-NXEOIP4Z.js.map +1 -0
  18. package/dist/chunk-PDUEHFTO.js +2 -0
  19. package/dist/chunk-PDUEHFTO.js.map +1 -0
  20. package/dist/chunk-QHUROD77.js +2 -0
  21. package/dist/chunk-QHUROD77.js.map +1 -0
  22. package/dist/chunk-UHEO47WY.js +2 -0
  23. package/dist/chunk-UHEO47WY.js.map +1 -0
  24. package/dist/chunk-WDOPCAA3.js +19 -0
  25. package/dist/chunk-WDOPCAA3.js.map +1 -0
  26. package/dist/eager.d.ts +46 -0
  27. package/dist/eager.js +8 -0
  28. package/dist/eager.js.map +1 -0
  29. package/dist/experimental.d.ts +24 -0
  30. package/dist/experimental.js +8 -0
  31. package/dist/experimental.js.map +1 -0
  32. package/dist/index.d.ts +70 -0
  33. package/dist/index.js +8 -0
  34. package/dist/index.js.map +1 -0
  35. package/dist/internal/facades-client.d.ts +50 -0
  36. package/dist/internal/facades-client.js +3 -0
  37. package/dist/internal/facades-client.js.map +1 -0
  38. package/dist/jsx/jsx-dev-runtime.d.ts +7 -79
  39. package/dist/jsx/jsx-dev-runtime.js +1 -66
  40. package/dist/jsx/jsx-dev-runtime.js.map +1 -1
  41. package/dist/jsx/jsx-runtime.d.ts +81 -2
  42. package/dist/jsx/jsx-runtime.js +1 -66
  43. package/dist/jsx/jsx-runtime.js.map +1 -1
  44. package/dist/jsx-shared-CFDVUVpc.d.ts +16 -0
  45. package/dist/motionBindingTypes-CjxIC5bP.d.ts +25 -0
  46. package/dist/runtime/registerEagerEntry.d.ts +8 -0
  47. package/dist/runtime/registerEagerEntry.js +2 -0
  48. package/dist/runtime/registerEagerEntry.js.map +1 -0
  49. package/dist/spatial.d.ts +25 -0
  50. package/dist/spatial.js +7 -0
  51. package/dist/spatial.js.map +1 -0
  52. package/dist/useAnimation-C1LXt-xO.d.ts +28 -0
  53. package/dist/useMetrics-Bm_Urbtp.d.ts +96 -0
  54. package/package.json +53 -33
  55. package/dist/default/index.d.ts +0 -408
  56. package/dist/default/index.js +0 -3852
  57. package/dist/default/index.js.map +0 -1
  58. package/dist/jsx/jsx-dev-runtime.web.d.ts +0 -2
  59. package/dist/jsx/jsx-dev-runtime.web.js +0 -18
  60. package/dist/jsx/jsx-dev-runtime.web.js.map +0 -1
  61. package/dist/jsx/jsx-runtime.web.d.ts +0 -1
  62. package/dist/jsx/jsx-runtime.web.js +0 -18
  63. package/dist/jsx/jsx-runtime.web.js.map +0 -1
  64. package/dist/web/index.d.ts +0 -408
  65. package/dist/web/index.js +0 -3905
  66. package/dist/web/index.js.map +0 -1
@@ -0,0 +1,214 @@
1
+ import * as React$1 from 'react';
2
+ import { ReactNode } from 'react';
3
+ import { supports } from '@webspatial/core-sdk/runtime';
4
+ import { Vec3, SpatialSceneCreationOptions, SpatialSceneType, SpatialBoxGeometryOptions, SpatialConeGeometryOptions, SpatialCylinderGeometryOptions, SpatialPlaneGeometryOptions, SpatialSphereGeometryOptions, SpatialUnlitMaterialOptions } from '@webspatial/core-sdk';
5
+ import { I as SpatializedElementRef, l as EntityRef, k as EntityProps, m as EntityRefShape, E as EntityEventHandler } from './Reality-BDyKL6th.js';
6
+ import { b as ModelRef } from './Model-DO5ps8NA.js';
7
+ import * as react_jsx_runtime from 'react/jsx-runtime';
8
+
9
+ /**
10
+ * Tracks which published React SDK entry root (`lazy` default vs `eager`) has
11
+ * been loaded in the current JS realm. Per spatial-lazy-load "Mixed-import
12
+ * shape is rejected" — mixing both roots in one bundle is unsupported.
13
+ *
14
+ * Enforcement is disabled under Vitest unless a test opts in via
15
+ * `__setEntryRegistryEnforcementForTests(true)` so suites that import both
16
+ * entries for export-shape comparison keep working.
17
+ */
18
+ type ReactSdkEntryKind = 'lazy' | 'eager';
19
+ declare class WebSpatialMixedEntryError extends Error {
20
+ readonly previous: ReactSdkEntryKind;
21
+ readonly next: ReactSdkEntryKind;
22
+ constructor(previous: ReactSdkEntryKind, next: ReactSdkEntryKind);
23
+ }
24
+
25
+ type WebSpatialBootErrorOptions = {
26
+ cause: unknown;
27
+ attempt: number;
28
+ };
29
+ declare class WebSpatialBootError extends Error {
30
+ readonly cause: unknown;
31
+ readonly attempt: number;
32
+ constructor({ cause, attempt }: WebSpatialBootErrorOptions);
33
+ }
34
+
35
+ type UseBootSpatialOptions = {
36
+ /**
37
+ * When `true` (default), invokes `bootSpatial()` once after mount.
38
+ * Set to `false` to call `boot()` manually.
39
+ */
40
+ auto?: boolean;
41
+ onReady?: () => void;
42
+ onError?: (error: WebSpatialBootError) => void;
43
+ };
44
+
45
+ type SpatialBootProps = {
46
+ children: ReactNode;
47
+ onReady?: UseBootSpatialOptions['onReady'];
48
+ onError?: UseBootSpatialOptions['onError'];
49
+ };
50
+
51
+ /**
52
+ * Runtime capability checks (`supports('Model')`, `supports('WindowScene', ['defaultSize'])`, ...).
53
+ * Spec: `openspec/specs/runtime-capabilities/spec.md`.
54
+ */
55
+ declare const WebSpatialRuntime: {
56
+ readonly supports: typeof supports;
57
+ };
58
+
59
+ declare function enableDebugTool(): void;
60
+
61
+ /**
62
+ * const e2e = await convertCoordinate(position, { from: elementOrEntity, to: elementOrEntity })
63
+ const e2w = await convertCoordinate(position, { from: elementOrEntity, to: window })
64
+ const w2e = await convertCoordinate(position, { from: window, to: elementOrEntity })
65
+ *
66
+ */
67
+
68
+ type CoordinateConvertible = Window | SpatializedElementRef<any> | EntityRef | ModelRef;
69
+ declare function convertCoordinate(position: Vec3, { from, to }: {
70
+ from: CoordinateConvertible;
71
+ to: CoordinateConvertible;
72
+ }): Promise<Vec3>;
73
+
74
+ declare function initScene(name: string, callback: (pre: SpatialSceneCreationOptions) => SpatialSceneCreationOptions, options?: {
75
+ type: SpatialSceneType;
76
+ }): void | undefined;
77
+
78
+ type WithChildren<T> = T & {
79
+ children?: React.ReactNode;
80
+ };
81
+ type EntityFacadeProps = WithChildren<EntityProps>;
82
+ type BoxEntityProps = WithChildren<EntityProps & {
83
+ materials?: string[];
84
+ } & SpatialBoxGeometryOptions>;
85
+ type SphereEntityProps = WithChildren<EntityProps & {
86
+ materials?: string[];
87
+ } & SpatialSphereGeometryOptions>;
88
+ type ConeEntityProps = WithChildren<EntityProps & {
89
+ materials?: string[];
90
+ } & SpatialConeGeometryOptions>;
91
+ type CylinderEntityProps = WithChildren<EntityProps & {
92
+ materials?: string[];
93
+ } & SpatialCylinderGeometryOptions>;
94
+ type PlaneEntityProps = WithChildren<EntityProps & {
95
+ materials?: string[];
96
+ } & SpatialPlaneGeometryOptions>;
97
+ type ModelEntityProps = WithChildren<EntityProps & EntityEventHandler & {
98
+ model: string;
99
+ materials?: string[];
100
+ }>;
101
+ type AttachmentEntityProps = {
102
+ attachment: string;
103
+ position?: [number, number, number];
104
+ size: {
105
+ width: number;
106
+ height: number;
107
+ };
108
+ };
109
+ declare const Entity: React$1.ForwardRefExoticComponent<EntityProps & {
110
+ children?: React.ReactNode;
111
+ } & React$1.RefAttributes<EntityRefShape>>;
112
+ declare const BoxEntity: React$1.ForwardRefExoticComponent<EntityProps & {
113
+ materials?: string[];
114
+ } & SpatialBoxGeometryOptions & {
115
+ children?: React.ReactNode;
116
+ } & React$1.RefAttributes<EntityRefShape>>;
117
+ declare const SphereEntity: React$1.ForwardRefExoticComponent<EntityProps & {
118
+ materials?: string[];
119
+ } & SpatialSphereGeometryOptions & {
120
+ children?: React.ReactNode;
121
+ } & React$1.RefAttributes<EntityRefShape>>;
122
+ declare const ConeEntity: React$1.ForwardRefExoticComponent<EntityProps & {
123
+ materials?: string[];
124
+ } & SpatialConeGeometryOptions & {
125
+ children?: React.ReactNode;
126
+ } & React$1.RefAttributes<EntityRefShape>>;
127
+ declare const CylinderEntity: React$1.ForwardRefExoticComponent<EntityProps & {
128
+ materials?: string[];
129
+ } & SpatialCylinderGeometryOptions & {
130
+ children?: React.ReactNode;
131
+ } & React$1.RefAttributes<EntityRefShape>>;
132
+ declare const PlaneEntity: React$1.ForwardRefExoticComponent<EntityProps & {
133
+ materials?: string[];
134
+ } & SpatialPlaneGeometryOptions & {
135
+ children?: React.ReactNode;
136
+ } & React$1.RefAttributes<EntityRefShape>>;
137
+ declare const ModelEntity: React$1.ForwardRefExoticComponent<EntityProps & EntityEventHandler & {
138
+ model: string;
139
+ materials?: string[];
140
+ } & {
141
+ children?: React.ReactNode;
142
+ } & React$1.RefAttributes<EntityRefShape>>;
143
+ declare const AttachmentEntity: {
144
+ (props: AttachmentEntityProps): react_jsx_runtime.JSX.Element | null;
145
+ displayName: string;
146
+ };
147
+
148
+ type UnlitMaterialProps = {
149
+ children?: ReactNode;
150
+ id: string;
151
+ } & SpatialUnlitMaterialOptions;
152
+ type MaterialProps = {
153
+ type: 'unlit';
154
+ } & UnlitMaterialProps;
155
+ type TextureProps = {
156
+ children?: ReactNode;
157
+ id: string;
158
+ url: string;
159
+ onLoad?: () => void;
160
+ onError?: (error: unknown) => void;
161
+ };
162
+ type ModelAssetProps = {
163
+ children?: ReactNode;
164
+ id: string;
165
+ src: string;
166
+ onLoad?: () => void;
167
+ onError?: (error: unknown) => void;
168
+ };
169
+ type AttachmentAssetProps = {
170
+ name: string;
171
+ children?: ReactNode;
172
+ };
173
+ declare const UnlitMaterial: {
174
+ (props: UnlitMaterialProps): react_jsx_runtime.JSX.Element | null;
175
+ displayName: string;
176
+ };
177
+ declare const Material: {
178
+ (props: MaterialProps): react_jsx_runtime.JSX.Element | null;
179
+ displayName: string;
180
+ };
181
+ declare const Texture: {
182
+ (props: TextureProps): react_jsx_runtime.JSX.Element | null;
183
+ displayName: string;
184
+ };
185
+ declare const ModelAsset: {
186
+ (props: ModelAssetProps): react_jsx_runtime.JSX.Element | null;
187
+ displayName: string;
188
+ };
189
+ declare const AttachmentAsset: {
190
+ (props: AttachmentAssetProps): react_jsx_runtime.JSX.Element | null;
191
+ displayName: string;
192
+ };
193
+
194
+ type SceneGraphProps = {
195
+ children?: ReactNode;
196
+ };
197
+ /**
198
+ * Default-entry facade for `SceneGraph`. Fallback is `null` (children NOT
199
+ * mounted), matching entity / asset facades and the usual authoring shape
200
+ * under `<Reality>` (whose fallback already suppresses the child subtree).
201
+ * Per spec per-component fallback table ("`SceneGraph` / `World` → `null`").
202
+ *
203
+ * **PARITY (spec tasks.md §15.6)**: Path 2 unpinned in
204
+ * `runtime-capabilities` today; the parity test is tracked as `it.todo`
205
+ * under §15.8 (see `src/__tests__/parity.test.tsx`). Once the real-impl
206
+ * unsupported branch lands or the spec amendment defines it, the
207
+ * existing `null` fallback here MUST stay aligned.
208
+ */
209
+ declare function SceneGraph({ children }: SceneGraphProps): react_jsx_runtime.JSX.Element | null;
210
+ declare namespace SceneGraph {
211
+ var displayName: string;
212
+ }
213
+
214
+ export { type AttachmentAssetProps as A, type BoxEntityProps as B, type ConeEntityProps as C, type EntityFacadeProps as E, type MaterialProps as M, type PlaneEntityProps as P, type SpatialBootProps as S, type TextureProps as T, type UnlitMaterialProps as U, WebSpatialBootError as W, type AttachmentEntityProps as a, type CylinderEntityProps as b, type ModelAssetProps as c, type ModelEntityProps as d, type SceneGraphProps as e, type SphereEntityProps as f, WebSpatialMixedEntryError as g, WebSpatialRuntime as h, convertCoordinate as i, enableDebugTool as j, initScene as k, AttachmentAsset as l, AttachmentEntity as m, BoxEntity as n, ConeEntity as o, CylinderEntity as p, Entity as q, Material as r, ModelAsset as s, ModelEntity as t, PlaneEntity as u, SceneGraph as v, SphereEntity as w, Texture as x, UnlitMaterial as y };
@@ -0,0 +1,2 @@
1
+ var REGISTRY_KEY="__WEBSPATIAL_REACT_SDK_ENTRY__",hasReportedMixed=!1,enforcementEnabled=!0,WebSpatialMixedEntryError=class extends Error{previous;next;constructor(previous,next){let prevPath=previous==="eager"?"@webspatial/react-sdk/eager":"@webspatial/react-sdk",nextPath=next==="eager"?"@webspatial/react-sdk/eager":"@webspatial/react-sdk";super(`Mixed @webspatial/react-sdk entry roots: already loaded ${prevPath}, then ${nextPath}. Use exactly one import root per application bundle (including transitive dependencies).`),this.name="WebSpatialMixedEntryError",this.previous=previous,this.next=next}};function registryGlobal(){return globalThis}function shouldEnforce(){return!(!enforcementEnabled||typeof process<"u"&&process.env.VITEST==="true"&&!registryGlobal().__WEBSPATIAL_ENTRY_REGISTRY_ENFORCE__)}function registerReactSdkEntry(kind){let g=registryGlobal(),previous=g[REGISTRY_KEY];if(previous!==kind){if(previous!==void 0){if(hasReportedMixed)return;hasReportedMixed=!0;let error=new WebSpatialMixedEntryError(previous,kind);if(shouldEnforce())throw error;typeof process<"u"&&process.env.NODE_ENV!=="production"&&console.error(`[WebSpatial] ${error.message}`);return}g[REGISTRY_KEY]=kind}}export{WebSpatialMixedEntryError,registerReactSdkEntry};
2
+ //# sourceMappingURL=chunk-6JSRUX7P.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/runtime/entryRegistry.ts"],"sourcesContent":["/**\n * Tracks which published React SDK entry root (`lazy` default vs `eager`) has\n * been loaded in the current JS realm. Per spatial-lazy-load \"Mixed-import\n * shape is rejected\" — mixing both roots in one bundle is unsupported.\n *\n * Enforcement is disabled under Vitest unless a test opts in via\n * `__setEntryRegistryEnforcementForTests(true)` so suites that import both\n * entries for export-shape comparison keep working.\n */\n\nexport type ReactSdkEntryKind = 'lazy' | 'eager'\n\nconst REGISTRY_KEY = '__WEBSPATIAL_REACT_SDK_ENTRY__'\n\nlet hasReportedMixed = false\nlet enforcementEnabled = true\n\nexport class WebSpatialMixedEntryError extends Error {\n readonly previous: ReactSdkEntryKind\n readonly next: ReactSdkEntryKind\n\n constructor(previous: ReactSdkEntryKind, next: ReactSdkEntryKind) {\n const prevPath =\n previous === 'eager'\n ? '@webspatial/react-sdk/eager'\n : '@webspatial/react-sdk'\n const nextPath =\n next === 'eager' ? '@webspatial/react-sdk/eager' : '@webspatial/react-sdk'\n super(\n `Mixed @webspatial/react-sdk entry roots: already loaded ${prevPath}, then ${nextPath}. ` +\n 'Use exactly one import root per application bundle (including transitive dependencies).',\n )\n this.name = 'WebSpatialMixedEntryError'\n this.previous = previous\n this.next = next\n }\n}\n\ntype RegistryGlobal = typeof globalThis & {\n [REGISTRY_KEY]?: ReactSdkEntryKind\n __WEBSPATIAL_ENTRY_REGISTRY_ENFORCE__?: boolean\n}\n\nfunction registryGlobal(): RegistryGlobal {\n return globalThis as RegistryGlobal\n}\n\nfunction shouldEnforce(): boolean {\n if (!enforcementEnabled) return false\n if (\n typeof process !== 'undefined' &&\n process.env.VITEST === 'true' &&\n !registryGlobal().__WEBSPATIAL_ENTRY_REGISTRY_ENFORCE__\n ) {\n return false\n }\n return true\n}\n\n/**\n * Called at module-evaluation time from `src/index.ts` (lazy) and\n * `src/eager.ts` (eager). Idempotent when the same kind registers twice.\n */\nexport function registerReactSdkEntry(kind: ReactSdkEntryKind): void {\n const g = registryGlobal()\n const previous = g[REGISTRY_KEY]\n if (previous === kind) return\n if (previous !== undefined) {\n if (hasReportedMixed) return\n hasReportedMixed = true\n const error = new WebSpatialMixedEntryError(previous, kind)\n if (shouldEnforce()) {\n throw error\n }\n if (\n typeof process !== 'undefined' &&\n process.env.NODE_ENV !== 'production'\n ) {\n // eslint-disable-next-line no-console\n console.error(`[WebSpatial] ${error.message}`)\n }\n return\n }\n g[REGISTRY_KEY] = kind\n}\n\nexport function getRegisteredReactSdkEntry(): ReactSdkEntryKind | undefined {\n return registryGlobal()[REGISTRY_KEY]\n}\n\nexport function __setEntryRegistryEnforcementForTests(enabled: boolean): void {\n enforcementEnabled = enabled\n registryGlobal().__WEBSPATIAL_ENTRY_REGISTRY_ENFORCE__ = enabled\n}\n\nexport function __resetEntryRegistryForTests(): void {\n hasReportedMixed = false\n enforcementEnabled = true\n const g = registryGlobal()\n delete g[REGISTRY_KEY]\n delete g.__WEBSPATIAL_ENTRY_REGISTRY_ENFORCE__\n}\n"],"mappings":"AAYA,IAAM,aAAe,iCAEjB,iBAAmB,GACnB,mBAAqB,GAEZ,0BAAN,cAAwC,KAAM,CAC1C,SACA,KAET,YAAY,SAA6B,KAAyB,CAChE,IAAM,SACJ,WAAa,QACT,8BACA,wBACA,SACJ,OAAS,QAAU,8BAAgC,wBACrD,MACE,2DAA2D,QAAQ,UAAU,QAAQ,2FAEvF,EACA,KAAK,KAAO,4BACZ,KAAK,SAAW,SAChB,KAAK,KAAO,IACd,CACF,EAOA,SAAS,gBAAiC,CACxC,OAAO,UACT,CAEA,SAAS,eAAyB,CAEhC,MADI,GAAC,oBAEH,OAAO,QAAY,KACnB,QAAQ,IAAI,SAAW,QACvB,CAAC,eAAe,EAAE,sCAKtB,CAMO,SAAS,sBAAsB,KAA+B,CACnE,IAAM,EAAI,eAAe,EACnB,SAAW,EAAE,YAAY,EAC/B,GAAI,WAAa,KACjB,IAAI,WAAa,OAAW,CAC1B,GAAI,iBAAkB,OACtB,iBAAmB,GACnB,IAAM,MAAQ,IAAI,0BAA0B,SAAU,IAAI,EAC1D,GAAI,cAAc,EAChB,MAAM,MAGN,OAAO,QAAY,KACnB,QAAQ,IAAI,WAAa,cAGzB,QAAQ,MAAM,gBAAgB,MAAM,OAAO,EAAE,EAE/C,MACF,CACA,EAAE,YAAY,EAAI,KACpB","names":[]}
@@ -0,0 +1,2 @@
1
+ import{detectSpatialRuntime,isSpatialReady,loadSpatialImpl,requireSpatialImpl,subscribeSpatialReady}from"./chunk-GG2QK5MA.js";import{markWebSpatialPrimitive}from"./chunk-QHUROD77.js";var hasBeenCalled=!1;async function bootSpatial(){hasBeenCalled=!0,detectSpatialRuntime()!==null&&await loadSpatialImpl()}function hasBootSpatialBeenCalled(){return hasBeenCalled}import{useState,useSyncExternalStore}from"react";var noopUnsubscribe=()=>{},noopSubscribe=()=>noopUnsubscribe,alwaysFalse=()=>!1;function useSpatialReady(){let[hasSpatialRuntime]=useState(()=>detectSpatialRuntime()!==null);return useSyncExternalStore(hasSpatialRuntime?subscribeSpatialReady:noopSubscribe,hasSpatialRuntime?isSpatialReady:alwaysFalse,alwaysFalse)}import{forwardRef}from"react";var hasWarned=!1;function warnBootForgotten(componentName){typeof process<"u"&&process.env.NODE_ENV==="production"||hasWarned||detectSpatialRuntime()!==null&&(isSpatialReady()||hasBootSpatialBeenCalled()||(hasWarned=!0,console.warn(`[WebSpatial] ${componentName} rendered fallback in a WebSpatial runtime because bootSpatial() may not have been awaited. Call \`await bootSpatial()\` from @webspatial/react-sdk before initial render.`)))}import{jsx}from"react/jsx-runtime";function ModelFacadeImpl(props,ref){if(!useSpatialReady())return warnBootForgotten("Model"),renderModelFallback(props,ref);let RealModel=requireSpatialImpl().Model;return jsx(RealModel,{...props,ref})}var Model=forwardRef(ModelFacadeImpl);Model.displayName="Model";markWebSpatialPrimitive(Model,"Model");function renderModelFallback(props,ref){let{onSpatialTap:_onSpatialTap,onSpatialDragStart:_onSpatialDragStart,onSpatialDrag:_onSpatialDrag,onSpatialDragEnd:_onSpatialDragEnd,onSpatialRotate:_onSpatialRotate,onSpatialRotateEnd:_onSpatialRotateEnd,onSpatialMagnify:_onSpatialMagnify,onSpatialMagnifyEnd:_onSpatialMagnifyEnd,spatialEventOptions:_spatialEventOptions,"enable-xr":_enableXR,...modelProps}=props;return jsx("model",{ref,...modelProps})}import{forwardRef as forwardRef2}from"react";import{jsx as jsx2}from"react/jsx-runtime";function RealityFacadeImpl(props,ref){if(!useSpatialReady())return warnBootForgotten("Reality"),renderRealityFallback(props,ref);let RealReality=requireSpatialImpl().Reality;return jsx2(RealReality,{...props,ref})}var Reality=forwardRef2(RealityFacadeImpl);Reality.displayName="Reality";markWebSpatialPrimitive(Reality,"Reality");function renderRealityFallback(props,ref){let{children:_children,onSpatialTap:_onSpatialTap,onSpatialDragStart:_onSpatialDragStart,onSpatialDrag:_onSpatialDrag,onSpatialDragEnd:_onSpatialDragEnd,onSpatialRotate:_onSpatialRotate,onSpatialRotateEnd:_onSpatialRotateEnd,onSpatialMagnify:_onSpatialMagnify,onSpatialMagnifyEnd:_onSpatialMagnifyEnd,spatialEventOptions:_spatialEventOptions,...divProps}=props;return jsx2("div",{...divProps,ref,"aria-hidden":!0})}import{forwardRef as forwardRef3}from"react";import{jsx as jsx3}from"react/jsx-runtime";var SPATIAL_EVENT_PROPS=["onSpatialTap","onSpatialDragStart","onSpatialDrag","onSpatialDragEnd","onSpatialRotate","onSpatialRotateEnd","onSpatialMagnify","onSpatialMagnifyEnd","spatialEventOptions","onSpatialContentReady","xr-animation"],facadeCache=new Map;function withSpatialized2DElementContainer(Component){let cached=facadeCache.get(Component);if(cached)return cached;let FacadeWrapper=forwardRef3(function(givenProps,ref){if(!useSpatialReady()){warnBootForgotten("withSpatialized2DElementContainer");let{component:_component,...rest}=givenProps,passthrough=stripSpatialOnlyProps(rest);return jsx3(Component,{...passthrough,ref})}let RealHOC=requireSpatialImpl().withSpatialized2DElementContainer,RealComponent=RealHOC(Component);return jsx3(RealComponent,{...givenProps,ref})});return FacadeWrapper.displayName=`WithSpatialized2DElementContainer(${componentDisplayName(Component)})`,facadeCache.set(Component,FacadeWrapper),FacadeWrapper}function stripSpatialOnlyProps(props){let out={};for(let key of Object.keys(props))SPATIAL_EVENT_PROPS.includes(key)||(out[key]=props[key]);return out}function componentDisplayName(Component){if(typeof Component=="string")return Component;let c=Component;return c.displayName||c.name||"Component"}import{forwardRef as forwardRef4}from"react";import{jsx as jsx4}from"react/jsx-runtime";var facadeCache2=new Map;function withSpatialMonitor(El){let cached=facadeCache2.get(El);if(cached)return cached;let FacadeWrapper=forwardRef4(function(givenProps,ref){if(!useSpatialReady()){warnBootForgotten("withSpatialMonitor");let{El:_ignoredEl,...passthrough}=givenProps;return jsx4(El,{...passthrough,ref})}let RealHOC=requireSpatialImpl().withSpatialMonitor,RealWrapper=RealHOC(El);return jsx4(RealWrapper,{...givenProps,ref})});return FacadeWrapper.displayName=`WithSpatialMonitor(${componentDisplayName2(El)})`,facadeCache2.set(El,FacadeWrapper),FacadeWrapper}function componentDisplayName2(El){if(typeof El=="string")return El;let c=El;return c.displayName||c.name||"Component"}export{bootSpatial,useSpatialReady,warnBootForgotten,Model,Reality,withSpatialized2DElementContainer,withSpatialMonitor};
2
+ //# sourceMappingURL=chunk-BTLTBCA7.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/runtime/boot.ts","../src/runtime/useSpatialReady.ts","../src/facades/Model.tsx","../src/facades/shared/warnBootForgotten.ts","../src/facades/Reality.tsx","../src/facades/withSpatialized2DElementContainer.tsx","../src/facades/withSpatialMonitor.tsx"],"sourcesContent":["import { loadSpatialImpl } from './bridge'\nimport { detectSpatialRuntime } from './detect'\n\nlet hasBeenCalled = false\n\nexport async function bootSpatial(): Promise<void> {\n hasBeenCalled = true\n\n if (detectSpatialRuntime() === null) {\n return\n }\n\n await loadSpatialImpl()\n}\n\n/**\n * Returns `true` once `bootSpatial()` has been invoked at least once on this\n * page (independent of resolution / rejection / runtime gating). Consumed by\n * the facades' dev-mode \"boot was forgotten\" warning per spatial-lazy-load\n * spec's \"Dev-mode warning when boot is forgotten in a WebSpatial runtime\"\n * Scenario. NOT part of the documented public API.\n */\nexport function hasBootSpatialBeenCalled(): boolean {\n return hasBeenCalled\n}\n\nexport function __resetBootStateForTests(): void {\n hasBeenCalled = false\n}\n","'use client'\n\nimport { useState, useSyncExternalStore } from 'react'\nimport { isSpatialReady, subscribeSpatialReady } from './bridge'\nimport { detectSpatialRuntime } from './detect'\n\n// Module-level constants so non-WebSpatial subscribers and SSR snapshots are\n// referentially stable across renders, per spatial-lazy-load spec's\n// \"getServerSnapshot returns a stable constant\" Scenario and design.md §4\n// (noopSubscribe / alwaysFalse pattern).\nconst noopUnsubscribe = (): void => {}\nconst noopSubscribe = (): (() => void) => noopUnsubscribe\nconst alwaysFalse = (): false => false\n\nexport function useSpatialReady(): boolean {\n const [hasSpatialRuntime] = useState(() => detectSpatialRuntime() !== null)\n\n return useSyncExternalStore(\n hasSpatialRuntime ? subscribeSpatialReady : noopSubscribe,\n hasSpatialRuntime ? isSpatialReady : alwaysFalse,\n alwaysFalse,\n )\n}\n","'use client'\n\nimport { ForwardedRef, forwardRef } from 'react'\nimport type { ModelProps, ModelRef } from '../Model'\nimport { requireSpatialImpl } from '../runtime/bridge'\nimport { useSpatialReady } from '../runtime/useSpatialReady'\nimport { markWebSpatialPrimitive } from '../jsx/primitive-marker'\nimport { warnBootForgotten } from './shared/warnBootForgotten'\n\nexport type { ModelProps, ModelRef }\n\n/**\n * Default-entry facade for `Model`. Renders the spec-pinned degraded\n * native `<model>` element when the spatial chunk is not ready, and\n * delegates to the real `Model` implementation once `bootSpatial()`\n * resolves in a WebSpatial runtime.\n *\n * Per spatial-lazy-load spec \"Component facades\" + \"Model fallback\n * renders degraded `<model>` tag\" Scenarios. Not wrapped in\n * `React.memo` (per facade conventions).\n */\nfunction ModelFacadeImpl(props: ModelProps, ref: ForwardedRef<ModelRef>) {\n const ready = useSpatialReady()\n if (!ready) {\n warnBootForgotten('Model')\n return renderModelFallback(props, ref)\n }\n const RealModel = requireSpatialImpl().Model\n return <RealModel {...props} ref={ref} />\n}\n\nexport const Model = forwardRef<ModelRef, ModelProps>(ModelFacadeImpl)\nModel.displayName = 'Model'\n// Brand so the JSX runtime short-circuits `Model` regardless of whether the\n// default-entry facade or the eager-entry real implementation reaches it.\nmarkWebSpatialPrimitive(Model, 'Model')\n\nfunction renderModelFallback(\n props: ModelProps,\n ref: ForwardedRef<ModelRef>,\n): JSX.Element {\n // Strip spatial-only event props + spatialEventOptions before reaching the\n // native <model> element (per spec \"Model fallback renders degraded\n // <model> tag\" Scenario).\n const {\n onSpatialTap: _onSpatialTap,\n onSpatialDragStart: _onSpatialDragStart,\n onSpatialDrag: _onSpatialDrag,\n onSpatialDragEnd: _onSpatialDragEnd,\n onSpatialRotate: _onSpatialRotate,\n onSpatialRotateEnd: _onSpatialRotateEnd,\n onSpatialMagnify: _onSpatialMagnify,\n onSpatialMagnifyEnd: _onSpatialMagnifyEnd,\n spatialEventOptions: _spatialEventOptions,\n 'enable-xr': _enableXR,\n ...modelProps\n } = props\n return <model ref={ref} {...modelProps} />\n}\n","import { hasBootSpatialBeenCalled } from '../../runtime/boot'\nimport { isSpatialReady } from '../../runtime/bridge'\nimport { detectSpatialRuntime } from '../../runtime/detect'\n\nlet hasWarned = false\n\n/**\n * One-shot dev-mode console warning when a facade renders fallback in a\n * WebSpatial runtime because `bootSpatial()` was never called.\n *\n * Per spatial-lazy-load spec Scenarios \"Dev-mode warning when boot is forgotten\n * in a WebSpatial runtime\" + \"No dev-mode warning in non-WebSpatial browsers\":\n * - Plain web (`detectSpatialRuntime() === null`): silent — fallback IS the\n * final intended display.\n * - `bootSpatial()` already called (pending / rejected / succeeded): silent —\n * the developer wired the boot path; this warning would be misleading.\n * - Bridge ready (`isSpatialReady()` is true): silent — facade is about to\n * render the real implementation anyway.\n * - WebSpatial runtime + boot not yet called + bridge not ready: warn once.\n *\n * Stripped from production builds via `process.env.NODE_ENV` guard\n * (consumer bundlers / tsup minify dead-code).\n */\nexport function warnBootForgotten(componentName: string): void {\n if (typeof process !== 'undefined' && process.env.NODE_ENV === 'production') {\n return\n }\n if (hasWarned) return\n if (detectSpatialRuntime() === null) return\n if (isSpatialReady()) return\n if (hasBootSpatialBeenCalled()) return\n\n hasWarned = true\n console.warn(\n `[WebSpatial] ${componentName} rendered fallback in a WebSpatial runtime because bootSpatial() may not have been awaited. Call \\`await bootSpatial()\\` from @webspatial/react-sdk before initial render.`,\n )\n}\n\nexport function __resetBootForgottenWarningForTests(): void {\n hasWarned = false\n}\n","'use client'\n\nimport { ForwardedRef, forwardRef } from 'react'\nimport type { RealityProps } from '../reality/components/Reality'\nimport type { SpatializedElementRef } from '../spatialized-container/types'\nimport { requireSpatialImpl } from '../runtime/bridge'\nimport { useSpatialReady } from '../runtime/useSpatialReady'\nimport { markWebSpatialPrimitive } from '../jsx/primitive-marker'\nimport { warnBootForgotten } from './shared/warnBootForgotten'\n\nexport type { RealityProps }\n\n/**\n * Default-entry facade for `Reality`. Renders a single\n * `<div aria-hidden=\"true\">` placeholder when the spatial chunk is not\n * ready (preserving the layout box and excluding the React children\n * subtree, per spec) and delegates to the real `Reality` once boot\n * resolves in a WebSpatial runtime.\n *\n * **PARITY (spec tasks.md §15.6)**: this Path 1 fallback is pinned\n * verbatim by `runtime-capabilities` \"`Reality` unsupported fallback\"\n * Scenario. The real-impl Path 2 in `src/reality/components/Reality.tsx`\n * does NOT yet render this placeholder — it currently mounts nothing\n * when `getSession()` returns null. Drift is tracked under §15.8 as an\n * OpenSpec follow-up (see `src/__tests__/parity.test.tsx` \"Reality\n * parity\" `it.todo`). Do not modify this Path 1 fallback without first\n * aligning the real-impl branch.\n */\nfunction RealityFacadeImpl(\n props: RealityProps,\n ref: ForwardedRef<SpatializedElementRef>,\n) {\n const ready = useSpatialReady()\n if (!ready) {\n warnBootForgotten('Reality')\n return renderRealityFallback(props, ref)\n }\n const RealReality = requireSpatialImpl().Reality\n return <RealReality {...props} ref={ref} />\n}\n\nexport const Reality = forwardRef<SpatializedElementRef, RealityProps>(\n RealityFacadeImpl,\n)\nReality.displayName = 'Reality'\n// Brand so the JSX runtime short-circuits `Reality` regardless of whether the\n// default-entry facade or the eager-entry real implementation reaches it.\nmarkWebSpatialPrimitive(Reality, 'Reality')\n\nfunction renderRealityFallback(\n props: RealityProps,\n ref: ForwardedRef<SpatializedElementRef>,\n): JSX.Element {\n // Strip spatial-only event handlers + spatialEventOptions + children before\n // reaching the host <div>; per spec the child subtree MUST NOT mount and\n // the placeholder MUST be excluded from focus + a11y tree.\n const {\n children: _children,\n onSpatialTap: _onSpatialTap,\n onSpatialDragStart: _onSpatialDragStart,\n onSpatialDrag: _onSpatialDrag,\n onSpatialDragEnd: _onSpatialDragEnd,\n onSpatialRotate: _onSpatialRotate,\n onSpatialRotateEnd: _onSpatialRotateEnd,\n onSpatialMagnify: _onSpatialMagnify,\n onSpatialMagnifyEnd: _onSpatialMagnifyEnd,\n spatialEventOptions: _spatialEventOptions,\n ...divProps\n } = props as RealityProps & { spatialEventOptions?: unknown }\n return (\n <div {...divProps} ref={ref as ForwardedRef<HTMLDivElement>} aria-hidden />\n )\n}\n","'use client'\n\nimport { ComponentType, ElementType, ForwardedRef, forwardRef } from 'react'\nimport type {\n Spatialized2DElementContainerProps,\n SpatializedElementRef,\n} from '../spatialized-container/types'\nimport { requireSpatialImpl } from '../runtime/bridge'\nimport { useSpatialReady } from '../runtime/useSpatialReady'\nimport { warnBootForgotten } from './shared/warnBootForgotten'\n\nconst SPATIAL_EVENT_PROPS = [\n 'onSpatialTap',\n 'onSpatialDragStart',\n 'onSpatialDrag',\n 'onSpatialDragEnd',\n 'onSpatialRotate',\n 'onSpatialRotateEnd',\n 'onSpatialMagnify',\n 'onSpatialMagnifyEnd',\n 'spatialEventOptions',\n 'onSpatialContentReady',\n 'xr-animation',\n] as const\n\nconst facadeCache = new Map<ElementType, ComponentType<any>>()\n\n/**\n * Default-entry facade for the `withSpatialized2DElementContainer(Comp)` HOC.\n *\n * Per spec \"HOC facade preserves wrapper-cache identity contract\" Scenario:\n * passing the same `Component` reference more than once returns the same\n * wrapper facade reference. Cache key is the raw `Component` reference; no\n * normalization.\n *\n * In fallback mode the wrapper is a transparent passthrough — `<Component\n * {...passthroughProps} ref={ref} />` after stripping spatial-only event\n * handlers / spatial-only options. Once `bootSpatial()` resolves, the\n * wrapper renders the real spatialized container by delegating to the real\n * HOC produced via `requireSpatialImpl().withSpatialized2DElementContainer`\n * (the real HOC has its own internal cache, so `RealHOC(Component)`\n * returns a stable reference across renders).\n *\n * **PARITY (spec tasks.md §15.6)**: Path 2 unpinned in\n * `runtime-capabilities` today; tracked under §15.8 (see\n * `src/__tests__/parity.test.tsx` \"withSpatialized2DElementContainer …\n * parity\" `it.todo`). Keep this transparent-passthrough fallback in sync\n * with whatever the real-impl unsupported branch later commits to.\n */\nexport function withSpatialized2DElementContainer<P extends ElementType>(\n Component: P,\n): P {\n const cached = facadeCache.get(Component)\n if (cached) {\n return cached as unknown as P\n }\n\n const FacadeWrapper = forwardRef(function FacadeWrapper(\n givenProps: Spatialized2DElementContainerProps<P>,\n ref: ForwardedRef<SpatializedElementRef>,\n ) {\n const ready = useSpatialReady()\n\n if (!ready) {\n warnBootForgotten('withSpatialized2DElementContainer')\n const { component: _component, ...rest } = givenProps as Record<\n string,\n unknown\n > & { component?: unknown }\n // Plain-web / pre-boot fallback is a transparent passthrough. Per the\n // product-confirmed semantics, `onSpatialContentReady` fires ONLY when a\n // real WebSpatial spatial content host exists (the portal path in\n // `useSpatialContentReady`); it MUST NOT fire on any degraded/plain-web\n // host. `stripSpatialOnlyProps` removes it (and the other spatial-only\n // props) so it is neither invoked here nor leaked as a DOM attribute.\n const passthrough = stripSpatialOnlyProps(rest)\n const Element = Component as ElementType\n return <Element {...(passthrough as any)} ref={ref as any} />\n }\n const RealHOC = requireSpatialImpl()\n .withSpatialized2DElementContainer as typeof withSpatialized2DElementContainer\n const RealWrapper = RealHOC(Component)\n const RealComponent = RealWrapper as unknown as ComponentType<\n Spatialized2DElementContainerProps<P> & { ref?: unknown }\n >\n return <RealComponent {...givenProps} ref={ref as any} />\n })\n\n FacadeWrapper.displayName = `WithSpatialized2DElementContainer(${componentDisplayName(Component)})`\n\n facadeCache.set(Component, FacadeWrapper)\n return FacadeWrapper as unknown as P\n}\n\nexport function __resetWithSpatialized2DElementContainerCacheForTests(): void {\n facadeCache.clear()\n}\n\nfunction stripSpatialOnlyProps(props: Record<string, unknown>) {\n const out: Record<string, unknown> = {}\n for (const key of Object.keys(props)) {\n if ((SPATIAL_EVENT_PROPS as readonly string[]).includes(key)) continue\n out[key] = props[key]\n }\n return out\n}\n\nfunction componentDisplayName(Component: ElementType): string {\n if (typeof Component === 'string') return Component\n const c = Component as { displayName?: string; name?: string }\n return c.displayName || c.name || 'Component'\n}\n","'use client'\n\nimport { ComponentType, ElementType, Ref, forwardRef } from 'react'\nimport { requireSpatialImpl } from '../runtime/bridge'\nimport { useSpatialReady } from '../runtime/useSpatialReady'\nimport { warnBootForgotten } from './shared/warnBootForgotten'\n\nconst facadeCache = new Map<ElementType, ComponentType<any>>()\n\n/**\n * Default-entry facade for the `withSpatialMonitor(El)` HOC.\n *\n * Per spec \"HOC facade preserves wrapper-cache identity contract\" Scenario:\n * same `El` reference → same wrapper reference. Cache key is the raw `El`.\n *\n * Fallback renders `<El {...passthrough} ref={ref} />` (transparent\n * passthrough). After boot the wrapper delegates to the real\n * `withSpatialMonitor(El)` HOC, which has its own internal cache so\n * repeated calls return a stable reference.\n *\n * **PARITY (spec tasks.md §15.6)**: Path 2 unpinned in\n * `runtime-capabilities` today; tracked under §15.8 (see\n * `src/__tests__/parity.test.tsx` \"withSpatialMonitor … parity\"\n * `it.todo`). Keep this transparent-passthrough fallback in sync with\n * whatever the real-impl unsupported branch later commits to.\n */\nexport function withSpatialMonitor(El: ElementType): ElementType {\n const cached = facadeCache.get(El)\n if (cached) return cached\n\n const FacadeWrapper = forwardRef(function FacadeWrapper(\n givenProps: Record<string, unknown>,\n ref: Ref<HTMLElement>,\n ) {\n const ready = useSpatialReady()\n if (!ready) {\n warnBootForgotten('withSpatialMonitor')\n const { El: _ignoredEl, ...passthrough } = givenProps\n const Element = El\n return <Element {...(passthrough as any)} ref={ref as any} />\n }\n const RealHOC = requireSpatialImpl()\n .withSpatialMonitor as typeof withSpatialMonitor\n const RealWrapper = RealHOC(El) as unknown as ComponentType<\n Record<string, unknown> & { ref?: unknown }\n >\n return <RealWrapper {...givenProps} ref={ref as any} />\n })\n\n FacadeWrapper.displayName = `WithSpatialMonitor(${componentDisplayName(El)})`\n\n facadeCache.set(El, FacadeWrapper)\n return FacadeWrapper\n}\n\nexport function __resetWithSpatialMonitorCacheForTests(): void {\n facadeCache.clear()\n}\n\nfunction componentDisplayName(El: ElementType): string {\n if (typeof El === 'string') return El\n const c = El as { displayName?: string; name?: string }\n return c.displayName || c.name || 'Component'\n}\n"],"mappings":"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","names":["forwardRef","jsx","forwardRef","forwardRef","jsx","forwardRef","forwardRef","jsx","facadeCache","forwardRef","componentDisplayName","componentDisplayName"]}
@@ -0,0 +1,2 @@
1
+ var WebSpatialRuntimeError=class extends Error{capability;constructor(capability,message){super(message??`Capability "${capability}" is not supported in this WebSpatial runtime`),this.name="WebSpatialRuntimeError",this.capability=capability}};var COMPONENT_KEYS=["Model","Reality","Entity","BoxEntity","SphereEntity","ConeEntity","CylinderEntity","PlaneEntity","SceneGraph","ModelAsset","ModelEntity","UnlitMaterial","Material","AttachmentAsset","AttachmentEntity"],CSS_KEYS=["-xr-background-material","-xr-back","-xr-depth","-xr-transform"],GESTURE_KEYS=["SpatialTapEvent","SpatialDragStartEvent","SpatialDragEvent","SpatialDragEndEvent","SpatialRotateEvent","SpatialRotateEndEvent","SpatialMagnifyEvent","SpatialMagnifyEndEvent"],ANIMATION_KEYS=["useAnimation"],JS_SCENE_KEYS=["useMetrics","convertCoordinate","initScene","WindowScene","VolumeScene"],ELEMENT_DOM_DEPTH_KEYS=["xrClientDepth","xrOffsetBack"],WINDOW_DOM_DEPTH_KEYS=["xrInnerDepth","xrOuterDepth"],DOM_DEPTH_KEYS=[...ELEMENT_DOM_DEPTH_KEYS,...WINDOW_DOM_DEPTH_KEYS],TOP_LEVEL_KEYS=[...COMPONENT_KEYS,...CSS_KEYS,...GESTURE_KEYS,...ANIMATION_KEYS,...JS_SCENE_KEYS,...DOM_DEPTH_KEYS],ALIAS_TO_CANONICAL={Box:"BoxEntity",Sphere:"SphereEntity",Cone:"ConeEntity",Cylinder:"CylinderEntity",Plane:"PlaneEntity",World:"SceneGraph"};function normalizeCapabilityName(name){return ALIAS_TO_CANONICAL[name]??name}var SUB_TOKENS_BY_NAME={Material:["unlit"],WindowScene:["defaultSize","resizability"],VolumeScene:["defaultSize","resizability","worldScaling","worldAlignment","baseplateVisibility"],SpatialRotateEvent:["constrainedToAxis"],AttachmentEntity:["placement"],Model:["autoplay","loop","stagemode","poster","loading","source","ready","currentSrc","entityTransform","paused","duration","playbackRate","play","pause","currentTime"]};function isKnownTopLevel(name){return TOP_LEVEL_KEYS.includes(name)}function isKnownSubToken(name,token){let allowed=SUB_TOKENS_BY_NAME[name];return allowed!==void 0&&allowed.includes(token)}function baseTrueFlags(){let flags={};for(let k of TOP_LEVEL_KEYS)flags[k]=!0;for(let[name,toks]of Object.entries(SUB_TOKENS_BY_NAME))for(let t of toks)flags[`${name}:${t}`]=!0;return flags}function matrixVision_1_5_0_Flags(){let flags=baseTrueFlags(),modelNo=["autoplay","loop","stagemode","poster","loading","source","paused","duration","playbackRate","play","pause","currentTime"];for(let t of modelNo)flags[`Model:${t}`]=!1;return flags["SpatialRotateEvent:constrainedToAxis"]=!0,flags.useAnimation=!1,flags["AttachmentEntity:placement"]=!1,flags}function matrixVision_1_6_0_Flags(){let flags=baseTrueFlags();for(let t of["stagemode","poster","loading","currentTime"])flags[`Model:${t}`]=!1;return flags["SpatialRotateEvent:constrainedToAxis"]=!0,flags.useAnimation=!1,flags["AttachmentEntity:placement"]=!1,flags}function matrixVision_1_7_0_Flags(){let flags=matrixVision_1_6_0_Flags();return flags["Model:currentTime"]=!0,flags["Model:loading"]=!0,flags["Model:poster"]=!0,flags}function matrixVision_1_8_0_Flags(){let flags=matrixVision_1_7_0_Flags();return flags.useAnimation=!0,flags}function matrixPico_0_1_1_Flags(){let flags=matrixVision_1_5_0_Flags();return flags.xrInnerDepth=!1,flags.xrOuterDepth=!1,flags}function matrixPico_0_1_2_Flags(){let flags=matrixVision_1_6_0_Flags();return flags.xrInnerDepth=!1,flags.xrOuterDepth=!1,flags["Model:currentTime"]=!0,flags["Model:poster"]=!0,flags}function matrixPico_0_2_2_Flags(){return matrixPico_0_1_2_Flags()}function matrixPico_0_3_1_Flags(){let flags=matrixPico_0_2_2_Flags();return flags["Model:loading"]=!0,flags}function matrixPico_0_4_90_Flags(){let flags=matrixPico_0_3_1_Flags();return flags.useAnimation=!0,flags["AttachmentEntity:placement"]=!0,flags}function visionOsRow_1_5_0(){return{version:"1.5.0",flags:matrixVision_1_5_0_Flags()}}function visionOsRow_1_6_0(){return{version:"1.6.0",flags:matrixVision_1_6_0_Flags()}}function visionOsRow_1_7_0(){return{version:"1.7.0",flags:matrixVision_1_7_0_Flags()}}function visionOsRow_1_8_0(){return{version:"1.8.0",flags:matrixVision_1_8_0_Flags()}}function picoOsRow_0_1_1(){return{version:"0.1.1",flags:matrixPico_0_1_1_Flags()}}function picoOsRow_0_1_2(){return{version:"0.1.2",flags:matrixPico_0_1_2_Flags()}}function picoOsRow_0_2_2(){return{version:"0.2.2",flags:matrixPico_0_2_2_Flags()}}function picoOsRow_0_3_1(){return{version:"0.3.1",flags:matrixPico_0_3_1_Flags()}}function picoOsRow_0_4_90(){return{version:"0.4.90",flags:matrixPico_0_4_90_Flags()}}var CAPABILITY_TABLE={visionos:[visionOsRow_1_5_0(),visionOsRow_1_6_0(),visionOsRow_1_7_0(),visionOsRow_1_8_0()],picoos:[picoOsRow_0_1_1(),picoOsRow_0_1_2(),picoOsRow_0_2_2(),picoOsRow_0_3_1(),picoOsRow_0_4_90()]};function compareSemver(a,b){let pa=parseSemverParts(a),pb=parseSemverParts(b);if(!pa||!pb)return String(a).localeCompare(String(b));let len=Math.max(pa.length,pb.length);for(let i=0;i<len;i++){let da=pa[i]??0,db=pb[i]??0;if(da!==db)return da-db}return 0}function parseSemverParts(v){let m=/^(\d+)(?:\.(\d+)(?:\.(\d+))?)?/.exec(v.trim());if(!m)return null;let major=Number(m[1]),minor=m[2]!==void 0?Number(m[2]):0,patch=m[3]!==void 0?Number(m[3]):0;return[major,minor,patch].some(n=>Number.isNaN(n))?null:[major,minor,patch]}function parseSemverOrNull(v){let m=/^(\d+(?:\.\d+){0,2})/.exec(v.trim());return m?m[1]:null}function parseShellToken(ua){let ws=/\bWSAppShell\/([\w.-]+)/i.exec(ua);if(ws?.[1])return{version:ws[1],source:"wsapp"};let pico=/\bPicoWebApp\/([\w.-]+)/i.exec(ua);return pico?.[1]?{version:pico[1],source:"picoapp"}:{version:null,source:null}}function inferPicoOs(ua){return/\bPicoWebApp\//i.test(ua)||/\bPicoBrowser\b/i.test(ua)}function inferVisionOsFromUa(ua){return/Mac OS X/i.test(ua)}function computeRuntimeFromUserAgent(userAgent){if(userAgent===void 0||userAgent==="")return{type:null,shellVersion:null};if(userAgent.includes("Puppeteer")){let{version:version2}=parseShellToken(userAgent);return{type:"puppeteer",shellVersion:version2}}let{version,source}=parseShellToken(userAgent);return version?source==="picoapp"||inferPicoOs(userAgent)?{type:"picoos",shellVersion:version}:source==="wsapp"?inferVisionOsFromUa(userAgent)?{type:"visionos",shellVersion:version}:{type:null,shellVersion:version}:{type:null,shellVersion:version}:{type:null,shellVersion:null}}var VISIONOS_DEBUG_SHELL_VERSION_PLACEHOLDER="WS_SHELL_VERSION",runtimeCache;function getRuntime(){return runtimeCache!==void 0?runtimeCache:typeof navigator>"u"?(runtimeCache={type:null,shellVersion:null},runtimeCache):(runtimeCache=computeRuntimeFromUserAgent(navigator.userAgent),runtimeCache)}function selectRow(type,shellVersion){let norm=parseSemverOrNull(shellVersion);if(!norm)return null;let rows=CAPABILITY_TABLE[type];if(!rows.length)return null;let sorted=[...rows].sort((a,b)=>compareSemver(a.version,b.version)),minV=sorted[0].version;if(compareSemver(norm,minV)<0)return null;let chosen=null;for(let row of sorted)if(compareSemver(row.version,norm)<=0)chosen=row;else break;return chosen}function supports(name,tokens){if(typeof name!="string")return!1;let canonical=normalizeCapabilityName(name);if(!isKnownTopLevel(canonical))return!1;let tokList=tokens===void 0?[]:Array.isArray(tokens)?[...tokens]:[];if(tokList.some(t=>typeof t!="string"))return!1;for(let t of tokList)if(!isKnownSubToken(canonical,t))return!1;let rt=getRuntime();if(rt.type==="puppeteer")return!0;if(rt.type===null||rt.shellVersion===null)return!1;if(rt.type==="visionos"&&rt.shellVersion===VISIONOS_DEBUG_SHELL_VERSION_PLACEHOLDER)return!0;let parsedShell=parseSemverOrNull(rt.shellVersion);if(!parsedShell||rt.type!=="visionos"&&rt.type!=="picoos")return!1;let row=selectRow(rt.type,parsedShell);return row?tokList.length===0?row.flags[canonical]===!0:row.flags[canonical]!==!0?!1:tokList.every(t=>row.flags[`${canonical}:${t}`]===!0):!1}var WebSpatialBootError=class extends Error{cause;attempt;constructor({cause,attempt}){super(`Failed to boot WebSpatial runtime on attempt ${attempt}`),this.name="WebSpatialBootError",this.cause=cause,this.attempt=attempt}};function detectSpatialRuntime(){return typeof window>"u"||typeof navigator>"u"?null:computeRuntimeFromUserAgent(navigator.userAgent).type}var spatialImpl=null,loadPromise=null,loadAttempt=0,spatialImplLoader=()=>import("./spatial.js"),readyListeners=new Set,errorListeners=new Set;function reportListenerError(error){typeof process<"u"&&process.env.NODE_ENV==="production"||console.error("[WebSpatial] spatial bridge listener threw:",error)}function notifyReadyListeners(){for(let listener of[...readyListeners])try{listener()}catch(error){reportListenerError(error)}}function notifyErrorListeners(error){for(let listener of[...errorListeners])try{listener(error)}catch(listenerError){reportListenerError(listenerError)}}function toBootError(error,attempt){return error instanceof WebSpatialBootError?error:new WebSpatialBootError({cause:error,attempt})}function getSpatialImpl(){return spatialImpl}function requireSpatialImpl(){if(spatialImpl===null)throw new Error("WebSpatial implementation is not ready");return spatialImpl}function isSpatialReady(){return spatialImpl!==null}function subscribeSpatialReady(listener){return readyListeners.add(listener),()=>{readyListeners.delete(listener)}}function onSpatialLoadError(listener){return errorListeners.add(listener),()=>{errorListeners.delete(listener)}}function loadSpatialImpl(){if(spatialImpl!==null)return Promise.resolve(spatialImpl);if(loadPromise!==null)return loadPromise;if(detectSpatialRuntime()===null)return Promise.resolve(null);let attempt=loadAttempt+1;return loadAttempt=attempt,loadPromise=spatialImplLoader().then(impl=>(spatialImpl=impl,loadPromise=null,notifyReadyListeners(),impl)).catch(error=>{loadPromise=null;let bootError=toBootError(error,attempt);throw notifyErrorListeners(bootError),bootError}),loadPromise}function __internalSetSpatialImpl(impl,_registrationToken){spatialImpl===null&&(spatialImpl=impl,loadAttempt=1,notifyReadyListeners())}export{WebSpatialRuntimeError,supports,detectSpatialRuntime,WebSpatialBootError,getSpatialImpl,requireSpatialImpl,isSpatialReady,subscribeSpatialReady,onSpatialLoadError,loadSpatialImpl,__internalSetSpatialImpl};
2
+ //# sourceMappingURL=chunk-GG2QK5MA.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../core/src/runtime/WebSpatialRuntimeError.ts","../../core/src/runtime/keys.ts","../../core/src/runtime/capability-data.ts","../../core/src/runtime/semver.ts","../../core/src/runtime/userAgent.ts","../../core/src/runtime/supports.ts","../src/runtime/errors.ts","../src/runtime/detect.ts","../src/runtime/bridge.ts"],"sourcesContent":["/**\n * Thrown when a runtime-gated JS API is invoked but `supports('<name>')` is false.\n * See OpenSpec `runtime-capabilities/spec.md` (Unsupported behavior contracts).\n */\nexport class WebSpatialRuntimeError extends Error {\n public readonly capability: string\n\n constructor(capability: string, message?: string) {\n super(\n message ??\n `Capability \"${capability}\" is not supported in this WebSpatial runtime`,\n )\n this.name = 'WebSpatialRuntimeError'\n this.capability = capability\n }\n}\n","/**\n * Canonical `supports(name)` key registry (OpenSpec `review.md` §3).\n * Aliases are normalized before lookup (see `normalizeCapabilityName`).\n *\n * @internal SDK contract data — not part of the public `@webspatial/react-sdk`\n * surface. Import via `@webspatial/core-sdk/runtime/keys` only for SDK demos,\n * contract tests, and capability-matrix tooling.\n */\n\nexport const COMPONENT_KEYS = [\n 'Model',\n 'Reality',\n 'Entity',\n 'BoxEntity',\n 'SphereEntity',\n 'ConeEntity',\n 'CylinderEntity',\n 'PlaneEntity',\n 'SceneGraph',\n 'ModelAsset',\n 'ModelEntity',\n 'UnlitMaterial',\n 'Material',\n 'AttachmentAsset',\n 'AttachmentEntity',\n] as const\n\nexport const CSS_KEYS = [\n '-xr-background-material',\n '-xr-back',\n '-xr-depth',\n '-xr-transform',\n] as const\n\nexport const GESTURE_KEYS = [\n 'SpatialTapEvent',\n 'SpatialDragStartEvent',\n 'SpatialDragEvent',\n 'SpatialDragEndEvent',\n 'SpatialRotateEvent',\n 'SpatialRotateEndEvent',\n 'SpatialMagnifyEvent',\n 'SpatialMagnifyEndEvent',\n] as const\n\nexport const ANIMATION_KEYS = ['useAnimation'] as const\n\nexport const JS_SCENE_KEYS = [\n 'useMetrics',\n 'convertCoordinate',\n 'initScene',\n 'WindowScene',\n 'VolumeScene',\n] as const\n\n/**\n * Spatialized container `ref` readbacks (`HTMLElement` / React `useDomProxy` Proxy).\n * See `global.d.ts` (`HTMLElement`) and `useDomProxy.ts` (`has` / `get` traps).\n */\nexport const ELEMENT_DOM_DEPTH_KEYS = ['xrClientDepth', 'xrOffsetBack'] as const\n\n/**\n * Scene / global readbacks on `Window` (`global.d.ts` → `Window`).\n */\nexport const WINDOW_DOM_DEPTH_KEYS = ['xrInnerDepth', 'xrOuterDepth'] as const\n\nexport const DOM_DEPTH_KEYS = [\n ...ELEMENT_DOM_DEPTH_KEYS,\n ...WINDOW_DOM_DEPTH_KEYS,\n] as const\n\n/** Top-level names accepted by `supports(name)` (canonical keys after alias normalization). */\nexport const TOP_LEVEL_KEYS = [\n ...COMPONENT_KEYS,\n ...CSS_KEYS,\n ...GESTURE_KEYS,\n ...ANIMATION_KEYS,\n ...JS_SCENE_KEYS,\n ...DOM_DEPTH_KEYS,\n] as const\n\n/** Union of documented capability keys; unknown strings may still be passed to `supports` (returns `false`). */\nexport type CapabilityKey = (typeof TOP_LEVEL_KEYS)[number]\n\nconst ALIAS_TO_CANONICAL: Record<string, string> = {\n Box: 'BoxEntity',\n Sphere: 'SphereEntity',\n Cone: 'ConeEntity',\n Cylinder: 'CylinderEntity',\n Plane: 'PlaneEntity',\n World: 'SceneGraph',\n}\n\nexport function normalizeCapabilityName(name: string): string {\n return ALIAS_TO_CANONICAL[name] ?? name\n}\n\n/** Known sub-tokens per canonical top-level `name` (AND semantics). */\nexport const SUB_TOKENS_BY_NAME: Readonly<Record<string, readonly string[]>> = {\n Material: ['unlit'],\n WindowScene: ['defaultSize', 'resizability'],\n VolumeScene: [\n 'defaultSize',\n 'resizability',\n 'worldScaling',\n 'worldAlignment',\n 'baseplateVisibility',\n ],\n SpatialRotateEvent: ['constrainedToAxis'],\n // Placement-shaped attachment JSB protocol (placementId + Vec3 transform +\n // meter width/height). Runtimes without it take the legacy payload\n // (parentEntityId + tuple position + point size).\n AttachmentEntity: ['placement'],\n Model: [\n 'autoplay',\n 'loop',\n 'stagemode',\n 'poster',\n 'loading',\n 'source',\n 'ready',\n 'currentSrc',\n 'entityTransform',\n 'paused',\n 'duration',\n 'playbackRate',\n 'play',\n 'pause',\n 'currentTime',\n ],\n}\n\nexport function isKnownTopLevel(name: string): boolean {\n return (TOP_LEVEL_KEYS as readonly string[]).includes(name)\n}\n\nexport function isKnownSubToken(name: string, token: string): boolean {\n const allowed = SUB_TOKENS_BY_NAME[name]\n return allowed !== undefined && allowed.includes(token)\n}\n","/**\n * Versioned capability rows transcribed from the product matrix (`capability-matrix.template.md`).\n * visionOS **WSAppShell/1.5.0** & **1.6.0** & **1.7.0** & **1.8.0**; picoOS **PicoWebApp/0.1.1** & **0.1.2** & **0.2.2** & **0.3.1** & **0.4.90** — see matrix in OpenSpec / product docs.\n *\n * **picoOS** rows use dedicated builders (alpha2.0 / alpha2.1 subtokens); visionOS rows are separate.\n */\nimport { SUB_TOKENS_BY_NAME, TOP_LEVEL_KEYS } from './keys'\n\nexport type CapabilityVersionRow = {\n /** Semver string from `WSAppShell` / `PicoWebApp` (see `review.md` §4). */\n version: string\n /** Top-level keys and `name:subToken` compound keys. */\n flags: Record<string, boolean>\n}\n\nfunction baseTrueFlags(): Record<string, boolean> {\n const flags: Record<string, boolean> = {}\n for (const k of TOP_LEVEL_KEYS) {\n flags[k] = true\n }\n for (const [name, toks] of Object.entries(SUB_TOKENS_BY_NAME)) {\n for (const t of toks) {\n flags[`${name}:${t}`] = true\n }\n }\n return flags\n}\n\n/**\n * visionOS **WSAppShell/1.5.0**.\n * Model: only `ready`, `currentSrc`, `entityTransform` among tracked sub-tokens are Y; SpatialRotateEvent:constrainedToAxis Y.\n */\nfunction matrixVision_1_5_0_Flags(): Record<string, boolean> {\n const flags = baseTrueFlags()\n const modelNo = [\n 'autoplay',\n 'loop',\n 'stagemode',\n 'poster',\n 'loading',\n 'source',\n 'paused',\n 'duration',\n 'playbackRate',\n 'play',\n 'pause',\n 'currentTime',\n ] as const\n for (const t of modelNo) {\n flags[`Model:${t}`] = false\n }\n flags['SpatialRotateEvent:constrainedToAxis'] = true\n // Container useAnimation is not supported until WSAppShell/1.8.0.\n flags['useAnimation'] = false\n // Placement-shaped attachment protocol lands in picoOS PicoWebApp/0.4.90\n // (OTA0); no visionOS shell decodes it yet.\n flags['AttachmentEntity:placement'] = false\n return flags\n}\n\n/**\n * visionOS **WSAppShell/1.6.0** — WebSpatial April / playback expansion (see product matrix).\n * Model: `stagemode`, `poster`, `loading`, `currentTime` remain N; rest of tracked Model sub-tokens Y.\n */\nfunction matrixVision_1_6_0_Flags(): Record<string, boolean> {\n const flags = baseTrueFlags()\n for (const t of ['stagemode', 'poster', 'loading', 'currentTime'] as const) {\n flags[`Model:${t}`] = false\n }\n flags['SpatialRotateEvent:constrainedToAxis'] = true\n // Container useAnimation is not supported until WSAppShell/1.8.0.\n flags['useAnimation'] = false\n // Placement-shaped attachment protocol lands in picoOS PicoWebApp/0.4.90\n // (OTA0); no visionOS shell decodes it yet.\n flags['AttachmentEntity:placement'] = false\n return flags\n}\n\n/**\n * visionOS **WSAppShell/1.7.0** — entity transform animation support.\n * Container `useAnimation` remains unavailable in this row.\n */\nfunction matrixVision_1_7_0_Flags(): Record<string, boolean> {\n const flags = matrixVision_1_6_0_Flags()\n flags['Model:currentTime'] = true\n flags['Model:loading'] = true\n flags['Model:poster'] = true\n return flags\n}\n\n/**\n * visionOS **WSAppShell/1.8.0**.\n */\nfunction matrixVision_1_8_0_Flags(): Record<string, boolean> {\n const flags = matrixVision_1_7_0_Flags()\n flags['useAnimation'] = true\n return flags\n}\n\n/**\n * picoOS **PicoWebApp/0.1.1** — alpha2.0 baseline (product matrix).\n * WindowScene / VolumeScene / Material subtokens Y; Model sub-tokens per matrix; **`xrInnerDepth` / `xrOuterDepth` N**.\n */\nfunction matrixPico_0_1_1_Flags(): Record<string, boolean> {\n const flags = matrixVision_1_5_0_Flags()\n flags.xrInnerDepth = false\n flags.xrOuterDepth = false\n return flags\n}\n\n/**\n * picoOS **PicoWebApp/0.1.2** — beta2.0 playback expansion (product matrix).\n * **`xrInnerDepth` / `xrOuterDepth` N** (same as 0.1.1).\n */\nfunction matrixPico_0_1_2_Flags(): Record<string, boolean> {\n const flags = matrixVision_1_6_0_Flags()\n flags.xrInnerDepth = false\n flags.xrOuterDepth = false\n flags['Model:currentTime'] = true\n flags['Model:poster'] = true\n return flags\n}\n\n/**\n * picoOS **PicoWebApp/0.2.2** — entity transform animation support.\n * Container `useAnimation` remains unavailable in this row.\n */\nfunction matrixPico_0_2_2_Flags(): Record<string, boolean> {\n const flags = matrixPico_0_1_2_Flags()\n return flags\n}\n\n/**\n * picoOS **PicoWebApp/0.3.1** — beta2.1\n */\nfunction matrixPico_0_3_1_Flags(): Record<string, boolean> {\n const flags = matrixPico_0_2_2_Flags()\n flags['Model:loading'] = true\n return flags\n}\n\n/**\n * picoOS **PicoWebApp/0.4.90** — OTA0 container animation support.\n */\nfunction matrixPico_0_4_90_Flags(): Record<string, boolean> {\n const flags = matrixPico_0_3_1_Flags()\n flags['useAnimation'] = true\n flags['AttachmentEntity:placement'] = true\n return flags\n}\n\nfunction visionOsRow_1_5_0(): CapabilityVersionRow {\n return { version: '1.5.0', flags: matrixVision_1_5_0_Flags() }\n}\n\nfunction visionOsRow_1_6_0(): CapabilityVersionRow {\n return { version: '1.6.0', flags: matrixVision_1_6_0_Flags() }\n}\n\nfunction visionOsRow_1_7_0(): CapabilityVersionRow {\n return { version: '1.7.0', flags: matrixVision_1_7_0_Flags() }\n}\n\n/**\n * Build the capability row for visionOS **WSAppShell/1.8.0**.\n */\nfunction visionOsRow_1_8_0(): CapabilityVersionRow {\n return { version: '1.8.0', flags: matrixVision_1_8_0_Flags() }\n}\n\nfunction picoOsRow_0_1_1(): CapabilityVersionRow {\n return { version: '0.1.1', flags: matrixPico_0_1_1_Flags() }\n}\n\n// Pico OS 6.0 Beta 2.0\nfunction picoOsRow_0_1_2(): CapabilityVersionRow {\n return { version: '0.1.2', flags: matrixPico_0_1_2_Flags() }\n}\n\nfunction picoOsRow_0_2_2(): CapabilityVersionRow {\n return { version: '0.2.2', flags: matrixPico_0_2_2_Flags() }\n}\n\n// Pico OS 6.0 Beta 2.1\nfunction picoOsRow_0_3_1(): CapabilityVersionRow {\n return { version: '0.3.1', flags: matrixPico_0_3_1_Flags() }\n}\n\n/**\n * Build the capability row for picoOS **PicoWebApp/0.4.90** OTA0.\n */\nfunction picoOsRow_0_4_90(): CapabilityVersionRow {\n return { version: '0.4.90', flags: matrixPico_0_4_90_Flags() }\n}\n\nexport const CAPABILITY_TABLE: {\n visionos: CapabilityVersionRow[]\n picoos: CapabilityVersionRow[]\n} = {\n visionos: [\n visionOsRow_1_5_0(),\n visionOsRow_1_6_0(),\n visionOsRow_1_7_0(),\n visionOsRow_1_8_0(),\n ],\n picoos: [\n picoOsRow_0_1_1(),\n picoOsRow_0_1_2(),\n picoOsRow_0_2_2(),\n picoOsRow_0_3_1(),\n picoOsRow_0_4_90(),\n ],\n}\n","/**\n * Minimal semver compare for capability table rows (`major.minor.patch`).\n * Returns negative if a < b, zero if equal, positive if a > b.\n */\nexport function compareSemver(a: string, b: string): number {\n const pa = parseSemverParts(a)\n const pb = parseSemverParts(b)\n if (!pa || !pb) {\n return String(a).localeCompare(String(b))\n }\n const len = Math.max(pa.length, pb.length)\n for (let i = 0; i < len; i++) {\n const da = pa[i] ?? 0\n const db = pb[i] ?? 0\n if (da !== db) return da - db\n }\n return 0\n}\n\nfunction parseSemverParts(v: string): number[] | null {\n const m = /^(\\d+)(?:\\.(\\d+)(?:\\.(\\d+))?)?/.exec(v.trim())\n if (!m) return null\n const major = Number(m[1])\n const minor = m[2] !== undefined ? Number(m[2]) : 0\n const patch = m[3] !== undefined ? Number(m[3]) : 0\n if ([major, minor, patch].some(n => Number.isNaN(n))) return null\n return [major, minor, patch]\n}\n\nexport function parseSemverOrNull(v: string): string | null {\n const m = /^(\\d+(?:\\.\\d+){0,2})/.exec(v.trim())\n return m ? m[1] : null\n}\n","import type { WebSpatialRuntimeSnapshot } from './types'\n\n/**\n * Parse shell token from UA:\n * - packaged/hybrid runtimes use `WSAppShell/<version>`\n * - browser-mode runtime on Pico OS uses `PicoWebApp/<version>`\n *\n * Keep `WSAppShell` precedence when both appear in one UA.\n */\nexport function parseShellToken(ua: string): {\n version: string | null\n source: 'wsapp' | 'picoapp' | null\n} {\n const ws = /\\bWSAppShell\\/([\\w.-]+)/i.exec(ua)\n if (ws?.[1]) return { version: ws[1], source: 'wsapp' }\n const pico = /\\bPicoWebApp\\/([\\w.-]+)/i.exec(ua)\n if (pico?.[1]) return { version: pico[1], source: 'picoapp' }\n return { version: null, source: null }\n}\n\n/** Pico runtime: require explicit Pico tokens (do not treat generic `like Quest` VR UAs as picoos). */\nfunction inferPicoOs(ua: string): boolean {\n return /\\bPicoWebApp\\//i.test(ua) || /\\bPicoBrowser\\b/i.test(ua)\n}\n\n/** visionOS-class WebView UAs include a Mac OS X platform token; `WSAppShell` alone is not enough. */\nfunction inferVisionOsFromUa(ua: string): boolean {\n return /Mac OS X/i.test(ua)\n}\n\n/**\n * Resolve internal runtime snapshot from `navigator.userAgent`.\n * SSR / no navigator → `{ type: null, shellVersion: null }` (no throw).\n */\nexport function computeRuntimeFromUserAgent(\n userAgent: string | undefined,\n): WebSpatialRuntimeSnapshot {\n if (userAgent === undefined || userAgent === '') {\n return { type: null, shellVersion: null }\n }\n // Must run before the shell-token gate: Puppeteer UAs may omit WSAppShell/PicoWebApp.\n if (userAgent.includes('Puppeteer')) {\n const { version } = parseShellToken(userAgent)\n return { type: 'puppeteer', shellVersion: version }\n }\n\n const { version, source } = parseShellToken(userAgent)\n if (!version) {\n return { type: null, shellVersion: null }\n }\n\n if (source === 'picoapp' || inferPicoOs(userAgent)) {\n return { type: 'picoos', shellVersion: version }\n }\n\n if (source === 'wsapp') {\n if (inferVisionOsFromUa(userAgent)) {\n return { type: 'visionos', shellVersion: version }\n }\n return { type: null, shellVersion: version }\n }\n\n return { type: null, shellVersion: version }\n}\n","import { CAPABILITY_TABLE, type CapabilityVersionRow } from './capability-data'\nimport { compareSemver, parseSemverOrNull } from './semver'\nimport type { WebSpatialRuntimeSnapshot } from './types'\nimport { computeRuntimeFromUserAgent } from './userAgent'\nimport {\n type CapabilityKey,\n isKnownSubToken,\n isKnownTopLevel,\n normalizeCapabilityName,\n} from './keys'\n\n/**\n * Unsubstituted shell version placeholder from visionOS manifest / Xcode template\n * (`manifest.swift`). When still present in `WSAppShell/<version>`, treat as debug\n * build: {@link supports} returns true for every valid capability query.\n */\nexport const VISIONOS_DEBUG_SHELL_VERSION_PLACEHOLDER = 'WS_SHELL_VERSION'\n\nlet runtimeCache: WebSpatialRuntimeSnapshot | undefined\n\n/** Test helper: clear cached UA/runtime snapshot between Vitest cases. */\nexport function resetRuntimeCacheForTests(): void {\n runtimeCache = undefined\n}\n\n/**\n * Internal runtime snapshot (not part of the public `@webspatial/react-sdk` surface).\n */\nexport function getRuntime(): WebSpatialRuntimeSnapshot {\n if (runtimeCache !== undefined) return runtimeCache\n if (typeof navigator === 'undefined') {\n runtimeCache = { type: null, shellVersion: null }\n return runtimeCache\n }\n runtimeCache = computeRuntimeFromUserAgent(navigator.userAgent)\n return runtimeCache\n}\n\nfunction selectRow(\n type: 'visionos' | 'picoos',\n shellVersion: string,\n): CapabilityVersionRow | null {\n const norm = parseSemverOrNull(shellVersion)\n if (!norm) return null\n const rows = CAPABILITY_TABLE[type]\n if (!rows.length) return null\n const sorted = [...rows].sort((a, b) => compareSemver(a.version, b.version))\n const minV = sorted[0].version\n if (compareSemver(norm, minV) < 0) return null\n\n let chosen: CapabilityVersionRow | null = null\n for (const row of sorted) {\n if (compareSemver(row.version, norm) <= 0) {\n chosen = row\n } else {\n break\n }\n }\n return chosen\n}\n\n/**\n * Public capability probe (`WebSpatialRuntime.supports` re-exports this from React SDK).\n */\nexport function supports(\n name: CapabilityKey,\n tokens?: readonly string[],\n): boolean\nexport function supports(name: string, tokens?: readonly string[]): boolean\nexport function supports(name: string, tokens?: readonly string[]): boolean {\n if (typeof name !== 'string') return false\n const canonical = normalizeCapabilityName(name)\n if (!isKnownTopLevel(canonical)) return false\n\n const tokList =\n tokens === undefined ? [] : Array.isArray(tokens) ? [...tokens] : []\n if (tokList.some(t => typeof t !== 'string')) return false\n\n for (const t of tokList) {\n if (!isKnownSubToken(canonical, t)) return false\n }\n\n const rt = getRuntime()\n if (rt.type === 'puppeteer') {\n return true\n }\n if (rt.type === null) return false\n if (rt.shellVersion === null) return false\n\n if (\n rt.type === 'visionos' &&\n rt.shellVersion === VISIONOS_DEBUG_SHELL_VERSION_PLACEHOLDER\n ) {\n return true\n }\n\n const parsedShell = parseSemverOrNull(rt.shellVersion)\n if (!parsedShell) return false\n\n if (rt.type !== 'visionos' && rt.type !== 'picoos') return false\n\n const row = selectRow(rt.type, parsedShell)\n if (!row) return false\n\n if (tokList.length === 0) {\n return row.flags[canonical] === true\n }\n if (row.flags[canonical] !== true) {\n return false\n }\n return tokList.every(t => row.flags[`${canonical}:${t}`] === true)\n}\n","export type WebSpatialBootErrorOptions = {\n cause: unknown\n attempt: number\n}\n\nexport class WebSpatialBootError extends Error {\n readonly cause: unknown\n readonly attempt: number\n\n constructor({ cause, attempt }: WebSpatialBootErrorOptions) {\n super(`Failed to boot WebSpatial runtime on attempt ${attempt}`)\n this.name = 'WebSpatialBootError'\n this.cause = cause\n this.attempt = attempt\n }\n}\n","import {\n computeRuntimeFromUserAgent,\n type WebSpatialRuntimeType,\n} from '@webspatial/core-sdk/runtime'\n\nexport type SpatialRuntimeType = Exclude<WebSpatialRuntimeType, null>\n\n/**\n * Browser-only spatial runtime detection used by the lazy-load boot path.\n * SSR and non-browser environments intentionally resolve to null so merely\n * importing the runtime foundation never schedules the spatial implementation.\n */\nexport function detectSpatialRuntime(): SpatialRuntimeType | null {\n if (typeof window === 'undefined' || typeof navigator === 'undefined') {\n return null\n }\n\n const snapshot = computeRuntimeFromUserAgent(navigator.userAgent)\n return snapshot.type\n}\n","import { detectSpatialRuntime } from './detect'\nimport { WebSpatialBootError } from './errors'\n\nexport type SpatialImplementation = typeof import('../spatial')\nexport type SpatialImplementationLoader = () => Promise<SpatialImplementation>\nexport type SpatialReadyListener = () => void\nexport type SpatialLoadErrorListener = (error: WebSpatialBootError) => void\n\nlet spatialImpl: SpatialImplementation | null = null\nlet loadPromise: Promise<SpatialImplementation | null> | null = null\nlet loadAttempt = 0\nlet spatialImplLoader: SpatialImplementationLoader = () => import('../spatial')\n\nconst readyListeners = new Set<SpatialReadyListener>()\nconst errorListeners = new Set<SpatialLoadErrorListener>()\n\n// Listener dispatch isolates user-callback failures so they cannot corrupt the\n// boot promise's resolve/reject contract: a throwing ready listener MUST NOT\n// turn a successful load into a rejection, a throwing error listener MUST NOT\n// replace the original `WebSpatialBootError` as the rejection reason, and one\n// throwing listener MUST NOT prevent the remaining listeners from running.\nfunction reportListenerError(error: unknown): void {\n if (typeof process !== 'undefined' && process.env.NODE_ENV === 'production') {\n return\n }\n // eslint-disable-next-line no-console\n console.error('[WebSpatial] spatial bridge listener threw:', error)\n}\n\nfunction notifyReadyListeners(): void {\n for (const listener of [...readyListeners]) {\n try {\n listener()\n } catch (error) {\n reportListenerError(error)\n }\n }\n}\n\nfunction notifyErrorListeners(error: WebSpatialBootError): void {\n for (const listener of [...errorListeners]) {\n try {\n listener(error)\n } catch (listenerError) {\n reportListenerError(listenerError)\n }\n }\n}\n\nfunction toBootError(error: unknown, attempt: number): WebSpatialBootError {\n if (error instanceof WebSpatialBootError) {\n return error\n }\n return new WebSpatialBootError({ cause: error, attempt })\n}\n\nexport function getSpatialImpl(): SpatialImplementation | null {\n return spatialImpl\n}\n\nexport function requireSpatialImpl(): SpatialImplementation {\n if (spatialImpl === null) {\n throw new Error('WebSpatial implementation is not ready')\n }\n return spatialImpl\n}\n\nexport function isSpatialReady(): boolean {\n return spatialImpl !== null\n}\n\nexport function subscribeSpatialReady(\n listener: SpatialReadyListener,\n): () => void {\n readyListeners.add(listener)\n return () => {\n readyListeners.delete(listener)\n }\n}\n\nexport function onSpatialLoadError(\n listener: SpatialLoadErrorListener,\n): () => void {\n errorListeners.add(listener)\n return () => {\n errorListeners.delete(listener)\n }\n}\n\nexport function loadSpatialImpl(): Promise<SpatialImplementation | null> {\n if (spatialImpl !== null) {\n return Promise.resolve(spatialImpl)\n }\n if (loadPromise !== null) {\n return loadPromise\n }\n\n // SSR / non-WebSpatial gating per spatial-lazy-load spec \"Bridge singleton /\n // SSR safety\" Scenario: bridge methods MUST resolve to `null` without\n // scheduling a network request when no spatial runtime is detectable.\n if (detectSpatialRuntime() === null) {\n return Promise.resolve(null)\n }\n\n const attempt = loadAttempt + 1\n loadAttempt = attempt\n\n loadPromise = spatialImplLoader()\n .then(impl => {\n spatialImpl = impl\n loadPromise = null\n notifyReadyListeners()\n return impl\n })\n .catch(error => {\n loadPromise = null\n const bootError = toBootError(error, attempt)\n notifyErrorListeners(bootError)\n throw bootError\n })\n\n return loadPromise\n}\n\n// Internal-only: the eager entry (`src/eager.ts`) calls this at module-\n// evaluation time to preload the bridge with the statically-linked spatial\n// implementation. After this call the bridge is permanently in the \"ready\"\n// state for the page lifetime — `bootSpatial()` becomes a no-op (the\n// `spatialImpl !== null` short-circuit at the top of `loadSpatialImpl()`\n// handles this), `isSpatialReady()` returns `true`, and `useSpatialReady()`\n// returns `true`. This is precisely the runtime contract the eager entry\n// promises to consumers per the \"Eager-mode entry for spatial-only consumers\"\n// Requirement.\n//\n// First call wins: subsequent calls with a different implementation are\n// silently ignored so that mixing import roots (an unsupported but possible\n// configuration; see \"Mixed-import shape is not supported\" Scenario) does\n// NOT corrupt the bridge. The first preload sets the contract; later\n// imports either match it (no-op) or are ignored (they would only happen\n// if a consumer simultaneously imports the lazy and eager entries, which\n// the migration guide explicitly forbids).\n//\n// This function is NOT re-exported from the default-entry public surface\n// — it is an internal coupling between the bridge and the eager entry.\n// The double-underscore prefix matches the test-only helpers below to\n// signal \"internal\" without prefixing every export with `internal_`.\nexport function __internalSetSpatialImpl(\n impl: SpatialImplementation,\n _registrationToken?: unknown,\n): void {\n if (spatialImpl !== null) return\n spatialImpl = impl\n loadAttempt = 1\n notifyReadyListeners()\n}\n\nexport function __setSpatialImplLoaderForTests(\n loader: SpatialImplementationLoader,\n): void {\n spatialImplLoader = loader\n}\n\nexport function __getSpatialLoadAttemptForTests(): number {\n return loadAttempt\n}\n\nexport function __getSpatialReadySubscriberCountForTests(): number {\n return readyListeners.size\n}\n\nexport function __resetSpatialBridgeForTests(): void {\n spatialImpl = null\n loadPromise = null\n loadAttempt = 0\n readyListeners.clear()\n errorListeners.clear()\n spatialImplLoader = () => import('../spatial')\n}\n"],"mappings":"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","names":["version"]}
@@ -0,0 +1,2 @@
1
+ import{registerReactSdkEntry}from"./chunk-6JSRUX7P.js";function register(){return registerReactSdkEntry("eager"),"eager"}var eagerEntryRegistered=register();export{eagerEntryRegistered};
2
+ //# sourceMappingURL=chunk-IOLNY4GP.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/runtime/registerEagerEntry.ts"],"sourcesContent":["// =============================================================================\n// Eager-entry registration guard.\n//\n// Two contracts must hold simultaneously:\n//\n// 1. ORDERING — the mixed-entry registration MUST run before `src/eager.ts`\n// evaluates `import * as SpatialImpl from './spatial'` (whose bootstrap\n// installs the `@webspatial/core-sdk` polyfill). ES modules evaluate static\n// imports in source order before the module body, so `eager.ts` imports\n// THIS module first; emitting it as its own tsup entry (see\n// `tsup.config.ts`) keeps it a standalone chunk that is evaluated during\n// `eager.js`'s import phase rather than inlined into the body after the\n// spatial import.\n//\n// 2. SURVIVES DOWNSTREAM TREE-SHAKING — a bare top-level\n// `registerReactSdkEntry('eager')` statement was dropped by consumer\n// bundlers: the emitted hashed chunk is not in the package `sideEffects`\n// allowlist, so esbuild/Rollup/Rspack treat it as side-effect-free and\n// elide the bare side-effect import, defeating mixed-entry detection. We\n// therefore carry the registration as the INITIALIZER of an exported\n// binding that `eager.ts` actually consumes. Because `dist/eager.js` is in\n// the `sideEffects` allowlist, the statement in `eager.ts` that references\n// `eagerEntryRegistered` is retained, which keeps this import live, which\n// keeps the registration call.\n// =============================================================================\n\nimport { registerReactSdkEntry } from './entryRegistry'\n\nfunction register(): 'eager' {\n registerReactSdkEntry('eager')\n return 'eager'\n}\n\n/**\n * Registers the eager entry root as a side effect of computing this value.\n * `src/eager.ts` MUST reference this binding (see its bridge-setup expression)\n * so downstream bundlers cannot tree-shake the registration away.\n */\nexport const eagerEntryRegistered = register()\n"],"mappings":"uDA4BA,SAAS,UAAoB,CAC3B,6BAAsB,OAAO,EACtB,OACT,CAOO,IAAM,qBAAuB,SAAS","names":[]}
@@ -0,0 +1,2 @@
1
+ import{WebSpatialRuntimeError,getSpatialImpl,supports}from"./chunk-GG2QK5MA.js";var WebSpatialRuntime={supports};function resolveSpatialObjectId(target){if(typeof window<"u"&&target===window)return getSpatialImpl()?.getSession?.()?.getSpatialScene()?.id??"";let maybeEntity=target;if(maybeEntity&&typeof maybeEntity=="object"&&"entity"in maybeEntity)return maybeEntity.entity?.id??null;let dom=target;if(dom&&typeof dom=="object"){let spatializedElement=dom.__spatializedElement??dom.__innerSpatializedElement?.();if(spatializedElement&&spatializedElement.id)return spatializedElement.id}return null}async function convertCoordinate(position,{from,to}){if(!supports("convertCoordinate"))throw new WebSpatialRuntimeError("convertCoordinate");let fromId=resolveSpatialObjectId(from),toId=resolveSpatialObjectId(to);if(fromId===null||toId===null)throw new WebSpatialRuntimeError("convertCoordinate","convertCoordinate: from or to is not a valid coordinate convertible");let spatialScene=getSpatialImpl()?.getSession?.()?.getSpatialScene();if(!spatialScene)throw new WebSpatialRuntimeError("convertCoordinate","convertCoordinate is not available until bootSpatial() has resolved");return await spatialScene.convertCoordinate(position,fromId,toId)??position}function initScene(name,callback,options){return getSpatialImpl()?.getSession?.()?.initScene(name,callback,options)}function createSpatialBoot(useBootHook){function SpatialBootComponent({children,onReady,onError}){let{status}=useBootHook({onReady,onError});return status!=="ready"?null:children}return SpatialBootComponent.displayName="SpatialBoot",SpatialBootComponent}export{createSpatialBoot,WebSpatialRuntime,convertCoordinate,initScene};
2
+ //# sourceMappingURL=chunk-NWVQY6CN.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/webSpatialRuntime.ts","../src/utils/convertCoordinate.ts","../src/initScene.ts","../src/runtime/createSpatialBoot.tsx"],"sourcesContent":["import { supports } from '@webspatial/core-sdk/runtime'\n\n/**\n * Runtime capability checks (`supports('Model')`, `supports('WindowScene', ['defaultSize'])`, ...).\n * Spec: `openspec/specs/runtime-capabilities/spec.md`.\n */\nexport const WebSpatialRuntime = {\n supports,\n} as const\n","/**\n * const e2e = await convertCoordinate(position, { from: elementOrEntity, to: elementOrEntity })\nconst e2w = await convertCoordinate(position, { from: elementOrEntity, to: window })\nconst w2e = await convertCoordinate(position, { from: window, to: elementOrEntity })\n * \n */\nimport type { Vec3 } from '@webspatial/core-sdk'\nimport { supports, WebSpatialRuntimeError } from '@webspatial/core-sdk/runtime'\nimport type { SpatializedElementRef } from '../spatialized-container/types'\nimport type { EntityRef } from '../reality'\nimport type { ModelRef } from '../Model'\nimport { getSpatialImpl } from '../runtime/bridge'\n\n// Per the lazy-load proposal `tasks.md §12.9` (\"Pre-v1 budget calibration\"),\n// `convertCoordinate` no longer statically imports `getSession` from\n// `./getSession`. That import would pull `Spatial` + `SpatialSession`\n// (and through `SpatialSession`, the entire spatial creator class graph\n// + `scene-polyfill`) into the default-entry bundle. The function's\n// fail-fast contract (per runtime-capabilities \"convertCoordinate fail-fast\"\n// Scenarios) gates on `supports('convertCoordinate')` via the inlined\n// `@webspatial/core-sdk/runtime` subset before touching the bridge.\n\ntype CoordinateConvertible =\n | Window\n | SpatializedElementRef<any>\n | EntityRef\n | ModelRef\n\nfunction resolveSpatialObjectId(target: CoordinateConvertible): string | null {\n // window -> current spatial scene id which is empty string\n if (typeof window !== 'undefined' && target === window) {\n const scene = getSpatialImpl()?.getSession?.()?.getSpatialScene()\n return scene?.id ?? ''\n }\n\n // EntityRef -> underlying SpatialEntity.id\n const maybeEntity = target as EntityRef\n if (\n maybeEntity &&\n typeof maybeEntity === 'object' &&\n 'entity' in maybeEntity\n ) {\n return maybeEntity.entity?.id ?? null\n }\n\n // SpatializedElementRef / ModelRef -> underlying SpatializedElement.id\n const dom: any = target as any\n if (dom && typeof dom === 'object') {\n const spatializedElement =\n dom.__spatializedElement ?? dom.__innerSpatializedElement?.()\n if (spatializedElement && spatializedElement.id) {\n return spatializedElement.id as string\n }\n }\n\n return null\n}\n\nexport async function convertCoordinate(\n position: Vec3,\n { from, to }: { from: CoordinateConvertible; to: CoordinateConvertible },\n): Promise<Vec3> {\n if (!supports('convertCoordinate')) {\n throw new WebSpatialRuntimeError('convertCoordinate')\n }\n\n const fromId = resolveSpatialObjectId(from)\n const toId = resolveSpatialObjectId(to)\n if (fromId === null || toId === null) {\n throw new WebSpatialRuntimeError(\n 'convertCoordinate',\n 'convertCoordinate: from or to is not a valid coordinate convertible',\n )\n }\n\n const spatialScene = getSpatialImpl()?.getSession?.()?.getSpatialScene()\n if (!spatialScene) {\n throw new WebSpatialRuntimeError(\n 'convertCoordinate',\n 'convertCoordinate is not available until bootSpatial() has resolved',\n )\n }\n\n const ret = await spatialScene.convertCoordinate(position, fromId, toId)\n return ret ?? position\n}\n","import type {\n SpatialSceneCreationOptions,\n SpatialSceneType,\n} from '@webspatial/core-sdk'\nimport { getSpatialImpl } from './runtime/bridge'\n\n// Per the lazy-load proposal `tasks.md §12.9` (\"Pre-v1 budget calibration\"),\n// `initScene` no longer statically imports `getSession` from `./utils`.\n// That import would pull `Spatial` + `SpatialSession` (and through\n// `SpatialSession`, the entire spatial creator class graph + the 636 LoC\n// `scene-polyfill`) into the default-entry bundle. Routing through\n// `getSpatialImpl()?.getSession?.()` keeps `getSession` reachable only\n// from the spatial chunk's static module graph, while preserving the\n// \"graceful no-op when no session is available\" behavior consumers\n// already relied on (the optional chaining returned `undefined` before\n// boot anyway).\nexport function initScene(\n name: string,\n callback: (pre: SpatialSceneCreationOptions) => SpatialSceneCreationOptions,\n options?: { type: SpatialSceneType },\n) {\n return getSpatialImpl()?.getSession?.()?.initScene(name, callback, options)\n}\n","'use client'\n\nimport type { ReactNode } from 'react'\nimport type {\n UseBootSpatialOptions,\n UseBootSpatialResult,\n} from './useBootSpatial'\n\nexport type SpatialBootProps = {\n children: ReactNode\n onReady?: UseBootSpatialOptions['onReady']\n onError?: UseBootSpatialOptions['onError']\n}\n\n/**\n * Runs `bootSpatial()` after mount. Does not mount `children` until boot\n * succeeds; on `WebSpatialBootError`, invokes `onError` and keeps `children`\n * unmounted.\n */\nexport function createSpatialBoot(\n useBootHook: (options: UseBootSpatialOptions) => UseBootSpatialResult,\n): (props: SpatialBootProps) => ReactNode {\n function SpatialBootComponent({\n children,\n onReady,\n onError,\n }: SpatialBootProps): ReactNode {\n const { status } = useBootHook({ onReady, onError })\n\n if (status !== 'ready') {\n return null\n }\n\n return children\n }\n\n SpatialBootComponent.displayName = 'SpatialBoot'\n return SpatialBootComponent\n}\n"],"mappings":"gFAMO,IAAM,kBAAoB,CAC/B,QACF,ECoBA,SAAS,uBAAuB,OAA8C,CAE5E,GAAI,OAAO,OAAW,KAAe,SAAW,OAE9C,OADc,eAAe,GAAG,aAAa,GAAG,gBAAgB,GAClD,IAAM,GAItB,IAAM,YAAc,OACpB,GACE,aACA,OAAO,aAAgB,UACvB,WAAY,YAEZ,OAAO,YAAY,QAAQ,IAAM,KAInC,IAAM,IAAW,OACjB,GAAI,KAAO,OAAO,KAAQ,SAAU,CAClC,IAAM,mBACJ,IAAI,sBAAwB,IAAI,4BAA4B,EAC9D,GAAI,oBAAsB,mBAAmB,GAC3C,OAAO,mBAAmB,EAE9B,CAEA,OAAO,IACT,CAEA,eAAsB,kBACpB,SACA,CAAE,KAAM,EAAG,EACI,CACf,GAAI,CAAC,SAAS,mBAAmB,EAC/B,MAAM,IAAI,uBAAuB,mBAAmB,EAGtD,IAAM,OAAS,uBAAuB,IAAI,EACpC,KAAO,uBAAuB,EAAE,EACtC,GAAI,SAAW,MAAQ,OAAS,KAC9B,MAAM,IAAI,uBACR,oBACA,qEACF,EAGF,IAAM,aAAe,eAAe,GAAG,aAAa,GAAG,gBAAgB,EACvE,GAAI,CAAC,aACH,MAAM,IAAI,uBACR,oBACA,qEACF,EAIF,OADY,MAAM,aAAa,kBAAkB,SAAU,OAAQ,IAAI,GACzD,QAChB,CCrEO,SAAS,UACd,KACA,SACA,QACA,CACA,OAAO,eAAe,GAAG,aAAa,GAAG,UAAU,KAAM,SAAU,OAAO,CAC5E,CCHO,SAAS,kBACd,YACwC,CACxC,SAAS,qBAAqB,CAC5B,SACA,QACA,OACF,EAAgC,CAC9B,GAAM,CAAE,MAAO,EAAI,YAAY,CAAE,QAAS,OAAQ,CAAC,EAEnD,OAAI,SAAW,QACN,KAGF,QACT,CAEA,4BAAqB,YAAc,cAC5B,oBACT","names":[]}
@@ -0,0 +1,2 @@
1
+ var __defProp=Object.defineProperty;var __export=(target,all)=>{for(var name in all)__defProp(target,name,{get:all[name],enumerable:!0})};export{__export};
2
+ //# sourceMappingURL=chunk-NXEOIP4Z.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":[],"sourcesContent":[],"mappings":"","names":[]}
@@ -0,0 +1,2 @@
1
+ import{getWebSpatialPrimitiveName}from"./chunk-QHUROD77.js";import{jsxDEV as _jsxDEV}from"react/jsx-dev-runtime";import*as _reactJSXRuntime from"react/jsx-runtime";import{createElement as reactCreateElement}from"react";import{withSpatialMonitor,withSpatialized2DElementContainer}from"@webspatial/react-sdk/internal/facades-client";var reactJSXRuntime=_reactJSXRuntime.default||_reactJSXRuntime,canWrapWithFacade=typeof withSpatialized2DElementContainer=="function"&&typeof withSpatialMonitor=="function",attributeFlag="enable-xr",styleFlag="enableXr",classFlag="__enableXr__",xrMonitorFlag="enable-xr-monitor";function replaceToSpatialPrimitiveType(type,props){if(getWebSpatialPrimitiveName(type)!==void 0||props===null||typeof props!="object")return type;let propsObject=props,wrapped=type;attributeFlag in propsObject&&(delete propsObject[attributeFlag],canWrapWithFacade&&wrapped===type&&(wrapped=withSpatialized2DElementContainer(type))),xrMonitorFlag in propsObject&&(delete propsObject[xrMonitorFlag],canWrapWithFacade&&wrapped===type&&(wrapped=withSpatialMonitor(type)));let style=propsObject.style;if(style!==null&&typeof style=="object"&&styleFlag in style){let{[styleFlag]:_enableXr,...restStyle}=style;propsObject.style=restStyle,canWrapWithFacade&&wrapped===type&&(wrapped=withSpatialized2DElementContainer(type))}let className=propsObject.className;if(typeof className=="string"&&className.indexOf(classFlag)!==-1){let tokens=className.split(" "),filtered=tokens.filter(token=>token!==classFlag);filtered.length!==tokens.length&&(propsObject.className=filtered.join(" "),canWrapWithFacade&&wrapped===type&&(wrapped=withSpatialized2DElementContainer(type)))}return wrapped}function jsxs(type,props,key){return type=replaceToSpatialPrimitiveType(type,props),reactJSXRuntime.jsxs(type,props,key)}function jsx(type,props,key){return type=replaceToSpatialPrimitiveType(type,props),reactJSXRuntime.jsx(type,props,key)}function jsxDEV(type,props,key,isStatic,source,self){return type=replaceToSpatialPrimitiveType(type,props),_jsxDEV(type,props,key,isStatic,source,self)}function createElement(...args){let[type,props,...rest]=args,newType=replaceToSpatialPrimitiveType(type,props);return reactCreateElement(newType,props,...rest)}export{jsxs,jsx,jsxDEV,createElement};
2
+ //# sourceMappingURL=chunk-PDUEHFTO.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/jsx/jsx-shared.ts"],"sourcesContent":["import { jsxDEV as _jsxDEV, JSXSource } from 'react/jsx-dev-runtime'\nimport * as _reactJSXRuntime from 'react/jsx-runtime'\nimport { createElement as reactCreateElement } from 'react'\n\nconst reactJSXRuntime = (_reactJSXRuntime as any).default || _reactJSXRuntime\n// The marker-wrapping HOC factories MUST resolve to the **facade** versions\n// defined in `../facades` (not to real spatial implementations). Per\n// spatial-lazy-load spec `tasks.md` §6.2 the JSX runtime delegates spatial\n// vs. fallback rendering to the facade HOCs; the JSX runtime itself NEVER\n// imports from `../spatial/`, NEVER calls `bootSpatial()`, and never\n// schedules a dynamic import. `Model` / `Reality` are handled separately by\n// the primitive marker check below.\n//\n// Why an external package self-reference instead of a relative import:\n// `dist/jsx/jsx-runtime.js` MUST be server-callable (Server Components in\n// the App Router compile their JSX to `jsx(...)` calls reaching this file\n// via `tsconfig \"jsxImportSource\"`), so it cannot itself carry\n// `'use client'`. The facade HOCs, however, transitively import React\n// hooks (`useSyncExternalStore`, `useLayoutEffect`, ...) which the RSC\n// compiler rejects from a server-callable module. We therefore route\n// `jsx-shared`'s facade lookup through an internal `'use client'`\n// boundary file (`src/internal/facades-client.ts`, published as the\n// `@webspatial/react-sdk/internal/facades-client` subpath and marked\n// external by `tsup.config.ts`). Next's RSC compiler walks\n// `jsx-runtime.js` → shared chunk → external subpath → facades-client.js\n// and STOPS at the directive, treating the imported facades as Client\n// References. The runtime check below (`canWrapWithFacade`) detects this\n// case and degrades to \"strip markers, no HOC wrap\" — see\n// `src/internal/facades-client.ts` for the full rationale.\nimport {\n withSpatialMonitor,\n withSpatialized2DElementContainer,\n} from '@webspatial/react-sdk/internal/facades-client'\nimport { getWebSpatialPrimitiveName } from './primitive-marker'\n\n// In an RSC server bundle, the HOC facade imports above resolve to\n// Client References (opaque objects) rather than callable functions. We\n// can still safely STRIP `enable-xr` / `enable-xr-monitor` markers from\n// props (so the resulting server-rendered DOM matches the client-side\n// facade fallback DOM), but we MUST NOT attempt to invoke the HOC\n// factories — calling a Client Reference throws. In the client bundle\n// (and during SSR pre-render of Client Components), the same imports\n// resolve to the real functions and the full strip + wrap path runs.\n//\n// The check is module-scoped because Client Reference identity is fixed\n// at module evaluation time and never flips back to a real function\n// during the lifetime of a process.\nconst canWrapWithFacade =\n typeof withSpatialized2DElementContainer === 'function' &&\n typeof withSpatialMonitor === 'function'\n\nconst attributeFlag = 'enable-xr'\nconst styleFlag = 'enableXr'\nconst classFlag = '__enableXr__'\nconst xrMonitorFlag = 'enable-xr-monitor'\n\n/**\n * Strip WebSpatial-only markers from `props` and, when at least one marker is\n * present, wrap the element `type` with the appropriate facade HOC. Performs\n * strip + wrap in a single pass and is invoked by every JSX call site\n * (`jsx`, `jsxs`, `jsxDEV`, and the deprecated `createElement` export).\n *\n * Per spatial-lazy-load spec \"JSX runtime strips spatial markers and wraps\n * with facade HOCs\":\n *\n * - `enable-xr` → `withSpatialized2DElementContainer(type)`\n * - `enable-xr-monitor` → `withSpatialMonitor(type)`\n * - `props.style.enableXr` → `withSpatialized2DElementContainer(type)` and\n * `props.style` is reassigned to a NEW object (spread-clone) with the\n * `enableXr` key omitted. The original `props.style` reference MUST NOT be\n * mutated (it MAY be user-memoized or `Object.freeze`d).\n * - `props.className` token → `withSpatialized2DElementContainer(type)` and\n * the `__enableXr__` token is removed from the className string.\n *\n * Mutation policy: the top-level `props` object is created fresh per JSX call\n * by React's transform and MAY be mutated in place — we delete the attribute\n * keys (`enable-xr`, `enable-xr-monitor`) directly and reassign `className`\n * and `style` on it. Only the nested `props.style` value is spread-cloned to\n * keep the user-supplied reference pristine.\n *\n * Marker source: only `props.className` is recognized. The HTML-style\n * `props.class` is **not** treated as a marker source in v1 (per the spec\n * \"HTML class attribute is not recognized as a marker source\" Scenario);\n * props pass through to React unchanged in that case.\n *\n * `Model` and `Reality` (identified by the stable primitive marker, covering\n * both the facade and the eager real implementations) short-circuit both\n * strip and wrap: both handle their own runtime branching and MUST NOT be\n * wrapped as generic 2D spatialized containers.\n *\n * Combined markers: when more than one marker is present, every marker MUST\n * be stripped (the `tasks.md §6.6(b)` requirement). The wrap is determined\n * by the highest-priority marker in the order listed above; the cascading\n * fall-through ensures that `withSpatialMonitor` is preferred only when\n * `enable-xr-monitor` is the sole 2D-container marker present.\n *\n * Zero-allocation fast path: when no markers are present, this function must\n * not clone `props.style`, must not split `className`, and must not reassign\n * any prop (per \"No marker present is a no-op\" Scenario).\n */\nexport function replaceToSpatialPrimitiveType(\n type: React.ElementType,\n props: unknown,\n): React.ElementType {\n // `Model` / `Reality` short-circuit both strip and wrap. We brand both the\n // default-entry facades and the eager-entry real implementations with a\n // stable marker (see `primitive-marker.ts`); identifying by marker — not by\n // object-reference equality against the facade — keeps the eager entry's\n // real `<Model enable-xr>` from being wrapped as a 2D spatialized container.\n if (getWebSpatialPrimitiveName(type) !== undefined) {\n return type\n }\n\n if (props === null || typeof props !== 'object') {\n return type\n }\n\n const propsObject = props as Record<string, any>\n let wrapped: React.ElementType = type\n\n if (attributeFlag in propsObject) {\n delete propsObject[attributeFlag]\n if (canWrapWithFacade && wrapped === type) {\n wrapped = withSpatialized2DElementContainer(type)\n }\n }\n\n if (xrMonitorFlag in propsObject) {\n delete propsObject[xrMonitorFlag]\n if (canWrapWithFacade && wrapped === type) {\n wrapped = withSpatialMonitor(type)\n }\n }\n\n // Style marker — spread-clone to avoid mutating a memoized / frozen ref.\n const style = propsObject.style\n if (style !== null && typeof style === 'object' && styleFlag in style) {\n const { [styleFlag]: _enableXr, ...restStyle } = style\n propsObject.style = restStyle\n if (canWrapWithFacade && wrapped === type) {\n wrapped = withSpatialized2DElementContainer(type)\n }\n }\n\n // className token — only check `props.className` (NOT `props.class`).\n // Fast-path: `indexOf` substring check skips the split/filter allocation\n // when the marker token is absent (per the \"No marker present is a no-op\"\n // Scenario).\n const className = propsObject.className\n if (typeof className === 'string' && className.indexOf(classFlag) !== -1) {\n const tokens = className.split(' ')\n const filtered = tokens.filter(token => token !== classFlag)\n if (filtered.length !== tokens.length) {\n propsObject.className = filtered.join(' ')\n if (canWrapWithFacade && wrapped === type) {\n wrapped = withSpatialized2DElementContainer(type)\n }\n }\n }\n\n return wrapped\n}\n\nexport function jsxs(type: React.ElementType, props: unknown, key?: React.Key) {\n type = replaceToSpatialPrimitiveType(type, props)\n return (reactJSXRuntime as any).jsxs(type, props, key)\n}\n\nexport function jsx(type: React.ElementType, props: unknown, key?: React.Key) {\n type = replaceToSpatialPrimitiveType(type, props)\n return (reactJSXRuntime as any).jsx(type, props, key)\n}\n\nexport function jsxDEV(\n type: React.ElementType,\n props: unknown,\n key: React.Key,\n isStatic: boolean,\n source?: JSXSource,\n self?: unknown,\n) {\n type = replaceToSpatialPrimitiveType(type, props)\n return _jsxDEV(type, props, key, isStatic, source, self)\n}\n\n/**\n * @deprecated Use the new JSX transform (tsconfig `\"jsx\": \"react-jsx\"` or\n * babel `runtime: \"automatic\"`) instead. SDK strip + facade-HOC wrap is\n * provided via the `package.json` `\"./jsx-runtime\"` mapping. This export\n * will be removed in v2.\n */\nexport function createElement(...args: Parameters<typeof reactCreateElement>) {\n const [type, props, ...rest] = args\n const newType = replaceToSpatialPrimitiveType(type as any, props)\n return reactCreateElement(newType, props, ...rest)\n}\n"],"mappings":"4DAAA,OAAS,UAAU,YAA0B,wBAC7C,UAAY,qBAAsB,oBAClC,OAAS,iBAAiB,uBAA0B,QA2BpD,OACE,mBACA,sCACK,gDA5BP,IAAM,gBAA4C,0BAAW,iBA2CvD,kBACJ,OAAO,mCAAsC,YAC7C,OAAO,oBAAuB,WAE1B,cAAgB,YAChB,UAAY,WACZ,UAAY,eACZ,cAAgB,oBA8Cf,SAAS,8BACd,KACA,MACmB,CAUnB,GAJI,2BAA2B,IAAI,IAAM,QAIrC,QAAU,MAAQ,OAAO,OAAU,SACrC,OAAO,KAGT,IAAM,YAAc,MAChB,QAA6B,KAE7B,iBAAiB,cACnB,OAAO,YAAY,aAAa,EAC5B,mBAAqB,UAAY,OACnC,QAAU,kCAAkC,IAAI,IAIhD,iBAAiB,cACnB,OAAO,YAAY,aAAa,EAC5B,mBAAqB,UAAY,OACnC,QAAU,mBAAmB,IAAI,IAKrC,IAAM,MAAQ,YAAY,MAC1B,GAAI,QAAU,MAAQ,OAAO,OAAU,UAAY,aAAa,MAAO,CACrE,GAAM,CAAE,CAAC,SAAS,EAAG,UAAW,GAAG,SAAU,EAAI,MACjD,YAAY,MAAQ,UAChB,mBAAqB,UAAY,OACnC,QAAU,kCAAkC,IAAI,EAEpD,CAMA,IAAM,UAAY,YAAY,UAC9B,GAAI,OAAO,WAAc,UAAY,UAAU,QAAQ,SAAS,IAAM,GAAI,CACxE,IAAM,OAAS,UAAU,MAAM,GAAG,EAC5B,SAAW,OAAO,OAAO,OAAS,QAAU,SAAS,EACvD,SAAS,SAAW,OAAO,SAC7B,YAAY,UAAY,SAAS,KAAK,GAAG,EACrC,mBAAqB,UAAY,OACnC,QAAU,kCAAkC,IAAI,GAGtD,CAEA,OAAO,OACT,CAEO,SAAS,KAAK,KAAyB,MAAgB,IAAiB,CAC7E,YAAO,8BAA8B,KAAM,KAAK,EACxC,gBAAwB,KAAK,KAAM,MAAO,GAAG,CACvD,CAEO,SAAS,IAAI,KAAyB,MAAgB,IAAiB,CAC5E,YAAO,8BAA8B,KAAM,KAAK,EACxC,gBAAwB,IAAI,KAAM,MAAO,GAAG,CACtD,CAEO,SAAS,OACd,KACA,MACA,IACA,SACA,OACA,KACA,CACA,YAAO,8BAA8B,KAAM,KAAK,EACzC,QAAQ,KAAM,MAAO,IAAK,SAAU,OAAQ,IAAI,CACzD,CAQO,SAAS,iBAAiB,KAA6C,CAC5E,GAAM,CAAC,KAAM,MAAO,GAAG,IAAI,EAAI,KACzB,QAAU,8BAA8B,KAAa,KAAK,EAChE,OAAO,mBAAmB,QAAS,MAAO,GAAG,IAAI,CACnD","names":[]}
@@ -0,0 +1,2 @@
1
+ var WEBSPATIAL_PRIMITIVE_MARKER="__webspatialPrimitive__";function markWebSpatialPrimitive(component,name){try{Object.defineProperty(component,WEBSPATIAL_PRIMITIVE_MARKER,{value:name,enumerable:!1,configurable:!0,writable:!1})}catch{}return component}function getWebSpatialPrimitiveName(type){if(type===null||typeof type!="object"&&typeof type!="function")return;let value=type[WEBSPATIAL_PRIMITIVE_MARKER];return value==="Model"||value==="Reality"?value:void 0}export{markWebSpatialPrimitive,getWebSpatialPrimitiveName};
2
+ //# sourceMappingURL=chunk-QHUROD77.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/jsx/primitive-marker.ts"],"sourcesContent":["// =============================================================================\n// WebSpatial primitive marker — stable identity for `Model` / `Reality`.\n//\n// The JSX runtime (`jsx-shared.ts`) must short-circuit `Model` and `Reality`\n// so the `enable-xr` marker never wraps them as a generic 2D spatialized\n// container. It previously did this by reference equality against the FACADE\n// `Model` / `Reality` imported from `internal/facades-client`. That breaks for\n// the eager entry (`src/eager.ts`), whose `<Model>` resolves to the REAL\n// implementation from `./spatial` — a different object identity than the\n// default-entry facade — so a reference-equality check failed and\n// `<Model enable-xr>` fell through to the 2D-container wrap path.\n//\n// We instead brand BOTH the facade and the real components with a stable\n// string-valued, non-enumerable property. A string literal (not a `Symbol`)\n// is intentional: the JSX runtime ships as its own build entry\n// (`dist/jsx/jsx-runtime.js`) and may carry a duplicate copy of this module,\n// so a module-scoped `Symbol()` would not compare equal across chunks. A\n// string brand is stable regardless of how many copies of this module exist.\n// =============================================================================\n\nexport const WEBSPATIAL_PRIMITIVE_MARKER = '__webspatialPrimitive__'\n\nexport type WebSpatialPrimitiveName = 'Model' | 'Reality'\n\n/**\n * Brand a component (facade or real implementation) as a WebSpatial primitive\n * so the JSX runtime can identify it without relying on object-reference\n * equality. Returns the same component for ergonomic call sites.\n */\nexport function markWebSpatialPrimitive<T>(\n component: T,\n name: WebSpatialPrimitiveName,\n): T {\n try {\n Object.defineProperty(component as object, WEBSPATIAL_PRIMITIVE_MARKER, {\n value: name,\n enumerable: false,\n configurable: true,\n writable: false,\n })\n } catch {\n // Best-effort: frozen / non-extensible exotic objects simply stay\n // unmarked. The JSX runtime degrades to \"no bypass\" for them, which is\n // the pre-existing (non-eager) behavior.\n }\n return component\n}\n\n/**\n * Return the primitive name a component is branded with, or `undefined` when\n * it is not a WebSpatial primitive.\n */\nexport function getWebSpatialPrimitiveName(\n type: unknown,\n): WebSpatialPrimitiveName | undefined {\n if (\n type === null ||\n (typeof type !== 'object' && typeof type !== 'function')\n ) {\n return undefined\n }\n const value = (type as Record<string, unknown>)[WEBSPATIAL_PRIMITIVE_MARKER]\n return value === 'Model' || value === 'Reality' ? value : undefined\n}\n"],"mappings":"AAoBO,IAAM,4BAA8B,0BASpC,SAAS,wBACd,UACA,KACG,CACH,GAAI,CACF,OAAO,eAAe,UAAqB,4BAA6B,CACtE,MAAO,KACP,WAAY,GACZ,aAAc,GACd,SAAU,EACZ,CAAC,CACH,MAAQ,CAIR,CACA,OAAO,SACT,CAMO,SAAS,2BACd,KACqC,CACrC,GACE,OAAS,MACR,OAAO,MAAS,UAAY,OAAO,MAAS,WAE7C,OAEF,IAAM,MAAS,KAAiC,2BAA2B,EAC3E,OAAO,QAAU,SAAW,QAAU,UAAY,MAAQ,MAC5D","names":[]}
@@ -0,0 +1,2 @@
1
+ import{getSpatialImpl}from"./chunk-GG2QK5MA.js";async function inspectCurrentSpatialScene(){let session=getSpatialImpl()?.getSession?.();if(!session)throw new Error("inspectCurrentSpatialScene: no spatial session. Call `await bootSpatial()` from `@webspatial/react-sdk` before invoking `window.inspectCurrentSpatialScene()`.");return session.getSpatialScene().inspect()}function getSpatialized2DElement(spatialized2DElement){return spatialized2DElement.__innerSpatializedElement?.()}function enableDebugTool(){typeof window>"u"||Object.assign(window,{inspectCurrentSpatialScene,getSpatialized2DElement})}export{enableDebugTool};
2
+ //# sourceMappingURL=chunk-UHEO47WY.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/utils/debugTool.ts"],"sourcesContent":["import type { Spatialized2DElement } from '@webspatial/core-sdk'\nimport { getSpatialImpl } from '../runtime/bridge'\n\n// Per the lazy-load proposal `tasks.md §12.9` (\"Pre-v1 budget calibration\"),\n// this default-entry utility no longer statically imports `getSession`\n// from `./getSession` — that would pull `Spatial` + `SpatialSession`\n// (and through `SpatialSession`, the entire spatial creator class graph\n// + `scene-polyfill`) into the default-entry bundle. Instead we route\n// through `getSpatialImpl()?.getSession?.()`, which only has a session\n// available after `await bootSpatial()` resolves. The debug tool already\n// requires a spatial session to do anything meaningful (`inspectCurrentSpatialScene`\n// can't render without one), so the new \"throws if called before boot\"\n// behavior is strictly an improvement over the previous \"throws via\n// `getSession()!` non-null assertion\".\n\nasync function inspectCurrentSpatialScene() {\n const session = getSpatialImpl()?.getSession?.()\n if (!session) {\n throw new Error(\n 'inspectCurrentSpatialScene: no spatial session. ' +\n 'Call `await bootSpatial()` from `@webspatial/react-sdk` before ' +\n 'invoking `window.inspectCurrentSpatialScene()`.',\n )\n }\n const spatialScene = session.getSpatialScene()\n return spatialScene.inspect()\n}\n\nfunction getSpatialized2DElement(\n spatialized2DElement: HTMLDivElement,\n): Spatialized2DElement {\n return (\n spatialized2DElement as any\n ).__innerSpatializedElement?.() as Spatialized2DElement\n}\n\nexport function enableDebugTool() {\n if (typeof window === 'undefined') return\n\n Object.assign(window, {\n inspectCurrentSpatialScene,\n getSpatialized2DElement,\n })\n}\n"],"mappings":"gDAeA,eAAe,4BAA6B,CAC1C,IAAM,QAAU,eAAe,GAAG,aAAa,EAC/C,GAAI,CAAC,QACH,MAAM,IAAI,MACR,gKAGF,EAGF,OADqB,QAAQ,gBAAgB,EACzB,QAAQ,CAC9B,CAEA,SAAS,wBACP,qBACsB,CACtB,OACE,qBACA,4BAA4B,CAChC,CAEO,SAAS,iBAAkB,CAC5B,OAAO,OAAW,KAEtB,OAAO,OAAO,OAAQ,CACpB,2BACA,uBACF,CAAC,CACH","names":[]}