@webspatial/core-sdk 1.3.0 → 1.4.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.
package/dist/index.js CHANGED
@@ -2,7 +2,7 @@
2
2
  (function(){
3
3
  if(typeof window === 'undefined') return;
4
4
  if(!window.__webspatialsdk__) window.__webspatialsdk__ = {}
5
- window.__webspatialsdk__['core-sdk-version'] = "1.3.0"
5
+ window.__webspatialsdk__['core-sdk-version'] = "1.4.0"
6
6
  })()
7
7
 
8
8
  var __defProp = Object.defineProperty;
@@ -105,7 +105,7 @@ var init_PuppeteerPlatform = __esm({
105
105
  init_CommandResultUtils();
106
106
  console.log("PuppeteerPlatform");
107
107
  PuppeteerPlatform = class {
108
- // 存储iframe实例
108
+ // store iframe instance
109
109
  iframeRegistry = /* @__PURE__ */ new Map();
110
110
  constructor() {
111
111
  }
@@ -135,7 +135,7 @@ var init_PuppeteerPlatform = __esm({
135
135
  });
136
136
  }
137
137
  /**
138
- * 同步创建Spatialized2DElementPuppeteer Runner
138
+ * Synchronously create Spatialized2DElement to Puppeteer Runner
139
139
  */
140
140
  createSpatializedElementSync(spatialId, webspatialUrl) {
141
141
  try {
@@ -207,7 +207,7 @@ var init_PuppeteerPlatform = __esm({
207
207
  }
208
208
  }
209
209
  /**
210
- * 创建基于iframe的窗口
210
+ * Synchronously create iframe-based window
211
211
  */
212
212
  createIframeWindow(url, target, features) {
213
213
  const iframe = document.createElement("iframe");
@@ -243,11 +243,11 @@ var init_PuppeteerPlatform = __esm({
243
243
  return { spatialId, iframe, windowProxy };
244
244
  }
245
245
  /**
246
- * 创建增强的windowProxy对象
246
+ * create enhanced windowProxy object
247
247
  */
248
248
  createEnhancedWindowProxy(iframe, url, spatialId) {
249
249
  return {
250
- // 基本属性
250
+ // basic properties
251
251
  location: {
252
252
  href: url,
253
253
  toString: () => url,
@@ -260,22 +260,22 @@ var init_PuppeteerPlatform = __esm({
260
260
  navigator: {
261
261
  userAgent: `Mozilla/5.0 (WebKit) SpatialId/${spatialId}`
262
262
  },
263
- // 方法
263
+ // methods
264
264
  close: () => {
265
265
  console.log(`Closing iframe with spatialId: ${spatialId}`);
266
266
  iframe.remove();
267
267
  this.iframeRegistry.delete(spatialId);
268
268
  },
269
- // 文档访问
269
+ // document access
270
270
  document: iframe.contentDocument || {},
271
271
  contentWindow: iframe.contentWindow || {},
272
- // 添加消息通信方法
272
+ // add message communication method
273
273
  postMessage: (message, targetOrigin) => {
274
274
  if (iframe.contentWindow) {
275
275
  iframe.contentWindow.postMessage(message, targetOrigin || "*");
276
276
  }
277
277
  },
278
- // 添加事件监听方法
278
+ // add event listener method
279
279
  addEventListener: (type, listener) => {
280
280
  if (iframe.contentWindow) {
281
281
  iframe.contentWindow.addEventListener(type, listener);
@@ -286,7 +286,7 @@ var init_PuppeteerPlatform = __esm({
286
286
  iframe.contentWindow.removeEventListener(type, listener);
287
287
  }
288
288
  },
289
- // 执行JavaScript
289
+ // execute JavaScript
290
290
  executeScript: (code) => {
291
291
  if (iframe.contentWindow) {
292
292
  try {
@@ -302,29 +302,29 @@ var init_PuppeteerPlatform = __esm({
302
302
  }
303
303
  return null;
304
304
  },
305
- // 获取iframe引用
305
+ // get iframe reference
306
306
  getIframe: () => iframe,
307
- // 获取spatialId
307
+ // get spatialId
308
308
  getSpatialId: () => spatialId
309
309
  };
310
310
  }
311
311
  /**
312
- * 初始化iframe内容
312
+ * initialize iframe content
313
313
  */
314
314
  initializeIframeContent(iframe, url, spatialId) {
315
315
  try {
316
316
  iframe.onload = () => {
317
317
  try {
318
318
  const iframeContent = `
319
- // \u6CE8\u5165\u901A\u4FE1\u811A\u672C
319
+ // inject communication script
320
320
  window.webSpatialId = '${spatialId}';
321
321
  window.SpatialId = '${spatialId}';
322
322
 
323
- // \u91CD\u5199window.open\u4EE5\u652F\u6301webspatial\u534F\u8BAE
323
+ // override window.open to support webspatial protocol
324
324
  const originalOpen = window.open;
325
325
  window.open = function(url, target, features) {
326
326
  if (url && url.startsWith('webspatial://')) {
327
- // \u901A\u8FC7windowProxy\u5904\u7406webspatial\u534F\u8BAE
327
+ // handle webspatial protocol through windowProxy
328
328
  const windowProxy = new Proxy({}, {
329
329
  get: function(target, prop) {
330
330
  if (prop === 'toString') {
@@ -338,28 +338,28 @@ var init_PuppeteerPlatform = __esm({
338
338
  return originalOpen.call(window, url, target, features);
339
339
  };
340
340
 
341
- // \u8BBE\u7F6Enavigator.userAgent\u4EE5\u8BC6\u522Bwebspatial\u73AF\u5883
341
+ // set navigator.userAgent to identify webspatial environment
342
342
  Object.defineProperty(navigator, 'userAgent', {
343
343
  value: 'WebSpatial/1.0 ' + navigator.userAgent,
344
344
  configurable: true
345
345
  });
346
346
 
347
- // \u53D1\u9001\u52A0\u8F7D\u5B8C\u6210\u6D88\u606F
347
+ // send loaded message
348
348
  window.parent.postMessage({
349
349
  type: 'iframe_loaded',
350
350
  spatialId: '${spatialId}',
351
351
  url: '${url}'
352
352
  }, '${window.location.origin}');
353
353
 
354
- // \u8BBE\u7F6E\u6D88\u606F\u5904\u7406\u5668
354
+ // set message handler
355
355
  window.addEventListener('message', (event) => {
356
356
  if (event.origin !== window.parent.location.origin) return;
357
357
 
358
358
  const data = event.data;
359
359
  if (data && data.type === 'webspatial_command') {
360
- // \u5904\u7406\u6765\u81EA\u7236\u7A97\u53E3\u7684\u547D\u4EE4
360
+ // handle command from parent window
361
361
  console.log('Received command in iframe from parent:', data.command);
362
- // \u8FD9\u91CC\u53EF\u4EE5\u6DFB\u52A0\u547D\u4EE4\u5904\u7406\u903B\u8F91
362
+ // add command handling logic here
363
363
  }
364
364
  });
365
365
  `;
@@ -396,7 +396,7 @@ var init_PuppeteerPlatform = __esm({
396
396
  }
397
397
  }
398
398
  /**
399
- * 解析features字符串为对象
399
+ * parse features string to object
400
400
  */
401
401
  parseFeatures(features) {
402
402
  const result = {};
@@ -410,7 +410,7 @@ var init_PuppeteerPlatform = __esm({
410
410
  return result;
411
411
  }
412
412
  /**
413
- * 发送消息到指定spatialId的iframe
413
+ * send message to iframe with specified spatialId
414
414
  */
415
415
  sendMessageToIframe(spatialId, message) {
416
416
  const iframe = this.iframeRegistry.get(spatialId);
@@ -421,7 +421,7 @@ var init_PuppeteerPlatform = __esm({
421
421
  return false;
422
422
  }
423
423
  /**
424
- * 获取所有活跃的iframe
424
+ * get all active iframes
425
425
  */
426
426
  getAllActiveIframes() {
427
427
  const result = [];
@@ -431,7 +431,7 @@ var init_PuppeteerPlatform = __esm({
431
431
  return result;
432
432
  }
433
433
  /**
434
- * 清理资源
434
+ * dispose all active iframes
435
435
  */
436
436
  dispose() {
437
437
  this.iframeRegistry.forEach((iframe, spatialId) => {
@@ -440,7 +440,7 @@ var init_PuppeteerPlatform = __esm({
440
440
  });
441
441
  this.iframeRegistry.clear();
442
442
  }
443
- // 生成UUID函数
443
+ // generate UUID function
444
444
  generateUUID() {
445
445
  return "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(
446
446
  /[xy]/g,
@@ -834,7 +834,7 @@ var init_utils = __esm({
834
834
  });
835
835
 
836
836
  // src/JSBCommand.ts
837
- var platform, JSBCommand, UpdateEntityPropertiesCommand, UpdateEntityEventCommand, UpdateSpatialSceneProperties, UpdateSceneConfig, FocusScene, GetSpatialSceneState, SpatializedElementCommand, UpdateSpatialized2DElementProperties, UpdateSpatializedDynamic3DElementProperties, UpdateUnlitMaterialProperties, UpdateSpatializedElementTransform, UpdateSpatializedStatic3DElementProperties, AddSpatializedElementToSpatialized2DElement, AddSpatializedElementToSpatialScene, CreateSpatializedStatic3DElementCommand, CreateSpatializedDynamic3DElementCommand, CreateSpatialEntityCommand, CreateModelComponentCommand, CreateSpatialModelEntityCommand, CreateModelAssetCommand, CreateSpatialGeometryCommand, CreateSpatialUnlitMaterialCommand, AddComponentToEntityCommand, SetParentForEntityCommand, ConvertFromEntityToEntityCommand, ConvertFromEntityToSceneCommand, ConvertFromSceneToEntityCommand, InspectCommand, DestroyCommand, CheckWebViewCanCreateCommand, WebSpatialProtocolCommand, createSpatialized2DElementCommand, createSpatialSceneCommand, CreateAttachmentEntityCommand, UpdateAttachmentEntityCommand;
837
+ var platform, JSBCommand, UpdateEntityPropertiesCommand, UpdateEntityEventCommand, UpdateSpatialSceneProperties, UpdateSceneConfig, FocusScene, GetSpatialSceneState, SpatializedElementCommand, UpdateSpatialized2DElementProperties, UpdateSpatializedDynamic3DElementProperties, UpdateUnlitMaterialProperties, UpdateSpatializedElementTransform, UpdateSpatializedStatic3DElementProperties, AddSpatializedElementToSpatialized2DElement, AddSpatializedElementToSpatialScene, CreateSpatializedStatic3DElementCommand, CreateSpatializedDynamic3DElementCommand, CreateSpatialEntityCommand, CreateModelComponentCommand, CreateSpatialModelEntityCommand, CreateModelAssetCommand, CreateSpatialGeometryCommand, CreateSpatialUnlitMaterialCommand, AddComponentToEntityCommand, SetParentForEntityCommand, ConvertFromEntityToEntityCommand, ConvertFromEntityToSceneCommand, ConvertFromSceneToEntityCommand, ConvertCoordinateCommand, InspectCommand, DestroyCommand, CheckWebViewCanCreateCommand, WebSpatialProtocolCommand, createSpatialized2DElementCommand, createSpatialSceneCommand, CreateAttachmentEntityCommand, InitializeAttachmentCommand, UpdateAttachmentEntityCommand;
838
838
  var init_JSBCommand = __esm({
839
839
  "src/JSBCommand.ts"() {
840
840
  "use strict";
@@ -1172,6 +1172,22 @@ var init_JSBCommand = __esm({
1172
1172
  }
1173
1173
  commandType = "ConvertFromSceneToEntity";
1174
1174
  };
1175
+ ConvertCoordinateCommand = class extends JSBCommand {
1176
+ constructor(position, fromId, toId) {
1177
+ super();
1178
+ this.position = position;
1179
+ this.fromId = fromId;
1180
+ this.toId = toId;
1181
+ }
1182
+ getParams() {
1183
+ return {
1184
+ position: this.position,
1185
+ fromId: this.fromId,
1186
+ toId: this.toId
1187
+ };
1188
+ }
1189
+ commandType = "ConvertCoordinate";
1190
+ };
1175
1191
  InspectCommand = class extends JSBCommand {
1176
1192
  constructor(id = "") {
1177
1193
  super();
@@ -1267,11 +1283,24 @@ var init_JSBCommand = __esm({
1267
1283
  this.options = options;
1268
1284
  }
1269
1285
  commandType = "createAttachment";
1286
+ getParams() {
1287
+ return {};
1288
+ }
1289
+ };
1290
+ InitializeAttachmentCommand = class extends JSBCommand {
1291
+ constructor(attachmentId, options) {
1292
+ super();
1293
+ this.attachmentId = attachmentId;
1294
+ this.options = options;
1295
+ }
1296
+ commandType = "InitializeAttachment";
1270
1297
  getParams() {
1271
1298
  return {
1299
+ id: this.attachmentId,
1272
1300
  parentEntityId: this.options.parentEntityId,
1273
1301
  position: this.options.position ?? [0, 0, 0],
1274
- size: this.options.size
1302
+ size: this.options.size,
1303
+ ownerViewId: this.options.ownerViewId
1275
1304
  };
1276
1305
  }
1277
1306
  };
@@ -1332,6 +1361,7 @@ init_JSBCommand();
1332
1361
 
1333
1362
  // src/SpatialScene.ts
1334
1363
  init_JSBCommand();
1364
+ init_JSBCommand();
1335
1365
  var instance;
1336
1366
  var SpatialScene = class _SpatialScene extends SpatialObject {
1337
1367
  /**
@@ -1345,6 +1375,19 @@ var SpatialScene = class _SpatialScene extends SpatialObject {
1345
1375
  }
1346
1376
  return instance;
1347
1377
  }
1378
+ async convertCoordinate(position, fromId, toId) {
1379
+ try {
1380
+ const ret = await new ConvertCoordinateCommand(
1381
+ position,
1382
+ fromId,
1383
+ toId
1384
+ ).execute();
1385
+ return ret?.data ?? position;
1386
+ } catch (error) {
1387
+ console.warn("SpatialScene.convertCoordinate error:", error);
1388
+ throw error;
1389
+ }
1390
+ }
1348
1391
  /**
1349
1392
  * Updates the properties of the spatial scene.
1350
1393
  * This can include background settings, lighting, and other scene-wide properties.
@@ -1844,29 +1887,6 @@ var SpatializedElement = class extends SpatialObject {
1844
1887
  const { type } = data;
1845
1888
  if (type === "objectdestroy" /* objectdestroy */) {
1846
1889
  this.isDestroyed = true;
1847
- } else if (type === "cubeInfo" /* cubeInfo */) {
1848
- const cubeInfoMsg = data;
1849
- this._cubeInfo = new CubeInfo(cubeInfoMsg.size, cubeInfoMsg.origin);
1850
- } else if (type === "transform" /* transform */) {
1851
- this._transform = new DOMMatrix([
1852
- data.detail.column0[0],
1853
- data.detail.column0[1],
1854
- data.detail.column0[2],
1855
- 0,
1856
- data.detail.column1[0],
1857
- data.detail.column1[1],
1858
- data.detail.column1[2],
1859
- 0,
1860
- data.detail.column2[0],
1861
- data.detail.column2[1],
1862
- data.detail.column2[2],
1863
- 0,
1864
- data.detail.column3[0],
1865
- data.detail.column3[1],
1866
- data.detail.column3[2],
1867
- 1
1868
- ]);
1869
- this._transformInv = this._transform.inverse();
1870
1890
  } else if (type === "spatialtap" /* spatialtap */) {
1871
1891
  const event = createSpatialEvent(
1872
1892
  "spatialtap" /* spatialtap */,
@@ -2045,6 +2065,7 @@ var SpatializedStatic3DElement = class extends SpatializedElement {
2045
2065
  * @returns Promise that resolves when the model is loaded (true) or fails to load (false)
2046
2066
  */
2047
2067
  createReadyPromise() {
2068
+ this._readyResolve?.(false);
2048
2069
  return new Promise((resolve) => {
2049
2070
  this._readyResolve = resolve;
2050
2071
  });
@@ -2120,6 +2141,7 @@ var SpatializedStatic3DElement = class extends SpatializedElement {
2120
2141
  init_JSBCommand();
2121
2142
  var SpatializedDynamic3DElement = class extends SpatializedElement {
2122
2143
  children = [];
2144
+ events = {};
2123
2145
  constructor(id) {
2124
2146
  super(id);
2125
2147
  }
@@ -2129,6 +2151,17 @@ var SpatializedDynamic3DElement = class extends SpatializedElement {
2129
2151
  entity.parent = this;
2130
2152
  return ans;
2131
2153
  }
2154
+ addEvent(type, callback) {
2155
+ this.events[type] = callback;
2156
+ }
2157
+ removeEvent(eventName) {
2158
+ if (this.events[eventName]) {
2159
+ delete this.events[eventName];
2160
+ }
2161
+ }
2162
+ dispatchEvent(evt) {
2163
+ this.events[evt.type]?.(evt);
2164
+ }
2132
2165
  async updateProperties(properties) {
2133
2166
  return new UpdateSpatializedDynamic3DElementProperties(
2134
2167
  this,
@@ -2197,6 +2230,7 @@ async function createAttachmentEntity(options) {
2197
2230
  throw new Error("createAttachmentEntity failed: " + result?.errorMessage);
2198
2231
  }
2199
2232
  const { id, windowProxy } = result.data;
2233
+ await new InitializeAttachmentCommand(id, options).execute();
2200
2234
  return new Attachment(id, windowProxy, options);
2201
2235
  }
2202
2236
 
@@ -2207,7 +2241,7 @@ init_JSBCommand();
2207
2241
  init_JSBCommand();
2208
2242
  init_JSBCommand();
2209
2243
  init_SpatialWebEvent();
2210
- var SpatialEntity = class _SpatialEntity extends SpatialObject {
2244
+ var SpatialEntity = class extends SpatialObject {
2211
2245
  constructor(id, userData) {
2212
2246
  super(id);
2213
2247
  this.userData = userData;
@@ -2219,6 +2253,20 @@ var SpatialEntity = class _SpatialEntity extends SpatialObject {
2219
2253
  events = {};
2220
2254
  children = [];
2221
2255
  parent = null;
2256
+ _enableInput = false;
2257
+ get enableInput() {
2258
+ return this._enableInput;
2259
+ }
2260
+ set enableInput(value) {
2261
+ if (this._enableInput === value) return;
2262
+ this._enableInput = value;
2263
+ void this.updateEntityEvent("spatialtap", value).catch((err) => {
2264
+ console.error("enableInput updateEntityEvent failed", "spatialtap", err);
2265
+ if (this._enableInput === value) {
2266
+ this._enableInput = !value;
2267
+ }
2268
+ });
2269
+ }
2222
2270
  async addComponent(component) {
2223
2271
  return new AddComponentToEntityCommand(this, component).execute();
2224
2272
  }
@@ -2286,10 +2334,7 @@ var SpatialEntity = class _SpatialEntity extends SpatialObject {
2286
2334
  if (type === "objectdestroy" /* objectdestroy */) {
2287
2335
  this.isDestroyed = true;
2288
2336
  } else if (type === "spatialtap" /* spatialtap */) {
2289
- const evt = createSpatialEvent(
2290
- "spatialtap" /* spatialtap */,
2291
- data.detail
2292
- );
2337
+ const evt = createSpatialEvent("spatialtap" /* spatialtap */, data.detail);
2293
2338
  this.dispatchEvent(evt);
2294
2339
  } else if (type === "spatialdragstart" /* spatialdragstart */) {
2295
2340
  const evt = createSpatialEvent(
@@ -2298,10 +2343,7 @@ var SpatialEntity = class _SpatialEntity extends SpatialObject {
2298
2343
  );
2299
2344
  this.dispatchEvent(evt);
2300
2345
  } else if (type === "spatialdrag" /* spatialdrag */) {
2301
- const evt = createSpatialEvent(
2302
- "spatialdrag" /* spatialdrag */,
2303
- data.detail
2304
- );
2346
+ const evt = createSpatialEvent("spatialdrag" /* spatialdrag */, data.detail);
2305
2347
  this.dispatchEvent(evt);
2306
2348
  } else if (type === "spatialdragend" /* spatialdragend */) {
2307
2349
  const evt = createSpatialEvent(
@@ -2341,7 +2383,7 @@ var SpatialEntity = class _SpatialEntity extends SpatialObject {
2341
2383
  }
2342
2384
  this.events[evt.type]?.(evt);
2343
2385
  if (evt.bubbles && !evt.cancelBubble) {
2344
- if (this.parent && this.parent instanceof _SpatialEntity) {
2386
+ if (this.parent) {
2345
2387
  this.parent.dispatchEvent(evt);
2346
2388
  }
2347
2389
  }
@@ -2704,6 +2746,7 @@ var SpatialSession = class {
2704
2746
  // src/Spatial.ts
2705
2747
  init_SpatialWebEvent();
2706
2748
  var Spatial = class {
2749
+ wsAppShellVersionFromUA;
2707
2750
  /**
2708
2751
  * Requests a spatial session object from the browser.
2709
2752
  * This is the primary method to initialize spatial functionality.
@@ -2729,6 +2772,20 @@ var Spatial = class {
2729
2772
  }
2730
2773
  return false;
2731
2774
  }
2775
+ getShellVersionFromUA() {
2776
+ if (this.wsAppShellVersionFromUA !== void 0) {
2777
+ return this.wsAppShellVersionFromUA;
2778
+ }
2779
+ if (typeof navigator === "undefined" || typeof navigator.userAgent !== "string") {
2780
+ this.wsAppShellVersionFromUA = null;
2781
+ return null;
2782
+ }
2783
+ const match = navigator.userAgent.match(
2784
+ /WSAppShell\/(\d+(?:\.\d+){2}(?:[-+][0-9A-Za-z.-]+)*)/
2785
+ );
2786
+ this.wsAppShellVersionFromUA = match ? match[1] : "1.3.0";
2787
+ return this.wsAppShellVersionFromUA;
2788
+ }
2732
2789
  /** @deprecated
2733
2790
  * Checks if WebSpatial is supported in the current environment.
2734
2791
  * Verifies compatibility between native and client versions.
@@ -2746,7 +2803,7 @@ var Spatial = class {
2746
2803
  if (window.__WebSpatialData && window.__WebSpatialData.getNativeVersion) {
2747
2804
  return window.__WebSpatialData.getNativeVersion();
2748
2805
  }
2749
- return window.WebSpatailNativeVersion === "PACKAGE_VERSION" ? this.getClientVersion() : window.WebSpatailNativeVersion;
2806
+ return window.WebSpatailNativeVersion === "WS_SHELL_VERSION" ? this.getClientVersion() : window.WebSpatailNativeVersion;
2750
2807
  }
2751
2808
  /** @deprecated
2752
2809
  * Gets the client SDK version.
@@ -2754,10 +2811,70 @@ var Spatial = class {
2754
2811
  * @returns Client SDK version string in format "x.x.x"
2755
2812
  */
2756
2813
  getClientVersion() {
2757
- return "1.3.0";
2814
+ return "1.4.0";
2758
2815
  }
2759
2816
  };
2760
2817
 
2818
+ // src/physicalMetrics.ts
2819
+ var physicalMetrics_exports = {};
2820
+ __export(physicalMetrics_exports, {
2821
+ getValue: () => getValue,
2822
+ physicalToPoint: () => physicalToPoint,
2823
+ pointToPhysical: () => pointToPhysical,
2824
+ subscribe: () => subscribe
2825
+ });
2826
+ init_SpatialWebEvent();
2827
+ var snapshot = {
2828
+ meterToPtUnscaled: 1360,
2829
+ meterToPtScaled: 1360
2830
+ };
2831
+ function getWorldScalingCompensation(options) {
2832
+ return options?.worldScalingCompensation ?? "scaled";
2833
+ }
2834
+ function pointToPhysical(point, options) {
2835
+ updateValue();
2836
+ const compensation = getWorldScalingCompensation(options);
2837
+ if (compensation === "unscaled") {
2838
+ return point / snapshot.meterToPtUnscaled;
2839
+ }
2840
+ return point / snapshot.meterToPtScaled;
2841
+ }
2842
+ function physicalToPoint(physical, options) {
2843
+ updateValue();
2844
+ const compensation = getWorldScalingCompensation(options);
2845
+ if (compensation === "unscaled") {
2846
+ return physical * snapshot.meterToPtUnscaled;
2847
+ }
2848
+ return physical * snapshot.meterToPtScaled;
2849
+ }
2850
+ function updateValue() {
2851
+ if (typeof window === "undefined") return;
2852
+ const src = window.__webspatialsdk__?.physicalMetrics;
2853
+ if (!src) return;
2854
+ const next = {
2855
+ meterToPtScaled: src.meterToPtScaled ?? snapshot.meterToPtScaled,
2856
+ meterToPtUnscaled: src.meterToPtUnscaled ?? snapshot.meterToPtUnscaled
2857
+ };
2858
+ if (next.meterToPtScaled !== snapshot.meterToPtScaled || next.meterToPtUnscaled !== snapshot.meterToPtUnscaled) {
2859
+ snapshot = next;
2860
+ }
2861
+ }
2862
+ function getValue() {
2863
+ updateValue();
2864
+ return snapshot;
2865
+ }
2866
+ function subscribe(cb) {
2867
+ if (typeof window === "undefined") return () => {
2868
+ };
2869
+ const handler = () => {
2870
+ cb();
2871
+ };
2872
+ SpatialWebEvent.addEventReceiver("window", handler);
2873
+ return () => {
2874
+ SpatialWebEvent.removeEventReceiver("window");
2875
+ };
2876
+ }
2877
+
2761
2878
  // src/index.ts
2762
2879
  init_ssr_polyfill();
2763
2880
 
@@ -2909,6 +3026,7 @@ export {
2909
3026
  BaseplateVisibilityValues,
2910
3027
  CubeInfo,
2911
3028
  ModelComponent,
3029
+ physicalMetrics_exports as PhysicalMetrics,
2912
3030
  Spatial,
2913
3031
  SpatialBoxGeometry,
2914
3032
  SpatialComponent,