gps-plus-slam-app-framework 1.3.0 → 1.7.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/absolute-orientation-CAEh840t.d.ts +54 -0
- package/dist/{app-selectors-B8VQoMDY.d.ts → app-selectors-ikTUQZpe.d.ts} +1 -1
- package/dist/ar/bresenham3d.d.ts +1 -1
- package/dist/ar/camera-blit-capture.d.ts +2 -2
- package/dist/ar/camera-blit-capture.js +74 -9
- package/dist/ar/capability-checker.d.ts +1 -1
- package/dist/ar/capture-failure-tracker.d.ts +1 -1
- package/dist/ar/chromium-camera-access-workaround.d.ts +1 -1
- package/dist/ar/depth-grid-lookup.d.ts +2 -0
- package/dist/ar/depth-grid-lookup.js +43 -0
- package/dist/ar/depth-sampler.d.ts +2 -2
- package/dist/ar/depth-sampler.js +2 -4
- package/dist/ar/depth-unprojection.d.ts +1 -1
- package/dist/ar/enable-gps-ar.d.ts +1 -1
- package/dist/ar/enable-gps-ar.js +26 -1
- package/dist/ar/frame-loop.d.ts +1 -1
- package/dist/ar/image-capture.d.ts +2 -2
- package/dist/ar/image-capture.js +1 -154
- package/dist/ar/image-quality.d.ts +2 -0
- package/dist/ar/image-quality.js +168 -0
- package/dist/ar/index.d.ts +31 -19
- package/dist/ar/index.js +17 -5
- package/dist/ar/occupancy-grid.d.ts +1 -1
- package/dist/ar/occupancy-grid.js +29 -2
- package/dist/ar/planar-pnp.d.ts +2 -0
- package/dist/ar/planar-pnp.js +425 -0
- package/dist/ar/qr-debug-view.d.ts +2 -0
- package/dist/ar/qr-debug-view.js +89 -0
- package/dist/ar/qr-derived-pose.d.ts +2 -0
- package/dist/ar/qr-derived-pose.js +114 -0
- package/dist/ar/qr-detection-controller.d.ts +2 -0
- package/dist/ar/qr-detection-controller.js +2 -0
- package/dist/ar/qr-frontend.d.ts +2 -0
- package/dist/ar/qr-frontend.js +60 -0
- package/dist/ar/qr-pose.d.ts +2 -0
- package/dist/ar/qr-pose.js +267 -0
- package/dist/ar/qr-size-depth-context.d.ts +3 -0
- package/dist/ar/qr-size-depth-context.js +42 -0
- package/dist/ar/qr-size-measurer.d.ts +2 -0
- package/dist/ar/qr-size-measurer.js +2 -0
- package/dist/ar/replay-scene.d.ts +1 -1
- package/dist/ar/replay-scene.js +1 -1
- package/dist/ar/scene-node-names.d.ts +1 -1
- package/dist/ar/webxr-nue-basis.d.ts +1 -1
- package/dist/ar/webxr-session.d.ts +4 -4
- package/dist/ar/webxr-session.js +2 -2
- package/dist/ar/xr-camera-texture.d.ts +1 -1
- package/dist/ar/xr-error-handler.d.ts +1 -1
- package/dist/ar/xr-frame-loop.d.ts +1 -1
- package/dist/ar-MFpFlV7j.js +382 -0
- package/dist/{ar-world-group-alignment-C9lwwIyI.d.ts → ar-world-group-alignment-69fgnB39.d.ts} +1 -1
- package/dist/{camera-blit-capture-CnxUDbKx.d.ts → camera-blit-capture-NKT9H5-e.d.ts} +57 -4
- package/dist/capture-motion-gate-0Yl2NpQG.d.ts +24 -0
- package/dist/capture-motion-gate-4EscNZCw.js +94 -0
- package/dist/concurrency-By0oOTZt.d.ts +50 -0
- package/dist/core/index.d.ts +2 -2
- package/dist/core/index.js +2 -2
- package/dist/create-slam-app-store-DkCHOpvb.js +149 -0
- package/dist/{create-slam-app-store-BljusOua.d.ts → create-slam-app-store-n_VF63D5.d.ts} +50 -40
- package/dist/depth-grid-lookup-DQ-IYhO3.d.ts +21 -0
- package/dist/{depth-sampler-Bhanfwla.d.ts → depth-sampler-asc8exHt.d.ts} +1 -1
- package/dist/{depth-unprojection-Y6i_mJuT.d.ts → depth-unprojection-DjsbJW9L.d.ts} +1 -1
- package/dist/{enable-gps-ar-BfUJOgpW.d.ts → enable-gps-ar-DkNhFv4Y.d.ts} +4 -4
- package/dist/{frame-conversions-BfsafGWR.d.ts → frame-conversions-DObhj8Wf.d.ts} +1 -1
- package/dist/{fused-path-DJoVu98b.d.ts → fused-path-v6eOmLl3.d.ts} +1 -1
- package/dist/geo/h3-proximity.d.ts +2 -2
- package/dist/geo/h3-proximity.js +61 -2
- package/dist/geo/index.d.ts +2 -2
- package/dist/geo/index.js +2 -2
- package/dist/geodesic-angle-BTldfFgs.js +39 -0
- package/dist/{gps-anchor-dYeCvvp5.d.ts → gps-anchor-BeFO2RYa.d.ts} +1 -1
- package/dist/{gps-ar-pose-sampler-DVb96iOy.d.ts → gps-ar-pose-sampler-DHMZmYAc.d.ts} +1 -1
- package/dist/{gps-event-coordinator-CWIDOk4U.d.ts → gps-event-coordinator-CjWW636x.d.ts} +21 -11
- package/dist/{gps-event-markers-Dc9FT-q1.d.ts → gps-event-markers-Cz9RMA2k.d.ts} +18 -0
- package/dist/{h3-proximity-I1msGPgE.d.ts → h3-proximity-C-j0pw1j.d.ts} +39 -1
- package/dist/image-capture-B2-b6tKK.js +374 -0
- package/dist/{image-capture-qAZ5Fh5X.d.ts → image-capture-CNZDrQXG.d.ts} +103 -3
- package/dist/image-quality-smCBoFj1.d.ts +158 -0
- package/dist/index-BAPokxMb.d.ts +22 -0
- package/dist/{index-BYYUdf9v.d.ts → index-BODDUTvD.d.ts} +1 -1
- package/dist/index-BneSj4_5.d.ts +399 -0
- package/dist/index-_Rhgoqkh.d.ts +2 -0
- package/dist/index.d.ts +80 -67
- package/dist/index.js +24 -12
- package/dist/{leaflet-map-overlay-6CJC-E1l.d.ts → leaflet-map-overlay-CmIyiE8n.d.ts} +1 -1
- package/dist/{map-data-CkloBxIl.d.ts → map-data-B4oEehUh.d.ts} +1 -1
- package/dist/{map-overlay-draw-krOKwDAq.d.ts → map-overlay-draw-ymz1s7fG.d.ts} +1 -1
- package/dist/{null-storage-backend-uKQE8tl7.d.ts → null-storage-backend-B9rtyDfG.d.ts} +2 -2
- package/dist/{occupancy-grid-BRNRaPyT.d.ts → occupancy-grid-DnOc-6PU.d.ts} +12 -2
- package/dist/{opfs-storage-D5zAn_lx.d.ts → opfs-storage-3VZh-qH6.d.ts} +23 -4
- package/dist/{opfs-storage-backend-6aYMUZlJ.d.ts → opfs-storage-backend-JJiUJo-3.d.ts} +3 -3
- package/dist/{persistence-middleware-B9ei4Nhx.d.ts → persistence-middleware-DAPTTwB2.d.ts} +1 -1
- package/dist/planar-pnp-my9bqULS.d.ts +67 -0
- package/dist/qr-debug-view-Brl73HGO.d.ts +29 -0
- package/dist/qr-derived-pose-CmxTP2m4.d.ts +122 -0
- package/dist/qr-detected-slice-VQssZmQJ.d.ts +166 -0
- package/dist/qr-detection-controller-B-tLVd-S.js +119 -0
- package/dist/qr-detection-controller-CDurHv8E.d.ts +48 -0
- package/dist/qr-frontend--fFX25mV.d.ts +58 -0
- package/dist/qr-pose-D2rfu5DA.d.ts +138 -0
- package/dist/qr-pose-aggregation-B7tWJq7j.d.ts +90 -0
- package/dist/qr-pose-aggregation-DBiaLW0O.js +191 -0
- package/dist/qr-size-depth-context-CeAG53fy.d.ts +13 -0
- package/dist/qr-size-measurer-DLb33geH.js +596 -0
- package/dist/qr-size-measurer-DQdAsid1.d.ts +165 -0
- package/dist/recording-options-BPCpMHLK.d.ts +514 -0
- package/dist/{recording-replayer-r0DZ9ALp.d.ts → recording-replayer-DQKpAGyQ.d.ts} +2 -2
- package/dist/recording-slice-DaxHZvNu.d.ts +55 -0
- package/dist/{replay-engine-XpDa0dy1.d.ts → replay-engine-CmKh_4wf.d.ts} +7 -4
- package/dist/{replay-scene-Bw58VL6p.d.ts → replay-scene-DBlDrV_x.d.ts} +3 -3
- package/dist/sensors/absolute-orientation.d.ts +2 -0
- package/dist/sensors/absolute-orientation.js +145 -0
- package/dist/sensors/gps-error-handler.d.ts +1 -1
- package/dist/sensors/gps.d.ts +1 -1
- package/dist/sensors/index.d.ts +5 -4
- package/dist/sensors/index.js +2 -1
- package/dist/sensors/permission-checker.d.ts +1 -1
- package/dist/sensors/permission-checker.js +1 -1
- package/dist/state/app-selectors.d.ts +1 -1
- package/dist/state/combined-root-state.d.ts +1 -1
- package/dist/state/create-slam-app-store.d.ts +1 -1
- package/dist/state/create-slam-app-store.js +1 -74
- package/dist/state/gps-ar-pose-sampler.d.ts +3 -3
- package/dist/state/gps-event-coordinator.d.ts +2 -2
- package/dist/state/gps-event-coordinator.js +27 -17
- package/dist/state/index.d.ts +20 -17
- package/dist/state/index.js +5 -4
- package/dist/state/persistence-middleware.d.ts +1 -1
- package/dist/state/persistence-middleware.js +30 -19
- package/dist/state/qr-detected-slice.d.ts +4 -0
- package/dist/state/qr-detected-slice.js +311 -0
- package/dist/state/recording-options.d.ts +2 -2
- package/dist/state/recording-options.js +273 -7
- package/dist/state/recording-replayer.d.ts +2 -2
- package/dist/state/recording-replayer.js +1 -1
- package/dist/state/recording-slice.d.ts +1 -1
- package/dist/state/recording-slice.js +5 -1
- package/dist/state/replay-engine.d.ts +1 -1
- package/dist/state/replay-engine.js +7 -3
- package/dist/state/store-subscribers.d.ts +2 -2
- package/dist/state/subscribe-to-selector.d.ts +1 -1
- package/dist/state/tracking-quality.d.ts +2 -2
- package/dist/state/tracking-quality.js +40 -128
- package/dist/state/tracking-slice.d.ts +1 -1
- package/dist/{state-BkIfpiyA.js → state-E51QT_-j.js} +2 -1
- package/dist/storage/file-system-utils.d.ts +1 -1
- package/dist/storage/index.d.ts +9 -9
- package/dist/storage/index.js +4 -4
- package/dist/storage/null-storage-backend.d.ts +1 -1
- package/dist/storage/opfs-storage-backend.d.ts +1 -1
- package/dist/storage/opfs-storage-backend.js +3 -3
- package/dist/storage/opfs-storage.d.ts +1 -1
- package/dist/storage/opfs-storage.js +5 -4
- package/dist/storage/storage-backend.d.ts +1 -1
- package/dist/storage/zip-coverage-embed.d.ts +2 -0
- package/dist/storage/zip-coverage-embed.js +88 -0
- package/dist/storage/zip-export.d.ts +2 -2
- package/dist/storage/zip-export.js +37 -59
- package/dist/storage/zip-reader.d.ts +1 -1
- package/dist/{storage-backend-Do6YDpNo.d.ts → storage-backend-BdVLD0dU.d.ts} +1 -1
- package/dist/{store-subscribers-0YWyOLvV.d.ts → store-subscribers-CA6AJH_8.d.ts} +2 -2
- package/dist/{subscribe-to-selector-CZ6k1NFP.d.ts → subscribe-to-selector-B6EUmQ3I.d.ts} +1 -1
- package/dist/test-utils/browser-mocks.d.ts +7 -1
- package/dist/test-utils/browser-mocks.js +6 -0
- package/dist/test-utils/zip-round-trip-helpers.d.ts +9 -1
- package/dist/test-utils/zip-round-trip-helpers.js +5 -1
- package/dist/{tracking-slice-CdK8c-8P.d.ts → tracking-slice-BuAZxXZ5.d.ts} +1 -1
- package/dist/types/ar-types.d.ts +1 -1
- package/dist/types/geo-types.d.ts +1 -1
- package/dist/types/index.d.ts +2 -2
- package/dist/utils/concurrency.d.ts +2 -2
- package/dist/utils/concurrency.js +66 -2
- package/dist/utils/failure-tracker.d.ts +1 -1
- package/dist/utils/format-file-size.d.ts +1 -1
- package/dist/utils/fused-path.d.ts +1 -1
- package/dist/utils/index.d.ts +8 -7
- package/dist/utils/index.js +2 -1
- package/dist/utils/list-formatter.d.ts +1 -1
- package/dist/utils/logger.d.ts +1 -1
- package/dist/visualization/accuracy-circles.d.ts +1 -1
- package/dist/visualization/alignment-lerper.d.ts +1 -1
- package/dist/visualization/ar-world-group-alignment.d.ts +1 -1
- package/dist/visualization/ar-world-group-alignment.js +1 -1
- package/dist/visualization/camera-follower.d.ts +1 -1
- package/dist/visualization/css3d-renderer-manager.d.ts +1 -1
- package/dist/visualization/frame-conversions.d.ts +1 -1
- package/dist/visualization/frustum-visibility.d.ts +1 -1
- package/dist/visualization/gps-anchor.d.ts +1 -1
- package/dist/visualization/gps-compass-cubes.d.ts +1 -1
- package/dist/visualization/gps-event-markers.d.ts +1 -1
- package/dist/visualization/gps-event-markers.js +40 -5
- package/dist/visualization/hit-test-reticle.d.ts +1 -1
- package/dist/visualization/hit-test-reticle.js +1 -0
- package/dist/visualization/index.d.ts +18 -18
- package/dist/visualization/leaflet-map-overlay.d.ts +1 -1
- package/dist/visualization/leaflet-map-overlay.js +15 -3
- package/dist/visualization/lerp-utils.d.ts +1 -1
- package/dist/visualization/map-data.d.ts +1 -1
- package/dist/visualization/map-overlay-draw.d.ts +1 -1
- package/dist/visualization/map-overlay.d.ts +1 -1
- package/dist/visualization/three-dispose.d.ts +1 -1
- package/dist/visualization/vis-colors.d.ts +1 -1
- package/dist/{webxr-session-TIaD883f.js → webxr-session-DG-eNfny.js} +244 -11
- package/dist/{webxr-session-GjZ2BIpS.d.ts → webxr-session-Do5L6G3B.d.ts} +86 -8
- package/dist/zip-coverage-embed-DCAREVmw.d.ts +41 -0
- package/dist/{zip-export-G14hkSPG.d.ts → zip-export-ol0S_Ofd.d.ts} +27 -23
- package/package.json +2 -2
- package/dist/concurrency-CO1FQvs3.d.ts +0 -24
- package/dist/file-system-CwXTNHmB.d.ts +0 -114
- package/dist/index-CF05QV2m.d.ts +0 -2
- package/dist/recording-options-DJBXuMxV.d.ts +0 -182
- package/dist/recording-slice-89O07ebs.d.ts +0 -36
- package/dist/storage/file-system.d.ts +0 -2
- package/dist/storage/file-system.js +0 -289
- /package/dist/{accuracy-circles-BpwWAs8G.d.ts → accuracy-circles-BtqOP_v1.d.ts} +0 -0
- /package/dist/{alignment-lerper-Dm9G7JJO.d.ts → alignment-lerper-Bil6vbVw.d.ts} +0 -0
- /package/dist/{ar-types-Dan1MVTi.d.ts → ar-types-BFX2r1wk.d.ts} +0 -0
- /package/dist/{bresenham3d-CFfd7n6B.d.ts → bresenham3d-CU1Gv2W4.d.ts} +0 -0
- /package/dist/{camera-follower-C2mwEn7c.d.ts → camera-follower-CqJJ7zRj.d.ts} +0 -0
- /package/dist/{capability-checker-CQXJHxXg.d.ts → capability-checker-DUQLg6gq.d.ts} +0 -0
- /package/dist/{capture-failure-tracker-CUeU3L_M.d.ts → capture-failure-tracker-gsm8q7yi.d.ts} +0 -0
- /package/dist/{chromium-camera-access-workaround-Jqbn0apH.d.ts → chromium-camera-access-workaround-D4K2uwwQ.d.ts} +0 -0
- /package/dist/{css3d-renderer-manager-ptu_t3B3.d.ts → css3d-renderer-manager-B3kGNtcn.d.ts} +0 -0
- /package/dist/{failure-tracker-Cn8Fo9D4.d.ts → failure-tracker-BO7M7jF_.d.ts} +0 -0
- /package/dist/{file-system-utils-CXIoL-DM.d.ts → file-system-utils-DOajnMm-.d.ts} +0 -0
- /package/dist/{format-file-size-CLCZz3lC.d.ts → format-file-size-Dc98ulzB.d.ts} +0 -0
- /package/dist/{frame-loop-CMewS8cY.d.ts → frame-loop-CpVjQ1dH.d.ts} +0 -0
- /package/dist/{frustum-visibility-CmI96ESS.d.ts → frustum-visibility-CeoCZchO.d.ts} +0 -0
- /package/dist/{geo-types-SaPnIEUM.d.ts → geo-types-3Ip1NzVR.d.ts} +0 -0
- /package/dist/{gps-VuezJWK3.d.ts → gps-BBO3hKfT.d.ts} +0 -0
- /package/dist/{gps-compass-cubes-BM1uGiYV.d.ts → gps-compass-cubes-DSN87L8p.d.ts} +0 -0
- /package/dist/{gps-error-handler-CJl_2MVm.d.ts → gps-error-handler-BbPsfw-_.d.ts} +0 -0
- /package/dist/{hit-test-reticle-BEzEybxZ.d.ts → hit-test-reticle-DV-2TpB9.d.ts} +0 -0
- /package/dist/{lerp-utils-BpV-0Dtk.d.ts → lerp-utils-BLmHhkVe.d.ts} +0 -0
- /package/dist/{list-formatter-RRcBe8Vg.d.ts → list-formatter-KNMS0ay2.d.ts} +0 -0
- /package/dist/{logger-BEHXsnnq.d.ts → logger-CLnPrHiD.d.ts} +0 -0
- /package/dist/{map-overlay-bcogY5fK.d.ts → map-overlay-Dh2B97MP.d.ts} +0 -0
- /package/dist/{permission-checker-GpAiSCwd.d.ts → permission-checker-CDuI8BwC.d.ts} +0 -0
- /package/dist/{scene-node-names-Bu0S66H1.d.ts → scene-node-names-BiShOQDB.d.ts} +0 -0
- /package/dist/{session-disposers-M-oashRH.js → session-disposers-zv9OGXPB.js} +0 -0
- /package/dist/{three-dispose-D950t71B.d.ts → three-dispose-Bt1k7WKh.d.ts} +0 -0
- /package/dist/{vis-colors-D6omC64K.d.ts → vis-colors-Obw2pLqT.d.ts} +0 -0
- /package/dist/{webxr-nue-basis-CqKQmZzT.d.ts → webxr-nue-basis-3nfjDJJp.d.ts} +0 -0
- /package/dist/{xr-camera-texture-DBwCaKTd.d.ts → xr-camera-texture-Cva1q3Qj.d.ts} +0 -0
- /package/dist/{xr-error-handler-C0AQRmxs.d.ts → xr-error-handler-CtvHpjfm.d.ts} +0 -0
- /package/dist/{xr-frame-loop-BtYytZJg.d.ts → xr-frame-loop-DIYtRcUa.d.ts} +0 -0
- /package/dist/{zip-reader-DSEXt7K6.d.ts → zip-reader-D9iPQwdQ.d.ts} +0 -0
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
//#region ../src/sensors/absolute-orientation.d.ts
|
|
2
|
+
/**
|
|
3
|
+
* AbsoluteOrientationSensor capture (Generic Sensor API).
|
|
4
|
+
*
|
|
5
|
+
* Phase 1 of the AbsoluteOrientationSensor plan
|
|
6
|
+
* (GpsPlusSlamJs_Docs/docs/2026-06-25-absolute-orientation-sensor-plan.md §5.1):
|
|
7
|
+
* passive instrumentation that fuses accelerometer + gyroscope + magnetometer
|
|
8
|
+
* into an Earth-referenced (ENU) quaternion, captured per GPS event as an
|
|
9
|
+
* independent north reference. No production behaviour change.
|
|
10
|
+
*
|
|
11
|
+
* Platform: Chrome Android only. Safari / Firefox / desktop / iOS lack the
|
|
12
|
+
* sensor → this module degrades to a clean, reported no-op.
|
|
13
|
+
*
|
|
14
|
+
* The raw `'device'` reference frame is recorded together with the screen angle
|
|
15
|
+
* so either the device- or screen-compensated form can be reconstructed offline
|
|
16
|
+
* (plan §8 Q1).
|
|
17
|
+
*/
|
|
18
|
+
/** A single absolute-orientation reading, snapshotted into the GPS event payload. */
|
|
19
|
+
interface AbsoluteOrientationReading {
|
|
20
|
+
/** [x,y,z,w] quaternion mapping device-frame → Earth ENU (+X East, +Y North, +Z Up). */
|
|
21
|
+
quaternion: [number, number, number, number];
|
|
22
|
+
/** Reference frame the quaternion is expressed in. We record raw 'device'. */
|
|
23
|
+
referenceFrame: 'device' | 'screen';
|
|
24
|
+
/** screen.orientation.angle at sample time — needed to reconstruct the 'device' frame. */
|
|
25
|
+
screenAngleDeg: number;
|
|
26
|
+
/** Capture time (epoch ms) — pairs with the GPS event; lets warm-up be detected offline. */
|
|
27
|
+
timestamp: number;
|
|
28
|
+
}
|
|
29
|
+
/** Lifecycle status surfaced to the caller (HUD/observability). */
|
|
30
|
+
type AbsoluteOrientationStatus = {
|
|
31
|
+
state: 'active';
|
|
32
|
+
} | {
|
|
33
|
+
state: 'unavailable';
|
|
34
|
+
reason: string;
|
|
35
|
+
} | {
|
|
36
|
+
state: 'error';
|
|
37
|
+
reason: string;
|
|
38
|
+
};
|
|
39
|
+
/** True when the sensor can plausibly run here (secure context + API present). */
|
|
40
|
+
declare function isAbsoluteOrientationAvailable(): boolean;
|
|
41
|
+
/**
|
|
42
|
+
* Start capturing absolute orientation. Idempotent (stops any prior watch first).
|
|
43
|
+
*
|
|
44
|
+
* On platforms without the sensor — or when permissions are denied — it reports
|
|
45
|
+
* `unavailable`/`error` via `onStatus` and stays a no-op; the recorder keeps
|
|
46
|
+
* working unchanged. Never throws.
|
|
47
|
+
*/
|
|
48
|
+
declare function startAbsoluteOrientationWatch(onStatus?: (status: AbsoluteOrientationStatus) => void): Promise<void>;
|
|
49
|
+
/** Latest reading, or null when unavailable/not-yet-warmed-up. Mirrors getLastDeviceOrientation. */
|
|
50
|
+
declare function getLatestAbsoluteOrientation(): AbsoluteOrientationReading | null;
|
|
51
|
+
/** Stop the watch and clear cached state. Idempotent. */
|
|
52
|
+
declare function stopAbsoluteOrientationWatch(): void;
|
|
53
|
+
//#endregion
|
|
54
|
+
export { startAbsoluteOrientationWatch as a, isAbsoluteOrientationAvailable as i, AbsoluteOrientationStatus as n, stopAbsoluteOrientationWatch as o, getLatestAbsoluteOrientation as r, AbsoluteOrientationReading as t };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { N as CombinedRootState, r as SlamAppRootState } from "./create-slam-app-store-n_VF63D5.js";
|
|
2
2
|
import * as _$gps_plus_slam_js0 from "gps-plus-slam-js";
|
|
3
3
|
import { ArImageCapture, GpsPoint, LatLong, Matrix4, Quaternion, Vector3 } from "gps-plus-slam-js";
|
|
4
4
|
import * as _$_reduxjs_toolkit0 from "@reduxjs/toolkit";
|
package/dist/ar/bresenham3d.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { n as MAX_TRACE_STEPS, r as bresenham3d, t as GridCell } from "../bresenham3d-
|
|
1
|
+
import { n as MAX_TRACE_STEPS, r as bresenham3d, t as GridCell } from "../bresenham3d-CU1Gv2W4.js";
|
|
2
2
|
export { GridCell, MAX_TRACE_STEPS, bresenham3d };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import {
|
|
2
|
-
export { CameraBlitCapture, CameraBlitCaptureConfig, DEFAULT_BLIT_CONFIG, computeCaptureSize };
|
|
1
|
+
import { a as computeCaptureSize, i as computeAspectFitSize, n as CameraBlitCaptureConfig, r as DEFAULT_BLIT_CONFIG, t as CameraBlitCapture } from "../camera-blit-capture-NKT9H5-e.js";
|
|
2
|
+
export { CameraBlitCapture, CameraBlitCaptureConfig, DEFAULT_BLIT_CONFIG, computeAspectFitSize, computeCaptureSize };
|
|
@@ -51,6 +51,36 @@ function computeCaptureSize(cameraWidth, cameraHeight, divisor) {
|
|
|
51
51
|
};
|
|
52
52
|
}
|
|
53
53
|
/**
|
|
54
|
+
* Compute blit dimensions that PRESERVE the camera aspect ratio with the
|
|
55
|
+
* **longer edge fixed at `maxEdge`**. Unlike {@link computeCaptureSize} (which
|
|
56
|
+
* divides the native resolution by a user divisor), this fits the frame into a
|
|
57
|
+
* fixed pixel budget, so a 4:3 camera becomes e.g. 512×384 — NOT a stretched
|
|
58
|
+
* 512×512. Used by the QR-detection blit (B2) so the detector sees an
|
|
59
|
+
* undistorted code while the readback cost stays bounded by `maxEdge²`.
|
|
60
|
+
*
|
|
61
|
+
* @param cameraWidth - Native camera width in pixels (from XRCamera)
|
|
62
|
+
* @param cameraHeight - Native camera height in pixels (from XRCamera)
|
|
63
|
+
* @param maxEdge - Target length (px) of the longer output edge.
|
|
64
|
+
* @returns Integer dimensions, longer edge == `maxEdge`, aspect preserved
|
|
65
|
+
* (within rounding), each clamped to ≥ 1. When `maxEdge` itself is invalid
|
|
66
|
+
* (< 1 / NaN / Infinity) the longer edge falls back to
|
|
67
|
+
* `DEFAULT_BLIT_CONFIG.width` (still aspect-preserving). When the camera
|
|
68
|
+
* dimensions are invalid (≤ 0 / NaN / Infinity) the aspect is unknown, so it
|
|
69
|
+
* returns a square at the (possibly defaulted) edge.
|
|
70
|
+
*/
|
|
71
|
+
function computeAspectFitSize(cameraWidth, cameraHeight, maxEdge) {
|
|
72
|
+
const safeEdge = maxEdge >= 1 && Number.isFinite(maxEdge) ? Math.floor(maxEdge) : DEFAULT_BLIT_CONFIG.width;
|
|
73
|
+
if (!(cameraWidth > 0) || !Number.isFinite(cameraWidth) || !(cameraHeight > 0) || !Number.isFinite(cameraHeight)) return {
|
|
74
|
+
width: safeEdge,
|
|
75
|
+
height: safeEdge
|
|
76
|
+
};
|
|
77
|
+
const scale = safeEdge / Math.max(cameraWidth, cameraHeight);
|
|
78
|
+
return {
|
|
79
|
+
width: Math.max(1, Math.round(cameraWidth * scale)),
|
|
80
|
+
height: Math.max(1, Math.round(cameraHeight * scale))
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
/**
|
|
54
84
|
* Number of sampled pixels to check in isBlackFrame.
|
|
55
85
|
* We sample a subset rather than checking every pixel for speed.
|
|
56
86
|
*/
|
|
@@ -168,6 +198,32 @@ var CameraBlitCapture = class {
|
|
|
168
198
|
}
|
|
169
199
|
}
|
|
170
200
|
/**
|
|
201
|
+
* Capture the camera texture as **top-left-origin** RGBA — the orientation
|
|
202
|
+
* QR detection (and `BarcodeDetector`) expects — returning a FRESH copy that
|
|
203
|
+
* is safe to retain beyond the next capture.
|
|
204
|
+
*
|
|
205
|
+
* This is the efficient replacement for the demo's old JPEG round-trip: blit
|
|
206
|
+
* + readback (shared with {@link captureToBlob} / {@link captureToPixels}),
|
|
207
|
+
* then the same vertical flip the JPEG encoder applies, but with no encode →
|
|
208
|
+
* decode. Unlike {@link captureToPixels} (which returns the reusable internal
|
|
209
|
+
* buffer in WebGL bottom-row-first order), this returns an owned,
|
|
210
|
+
* correctly-oriented `Uint8ClampedArray`.
|
|
211
|
+
*
|
|
212
|
+
* IMPORTANT: Must be called within the XR animation frame callback, while the
|
|
213
|
+
* camera texture is valid.
|
|
214
|
+
*
|
|
215
|
+
* @returns `{ data, width, height }` (top-left RGBA), or null on
|
|
216
|
+
* failure/dispose.
|
|
217
|
+
*/
|
|
218
|
+
captureToRgba(renderer, cameraTexture) {
|
|
219
|
+
if (!this.captureToPixels(renderer, cameraTexture)) return null;
|
|
220
|
+
return {
|
|
221
|
+
data: this.flippedPixelCopy(),
|
|
222
|
+
width: this.width,
|
|
223
|
+
height: this.height
|
|
224
|
+
};
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
171
227
|
* Check if a pixel buffer is entirely black (all zeros).
|
|
172
228
|
* Uses sampling for performance (checks BLACK_CHECK_SAMPLE_COUNT evenly-spaced pixels).
|
|
173
229
|
*
|
|
@@ -197,10 +253,19 @@ var CameraBlitCapture = class {
|
|
|
197
253
|
return this.pixelsToJpegViaCanvas(quality);
|
|
198
254
|
}
|
|
199
255
|
getFlippedImageData() {
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
256
|
+
return new ImageData(this.flippedPixelCopy(), this.width, this.height);
|
|
257
|
+
}
|
|
258
|
+
/**
|
|
259
|
+
* Produce a FRESH, top-left-origin RGBA copy of the internal readback buffer.
|
|
260
|
+
* WebGL `readPixels` returns bottom-row-first; this copies (so the internal
|
|
261
|
+
* buffer stays y-flipped for a subsequent capture) and swaps rows. Shared by
|
|
262
|
+
* the JPEG encode path ({@link getFlippedImageData}) and {@link captureToRgba}.
|
|
263
|
+
*/
|
|
264
|
+
flippedPixelCopy() {
|
|
265
|
+
const copy = new Uint8ClampedArray(this.pixelBuffer.length);
|
|
266
|
+
copy.set(this.pixelBuffer);
|
|
267
|
+
this.flipRowsVertically(copy, this.width, this.height);
|
|
268
|
+
return copy;
|
|
204
269
|
}
|
|
205
270
|
async pixelsToJpegViaOffscreenCanvas(quality) {
|
|
206
271
|
const offscreen = new OffscreenCanvas(this.width, this.height);
|
|
@@ -229,11 +294,11 @@ var CameraBlitCapture = class {
|
|
|
229
294
|
});
|
|
230
295
|
}
|
|
231
296
|
/**
|
|
232
|
-
* Flip
|
|
233
|
-
* WebGL readPixels returns bottom-row-first; canvas
|
|
297
|
+
* Flip an RGBA buffer vertically in-place (row swap).
|
|
298
|
+
* WebGL readPixels returns bottom-row-first; canvas / detectors expect
|
|
299
|
+
* top-row-first.
|
|
234
300
|
*/
|
|
235
|
-
|
|
236
|
-
const { data, width, height } = imageData;
|
|
301
|
+
flipRowsVertically(data, width, height) {
|
|
237
302
|
const rowSize = width * 4;
|
|
238
303
|
const tempRow = new Uint8ClampedArray(rowSize);
|
|
239
304
|
for (let y = 0; y < Math.floor(height / 2); y++) {
|
|
@@ -291,4 +356,4 @@ var CameraBlitCapture = class {
|
|
|
291
356
|
}
|
|
292
357
|
};
|
|
293
358
|
//#endregion
|
|
294
|
-
export { CameraBlitCapture, DEFAULT_BLIT_CONFIG, computeCaptureSize };
|
|
359
|
+
export { CameraBlitCapture, DEFAULT_BLIT_CONFIG, computeAspectFitSize, computeCaptureSize };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { i as isFullySupported, n as CapabilitySupport, r as capabilityMessage, t as CapabilityMessageOptions } from "../capability-checker-
|
|
1
|
+
import { i as isFullySupported, n as CapabilitySupport, r as capabilityMessage, t as CapabilityMessageOptions } from "../capability-checker-DUQLg6gq.js";
|
|
2
2
|
export { CapabilityMessageOptions, CapabilitySupport, capabilityMessage, isFullySupported };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as createCaptureFailureTracker, i as DEFAULT_CAPTURE_TRACKER_CONFIG, n as CaptureFailureTracker, r as CaptureFailureTrackerConfig, t as CAPTURE_FAILURE_WARNING } from "../capture-failure-tracker-
|
|
1
|
+
import { a as createCaptureFailureTracker, i as DEFAULT_CAPTURE_TRACKER_CONFIG, n as CaptureFailureTracker, r as CaptureFailureTrackerConfig, t as CAPTURE_FAILURE_WARNING } from "../capture-failure-tracker-gsm8q7yi.js";
|
|
2
2
|
export { CAPTURE_FAILURE_WARNING, CaptureFailureTracker, CaptureFailureTrackerConfig, DEFAULT_CAPTURE_TRACKER_CONFIG, createCaptureFailureTracker };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as applyChromiumProjectionLayerWorkaround, i as ChromiumProjectionLayerWorkaroundResult, n as BASELAYER_WINDOW_MIN, o as needsBaseLayerPersistence, r as ChromeVersion, s as parseChromeVersion, t as BASELAYER_WINDOW_MAX } from "../chromium-camera-access-workaround-
|
|
1
|
+
import { a as applyChromiumProjectionLayerWorkaround, i as ChromiumProjectionLayerWorkaroundResult, n as BASELAYER_WINDOW_MIN, o as needsBaseLayerPersistence, r as ChromeVersion, s as parseChromeVersion, t as BASELAYER_WINDOW_MAX } from "../chromium-camera-access-workaround-D4K2uwwQ.js";
|
|
2
2
|
export { BASELAYER_WINDOW_MAX, BASELAYER_WINDOW_MIN, ChromeVersion, ChromiumProjectionLayerWorkaroundResult, applyChromiumProjectionLayerWorkaround, needsBaseLayerPersistence, parseChromeVersion };
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
//#region ../src/ar/depth-grid-lookup.ts
|
|
2
|
+
/** A node's depth if finite and positive, else `null` (a grid hole). */
|
|
3
|
+
function validDepth(points, index) {
|
|
4
|
+
const p = points[index];
|
|
5
|
+
if (!p) return null;
|
|
6
|
+
const d = p.depthM;
|
|
7
|
+
return Number.isFinite(d) && d > 0 ? d : null;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* Build a bilinear lookup over a depth-sampler grid.
|
|
11
|
+
*
|
|
12
|
+
* @param points - the grid `DepthPoint`s (row-major, `row·g + col`).
|
|
13
|
+
* @param gridSize - points-per-side; inferred as `round(√points.length)` when
|
|
14
|
+
* omitted (the sampler always emits a full `g²` grid).
|
|
15
|
+
*/
|
|
16
|
+
function createDepthGridLookup(points, gridSize) {
|
|
17
|
+
const g = gridSize ?? Math.round(Math.sqrt(points.length));
|
|
18
|
+
if (g < 2 || points.length < g * g) return { depthAt() {
|
|
19
|
+
for (let i = 0; i < points.length; i++) {
|
|
20
|
+
const d = validDepth(points, i);
|
|
21
|
+
if (d !== null) return d;
|
|
22
|
+
}
|
|
23
|
+
return null;
|
|
24
|
+
} };
|
|
25
|
+
return { depthAt(screenX, screenY) {
|
|
26
|
+
const gx = screenX * (g + 1) - 1;
|
|
27
|
+
const gy = screenY * (g + 1) - 1;
|
|
28
|
+
if (gx < 0 || gx > g - 1 || gy < 0 || gy > g - 1) return null;
|
|
29
|
+
const col0 = Math.min(Math.floor(gx), g - 2);
|
|
30
|
+
const row0 = Math.min(Math.floor(gy), g - 2);
|
|
31
|
+
const fx = gx - col0;
|
|
32
|
+
const fy = gy - row0;
|
|
33
|
+
const d00 = validDepth(points, row0 * g + col0);
|
|
34
|
+
const d10 = validDepth(points, row0 * g + col0 + 1);
|
|
35
|
+
const d01 = validDepth(points, (row0 + 1) * g + col0);
|
|
36
|
+
const d11 = validDepth(points, (row0 + 1) * g + col0 + 1);
|
|
37
|
+
if (d00 === null || d10 === null || d01 === null || d11 === null) return null;
|
|
38
|
+
const top = d00 + (d10 - d00) * fx;
|
|
39
|
+
return top + (d01 + (d11 - d01) * fx - top) * fy;
|
|
40
|
+
} };
|
|
41
|
+
}
|
|
42
|
+
//#endregion
|
|
43
|
+
export { createDepthGridLookup };
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { i as DepthSample } from "../ar-types-
|
|
2
|
-
import { a as wrapXRDepthInfo, i as DepthSamplerConfig, n as DepthSampler, r as DepthSamplerCallbacks, t as DepthInfo } from "../depth-sampler-
|
|
1
|
+
import { i as DepthSample } from "../ar-types-BFX2r1wk.js";
|
|
2
|
+
import { a as wrapXRDepthInfo, i as DepthSamplerConfig, n as DepthSampler, r as DepthSamplerCallbacks, t as DepthInfo } from "../depth-sampler-asc8exHt.js";
|
|
3
3
|
export { DepthInfo, DepthSample, DepthSampler, DepthSamplerCallbacks, DepthSamplerConfig, wrapXRDepthInfo };
|
package/dist/ar/depth-sampler.js
CHANGED
|
@@ -56,10 +56,8 @@ var DepthSampler = class {
|
|
|
56
56
|
unavailableCallbackFired = false;
|
|
57
57
|
constructor(callbacks, config) {
|
|
58
58
|
this.callbacks = callbacks;
|
|
59
|
-
this.config = {
|
|
60
|
-
|
|
61
|
-
...config
|
|
62
|
-
};
|
|
59
|
+
this.config = { ...DEFAULT_CONFIG };
|
|
60
|
+
if (config) this.updateConfig(config);
|
|
63
61
|
}
|
|
64
62
|
/**
|
|
65
63
|
* Start depth sampling.
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { n as createDepthUnprojector, r as unprojectDepthPoint, t as DepthUnprojector } from "../depth-unprojection-
|
|
1
|
+
import { n as createDepthUnprojector, r as unprojectDepthPoint, t as DepthUnprojector } from "../depth-unprojection-DjsbJW9L.js";
|
|
2
2
|
export { DepthUnprojector, createDepthUnprojector, unprojectDepthPoint };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as EnableGpsArState, i as EnableGpsArResult, n as EnableGpsArController, o as EnableGpsArStatus, r as EnableGpsArDeps, s as createEnableGpsArController, t as EnableGpsArConfig } from "../enable-gps-ar-
|
|
1
|
+
import { a as EnableGpsArState, i as EnableGpsArResult, n as EnableGpsArController, o as EnableGpsArStatus, r as EnableGpsArDeps, s as createEnableGpsArController, t as EnableGpsArConfig } from "../enable-gps-ar-DkNhFv4Y.js";
|
|
2
2
|
export { EnableGpsArConfig, EnableGpsArController, EnableGpsArDeps, EnableGpsArResult, EnableGpsArState, EnableGpsArStatus, createEnableGpsArController };
|
package/dist/ar/enable-gps-ar.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { createLogger } from "../utils/logger.js";
|
|
2
|
+
import { a as endARSession, b as isWebXRSupported, y as initAR } from "../webxr-session-DG-eNfny.js";
|
|
2
3
|
import { requestGeolocationPermission, requestOrientationPermission, requestWebXRWithDepthPermission } from "../sensors/permission-checker.js";
|
|
3
4
|
import { startGpsWatch, startOrientationWatch, stopGpsWatch, stopOrientationWatch } from "../sensors/gps.js";
|
|
4
|
-
import { _ as isWebXRSupported, g as initAR, i as endARSession } from "../webxr-session-TIaD883f.js";
|
|
5
5
|
//#region ../src/ar/enable-gps-ar.ts
|
|
6
6
|
const log = createLogger("EnableGpsAr");
|
|
7
7
|
const defaultDeps = {
|
|
@@ -74,10 +74,12 @@ function createEnableGpsArController(deps = {}) {
|
|
|
74
74
|
error: "AR is already starting, running or stopping."
|
|
75
75
|
};
|
|
76
76
|
setState({ status: "starting" });
|
|
77
|
+
let sessionStarted = false;
|
|
77
78
|
try {
|
|
78
79
|
const permissionError = await requestPermissions(config);
|
|
79
80
|
if (permissionError !== null) return fail(permissionError);
|
|
80
81
|
await resolved.initAR(config.container, config.isolationOptions, { requestHitTest: config.requestHitTest });
|
|
82
|
+
sessionStarted = true;
|
|
81
83
|
if (config.onGpsPosition) {
|
|
82
84
|
resolved.startGpsWatch(config.onGpsPosition);
|
|
83
85
|
gpsWatchActive = true;
|
|
@@ -89,6 +91,29 @@ function createEnableGpsArController(deps = {}) {
|
|
|
89
91
|
setState({ status: "running" });
|
|
90
92
|
return { ok: true };
|
|
91
93
|
} catch (err) {
|
|
94
|
+
if (sessionStarted) {
|
|
95
|
+
if (gpsWatchActive) {
|
|
96
|
+
try {
|
|
97
|
+
resolved.stopGpsWatch();
|
|
98
|
+
} catch (cleanupErr) {
|
|
99
|
+
log.error("stopGpsWatch during enable() cleanup threw:", cleanupErr);
|
|
100
|
+
}
|
|
101
|
+
gpsWatchActive = false;
|
|
102
|
+
}
|
|
103
|
+
if (orientationWatchActive) {
|
|
104
|
+
try {
|
|
105
|
+
resolved.stopOrientationWatch();
|
|
106
|
+
} catch (cleanupErr) {
|
|
107
|
+
log.error("stopOrientationWatch during enable() cleanup threw:", cleanupErr);
|
|
108
|
+
}
|
|
109
|
+
orientationWatchActive = false;
|
|
110
|
+
}
|
|
111
|
+
try {
|
|
112
|
+
await resolved.endARSession();
|
|
113
|
+
} catch (cleanupErr) {
|
|
114
|
+
log.error("Cleanup after enable() failure threw; continuing:", cleanupErr);
|
|
115
|
+
}
|
|
116
|
+
}
|
|
92
117
|
return fail(err instanceof Error ? err.message : String(err));
|
|
93
118
|
}
|
|
94
119
|
}
|
package/dist/ar/frame-loop.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { i as runFrameUpdates, n as clearFrameUpdates, r as registerFrameUpdate, t as FrameUpdate } from "../frame-loop-
|
|
1
|
+
import { i as runFrameUpdates, n as clearFrameUpdates, r as registerFrameUpdate, t as FrameUpdate } from "../frame-loop-CpVjQ1dH.js";
|
|
2
2
|
export { FrameUpdate, clearFrameUpdates, registerFrameUpdate, runFrameUpdates };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { a as
|
|
2
|
-
export { CapturedFrame, CapturedImage, DEFAULT_CAPTURE_CONFIG, ImageCaptureCallbacks, ImageCaptureConfig, ImageCaptureManager, MIN_VALID_IMAGE_BYTES };
|
|
1
|
+
import { a as ImageCaptureCallbacks, c as MIN_VALID_IMAGE_BYTES, i as FrameQualityVerdict, n as CapturedImage, o as ImageCaptureConfig, r as DEFAULT_CAPTURE_CONFIG, s as ImageCaptureManager, t as CapturedFrame } from "../image-capture-CNZDrQXG.js";
|
|
2
|
+
export { CapturedFrame, CapturedImage, DEFAULT_CAPTURE_CONFIG, FrameQualityVerdict, ImageCaptureCallbacks, ImageCaptureConfig, ImageCaptureManager, MIN_VALID_IMAGE_BYTES };
|
package/dist/ar/image-capture.js
CHANGED
|
@@ -1,155 +1,2 @@
|
|
|
1
|
-
import {
|
|
2
|
-
//#region ../src/ar/image-capture.ts
|
|
3
|
-
/**
|
|
4
|
-
* Image Capture Module
|
|
5
|
-
*
|
|
6
|
-
* Captures periodic JPEG screenshots from the WebGL canvas during AR recording.
|
|
7
|
-
* Uses async toBlob() for better performance (non-blocking).
|
|
8
|
-
*
|
|
9
|
-
* Includes validation to detect suspiciously small images (likely black/empty)
|
|
10
|
-
* which can occur on mobile devices when the WebGL context hasn't composited yet.
|
|
11
|
-
*/
|
|
12
|
-
const log = createLogger("ImageCapture");
|
|
13
|
-
/**
|
|
14
|
-
* Minimum expected blob size in bytes for a valid JPEG image.
|
|
15
|
-
* A black/empty 1920x1080 JPEG still compresses to ~2-3KB due to headers.
|
|
16
|
-
* A real camera frame at 0.7 quality should be 50KB+.
|
|
17
|
-
* We use a conservative threshold to catch obviously broken captures.
|
|
18
|
-
*/
|
|
19
|
-
const MIN_VALID_IMAGE_BYTES = 5e3;
|
|
20
|
-
/**
|
|
21
|
-
* Default capture configuration
|
|
22
|
-
*/
|
|
23
|
-
const DEFAULT_CAPTURE_CONFIG = {
|
|
24
|
-
intervalMs: 2e3,
|
|
25
|
-
quality: .7,
|
|
26
|
-
captureTimeoutMs: 5e3,
|
|
27
|
-
resolutionDivisor: 1
|
|
28
|
-
};
|
|
29
|
-
/**
|
|
30
|
-
* Manages periodic image capture from a canvas.
|
|
31
|
-
*
|
|
32
|
-
* Usage:
|
|
33
|
-
* 1. Create with canvas and callbacks
|
|
34
|
-
* 2. Call start() when recording begins
|
|
35
|
-
* 3. Call onFrame(time) each XR frame
|
|
36
|
-
* 4. Call stop() when recording ends
|
|
37
|
-
*/
|
|
38
|
-
var ImageCaptureManager = class {
|
|
39
|
-
canvas;
|
|
40
|
-
callbacks;
|
|
41
|
-
config;
|
|
42
|
-
capturing = false;
|
|
43
|
-
lastCaptureTime = 0;
|
|
44
|
-
frameCount = 0;
|
|
45
|
-
captureInProgress = false;
|
|
46
|
-
captureTimeoutId = null;
|
|
47
|
-
constructor(canvas, callbacks, config = DEFAULT_CAPTURE_CONFIG) {
|
|
48
|
-
this.canvas = canvas;
|
|
49
|
-
this.callbacks = callbacks;
|
|
50
|
-
this.config = config;
|
|
51
|
-
}
|
|
52
|
-
/**
|
|
53
|
-
* Start capturing images.
|
|
54
|
-
* Resets frame counter and last capture time.
|
|
55
|
-
*/
|
|
56
|
-
start() {
|
|
57
|
-
this.capturing = true;
|
|
58
|
-
this.lastCaptureTime = 0;
|
|
59
|
-
this.frameCount = 0;
|
|
60
|
-
}
|
|
61
|
-
/**
|
|
62
|
-
* Stop capturing images.
|
|
63
|
-
* Clears any pending safety timeout and resets in-flight capture state.
|
|
64
|
-
*/
|
|
65
|
-
stop() {
|
|
66
|
-
this.capturing = false;
|
|
67
|
-
this.clearCaptureTimeout();
|
|
68
|
-
this.captureInProgress = false;
|
|
69
|
-
}
|
|
70
|
-
/**
|
|
71
|
-
* Check if capture manager is active.
|
|
72
|
-
*/
|
|
73
|
-
isCapturing() {
|
|
74
|
-
return this.capturing;
|
|
75
|
-
}
|
|
76
|
-
/**
|
|
77
|
-
* Get the current frame count.
|
|
78
|
-
*/
|
|
79
|
-
getFrameCount() {
|
|
80
|
-
return this.frameCount;
|
|
81
|
-
}
|
|
82
|
-
/**
|
|
83
|
-
* Called each XR frame to check if a capture is needed.
|
|
84
|
-
*
|
|
85
|
-
* @param time - Frame timestamp in milliseconds (from requestAnimationFrame)
|
|
86
|
-
*/
|
|
87
|
-
onFrame(time) {
|
|
88
|
-
if (!this.capturing) return;
|
|
89
|
-
if (this.captureInProgress) return;
|
|
90
|
-
const elapsed = time - this.lastCaptureTime;
|
|
91
|
-
if (this.lastCaptureTime > 0 && elapsed < this.config.intervalMs) return;
|
|
92
|
-
const pose = this.callbacks.getCurrentPose();
|
|
93
|
-
if (!pose) return;
|
|
94
|
-
this.captureInProgress = true;
|
|
95
|
-
this.lastCaptureTime = time;
|
|
96
|
-
const timestamp = performance.timeOrigin + time;
|
|
97
|
-
const screenRotation = this.callbacks.getScreenRotation();
|
|
98
|
-
const frameIndex = ++this.frameCount;
|
|
99
|
-
this.captureTimeoutId = setTimeout(() => {
|
|
100
|
-
if (this.captureInProgress) {
|
|
101
|
-
log.error(`Capture timeout after ${this.config.captureTimeoutMs}ms — force-resetting captureInProgress`);
|
|
102
|
-
this.captureInProgress = false;
|
|
103
|
-
this.captureTimeoutId = null;
|
|
104
|
-
}
|
|
105
|
-
}, this.config.captureTimeoutMs);
|
|
106
|
-
if (this.callbacks.captureFrame) this.callbacks.captureFrame(this.config.quality).then((frame) => {
|
|
107
|
-
this.handleCapturedBlob(frame?.blob ?? null, frame?.width, frame?.height, timestamp, frameIndex, pose, screenRotation);
|
|
108
|
-
}).catch(() => {
|
|
109
|
-
this.clearCaptureTimeout();
|
|
110
|
-
this.captureInProgress = false;
|
|
111
|
-
this.callbacks.onCaptureFailed?.();
|
|
112
|
-
});
|
|
113
|
-
else this.canvas.toBlob((blob) => {
|
|
114
|
-
this.handleCapturedBlob(blob, this.canvas.width, this.canvas.height, timestamp, frameIndex, pose, screenRotation);
|
|
115
|
-
}, "image/jpeg", this.config.quality);
|
|
116
|
-
}
|
|
117
|
-
/**
|
|
118
|
-
* Clear the safety timeout for captureInProgress.
|
|
119
|
-
* Called when capture completes (success or failure) before the timeout fires.
|
|
120
|
-
*/
|
|
121
|
-
clearCaptureTimeout() {
|
|
122
|
-
if (this.captureTimeoutId !== null) {
|
|
123
|
-
clearTimeout(this.captureTimeoutId);
|
|
124
|
-
this.captureTimeoutId = null;
|
|
125
|
-
}
|
|
126
|
-
}
|
|
127
|
-
/**
|
|
128
|
-
* Common handler for captured blobs (from either canvas.toBlob or captureFrame).
|
|
129
|
-
* Handles null blobs, suspicious image detection, and dispatching onCaptured.
|
|
130
|
-
*/
|
|
131
|
-
handleCapturedBlob(blob, width, height, timestamp, frameIndex, pose, screenRotation) {
|
|
132
|
-
this.clearCaptureTimeout();
|
|
133
|
-
this.captureInProgress = false;
|
|
134
|
-
if (!blob) {
|
|
135
|
-
this.callbacks.onCaptureFailed?.();
|
|
136
|
-
return;
|
|
137
|
-
}
|
|
138
|
-
if (blob.size < 5e3) {
|
|
139
|
-
log.error(`Suspicious image at frame ${frameIndex}: blob size ${blob.size} bytes is below minimum ${MIN_VALID_IMAGE_BYTES} bytes. Image may be black/empty.`);
|
|
140
|
-
this.callbacks.onSuspiciousImage?.(blob.size, frameIndex);
|
|
141
|
-
}
|
|
142
|
-
this.callbacks.onCaptured({
|
|
143
|
-
blob,
|
|
144
|
-
timestamp,
|
|
145
|
-
frameIndex,
|
|
146
|
-
position: pose.position,
|
|
147
|
-
rotation: pose.orientation,
|
|
148
|
-
screenRotation,
|
|
149
|
-
...width && width > 0 ? { width } : {},
|
|
150
|
-
...height && height > 0 ? { height } : {}
|
|
151
|
-
});
|
|
152
|
-
}
|
|
153
|
-
};
|
|
154
|
-
//#endregion
|
|
1
|
+
import { n as ImageCaptureManager, r as MIN_VALID_IMAGE_BYTES, t as DEFAULT_CAPTURE_CONFIG } from "../image-capture-B2-b6tKK.js";
|
|
155
2
|
export { DEFAULT_CAPTURE_CONFIG, ImageCaptureManager, MIN_VALID_IMAGE_BYTES };
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import { a as QualityFilterConfig, c as meanLuminance, i as ImageQualityGate, l as rgbaToGrayscale, n as DEFAULT_SHARPNESS_HISTORY_SIZE, o as QualityRejectReason, r as DEFAULT_SHARPNESS_MIN_SAMPLES, s as QualityVerdict, t as DEFAULT_QUALITY_FILTER, u as sharpnessScore } from "../image-quality-smCBoFj1.js";
|
|
2
|
+
export { DEFAULT_QUALITY_FILTER, DEFAULT_SHARPNESS_HISTORY_SIZE, DEFAULT_SHARPNESS_MIN_SAMPLES, ImageQualityGate, QualityFilterConfig, QualityRejectReason, QualityVerdict, meanLuminance, rgbaToGrayscale, sharpnessScore };
|