@splnlss/3d-story-viewer 0.8.3 → 0.8.5
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/README.md +45 -1
- package/build/{main-CEG3MR57.js → main-DCLbtFn7.js} +1247 -476
- package/build/main-DXC7nIw_.cjs +1 -0
- package/build/spark.module-BPiIta4L.cjs +1 -0
- package/build/{spark.module-CHPihKhu.js → spark.module-SbwV3up9.js} +235 -13
- package/build/types/src/main.d.ts +11 -1
- package/build/types/src/viewer/ContentLayer/ContentLayerRegistry.d.ts +31 -0
- package/build/types/src/viewer/ContentLayer/GeojsonLayer.d.ts +1 -0
- package/build/types/src/viewer/ContentLayer/MeshLayer.d.ts +4 -1
- package/build/types/src/viewer/ContentLayer/TilesLayer.d.ts +1 -0
- package/build/types/src/viewer/ContentLayer/gaussianSplatUtils.d.ts +6 -0
- package/build/types/src/viewer/DesktopLookControls.d.ts +22 -0
- package/build/types/src/viewer/GlobeManager.d.ts +4 -1
- package/build/types/src/viewer/SplatDestinationPrefetch.d.ts +18 -0
- package/build/types/src/viewer/WebXRSession.d.ts +2 -2
- package/build/types/src/viewer/XRDiagnosticsPanel.d.ts +14 -0
- package/build/types/src/viewer/XRRenderBridge.d.ts +3 -4
- package/build/types/src/viewer/index.d.ts +135 -7
- package/build/types/src/viewer/loadingDiagnostics.d.ts +10 -0
- package/build/types/src/workers/WorkerPool.d.ts +9 -3
- package/build/viewer.cjs +1 -1
- package/build/viewer.js +1 -1
- package/package.json +1 -1
- package/build/main-DOWS9MQ7.cjs +0 -1
- package/build/spark.module-CsQUyNT4.cjs +0 -1
|
@@ -1,7 +1,14 @@
|
|
|
1
1
|
var __defProp = Object.defineProperty;
|
|
2
|
+
var __typeError = (msg) => {
|
|
3
|
+
throw TypeError(msg);
|
|
4
|
+
};
|
|
2
5
|
var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
|
|
3
6
|
var __publicField = (obj, key, value) => __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
|
|
4
|
-
var
|
|
7
|
+
var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
|
|
8
|
+
var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
|
|
9
|
+
var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
|
|
10
|
+
var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), setter ? setter.call(obj, value) : member.set(obj, value), value);
|
|
11
|
+
var _a2, _destinationTileTimeout;
|
|
5
12
|
import { S as ShaderChunk, M as Matrix4, V as Vector3, O as Object3D, a as Vector2, b as Mesh, P as PlaneGeometry, c as ShaderMaterial, R as Ray, E as EventDispatcher$1, d as Plane, e as Raycaster, C as Clock, Q as Quaternion, f as MathUtils, T as TrianglesDrawMode, g as TriangleFanDrawMode, h as TriangleStripDrawMode, L as Loader, i as LoaderUtils, F as FileLoader, j as MeshPhysicalMaterial, k as Color, l as LinearSRGBColorSpace, m as SRGBColorSpace, n as SpotLight, o as PointLight, D as DirectionalLight, I as InstancedMesh, p as InstancedBufferAttribute, B as BufferGeometry, q as TextureLoader, r as ImageBitmapLoader, s as BufferAttribute, t as InterleavedBuffer, u as LinearMipmapLinearFilter, N as NearestMipmapLinearFilter, v as LinearMipmapNearestFilter, w as NearestMipmapNearestFilter, x as LinearFilter, y as NearestFilter, z as RepeatWrapping, A as MirroredRepeatWrapping, G as ClampToEdgeWrapping, H as PointsMaterial, J as Material, K as LineBasicMaterial, U as MeshStandardMaterial, W as DoubleSide, X as MeshBasicMaterial, Y as PropertyBinding, Z as SkinnedMesh, _ as LineSegments, $ as Line, a0 as LineLoop, a1 as Points, a2 as Group$1, a3 as PerspectiveCamera, a4 as OrthographicCamera, a5 as Skeleton, a6 as AnimationClip, a7 as Bone, a8 as InterpolateDiscrete, a9 as InterpolateLinear, aa as InterleavedBufferAttribute, ab as Texture, ac as VectorKeyframeTrack, ad as NumberKeyframeTrack, ae as QuaternionKeyframeTrack, af as ColorManagement, ag as FrontSide, ah as Interpolant, ai as Box3, aj as Sphere, ak as Euler, al as Spherical, am as LoadingManager, an as Frustum, ao as DefaultLoadingManager, ap as Matrix3, aq as TextureUtils, ar as CompressedCubeTexture, as as CompressedArrayTexture, at as CompressedTexture, au as NoColorSpace, av as RGBA_PVRTC_2BPPV1_Format, aw as RGBA_PVRTC_4BPPV1_Format, ax as RGBA_BPTC_Format, ay as RED_GREEN_RGTC2_Format, az as SIGNED_RED_GREEN_RGTC2_Format, aA as RED_RGTC1_Format, aB as SIGNED_RED_RGTC1_Format, aC as RGBA_S3TC_DXT5_Format, aD as RGB_S3TC_DXT1_Format, aE as RGBA_S3TC_DXT1_Format, aF as RGBA_ASTC_6x6_Format, aG as RGBA_ASTC_4x4_Format, aH as SIGNED_RG11_EAC_Format, aI as RG11_EAC_Format, aJ as SIGNED_R11_EAC_Format, aK as R11_EAC_Format, aL as RGB_ETC2_Format, aM as RGBA_ETC2_EAC_Format, aN as RGBFormat, aO as RedFormat, aP as RGFormat, aQ as RGBAFormat, aR as UnsignedByteType, aS as HalfFloatType, aT as UnsignedInt101111Type, aU as UnsignedInt5999Type, aV as UnsignedShortType, aW as FloatType, aX as DataTexture, aY as Data3DTexture, aZ as RGB_PVRTC_4BPPV1_Format, a_ as RGB_ETC1_Format, a$ as RGB_BPTC_UNSIGNED_Format, b0 as REVISION, b1 as TextureSource, b2 as ImageUtils, b3 as Scene, b4 as ecefToGeodeticPosition, b5 as getEnuBasis, b6 as Float32BufferAttribute, b7 as LinearMipMapLinearFilter, b8 as Triangle, b9 as CanvasTexture, ba as WebGLRenderer, bb as WebGLRenderTarget, bc as OneFactor, bd as ZeroFactor, be as CustomBlending, bf as Box2, bg as Matrix2, bh as Vector4, bi as validateGeodeticPosition, bj as validateRotation, bk as geodeticToEcefPosition, bl as DataTextureLoader, bm as DataUtils, bn as BackSide, bo as BoxGeometry, bp as normalizeLayerOffset, bq as geodeticOffsetToEcefDelta, br as validateTuple, bs as validateScale, bt as enuToEcefDelta, bu as RingGeometry, bv as AgXToneMapping, bw as EquirectangularReflectionMapping, bx as requireFiniteNumber } from "./index-a8PLKOvo.js";
|
|
6
13
|
var bayer_dither_hash_pars_default$1 = "#ifdef USE_HASH\nuniform float hashOpacity;varying float vCameraDistance;float bayerDitherPattern(vec2 p){float bayerMatrix[16];bayerMatrix[0]=0.0;bayerMatrix[1]=8.0;bayerMatrix[2]=2.0;bayerMatrix[3]=10.0;bayerMatrix[4]=12.0;bayerMatrix[5]=4.0;bayerMatrix[6]=14.0;bayerMatrix[7]=6.0;bayerMatrix[8]=3.0;bayerMatrix[9]=11.0;bayerMatrix[10]=1.0;bayerMatrix[11]=9.0;bayerMatrix[12]=15.0;bayerMatrix[13]=7.0;bayerMatrix[14]=13.0;bayerMatrix[15]=5.0;int x=int(mod(p.x,4.0));int y=int(mod(p.y,4.0));int index=x+y*4;return bayerMatrix[index]/16.0;}\n#endif\n";
|
|
7
14
|
var bayer_dither_hash_default$1 = "#ifdef USE_HASH\nfloat hashAmount=smoothstep(5e4,1e2,vCameraDistance)*0.75+0.1;float ditherValue=bayerDitherPattern(gl_FragCoord.xy);if(hashAmount<ditherValue){discard;}\n#endif\n";
|
|
@@ -156,7 +163,7 @@ class CSS2DRenderer {
|
|
|
156
163
|
}
|
|
157
164
|
let sparkPromise = null;
|
|
158
165
|
function loadSpark() {
|
|
159
|
-
sparkPromise ?? (sparkPromise = import("./spark.module-
|
|
166
|
+
sparkPromise ?? (sparkPromise = import("./spark.module-SbwV3up9.js").catch((error) => {
|
|
160
167
|
sparkPromise = null;
|
|
161
168
|
throw error;
|
|
162
169
|
}));
|
|
@@ -6177,7 +6184,7 @@ class GlobeControls extends EnvironmentControls {
|
|
|
6177
6184
|
}
|
|
6178
6185
|
}
|
|
6179
6186
|
_updateRotation(...args) {
|
|
6180
|
-
if (this._rotationMode === 1 || this._isNearControls()) {
|
|
6187
|
+
if (this._rotationMode === 1 || this._isNearControls() || this.rotationSpeed !== 0 && this.pointerTracker.getPointerType() === "mouse" && this.pointerTracker.isRightClicked()) {
|
|
6181
6188
|
this._rotationMode = 1;
|
|
6182
6189
|
super._updateRotation(...args);
|
|
6183
6190
|
} else {
|
|
@@ -7711,11 +7718,10 @@ class TileDecoders {
|
|
|
7711
7718
|
this.disposed = false;
|
|
7712
7719
|
}
|
|
7713
7720
|
getDraco() {
|
|
7714
|
-
var _a3, _b2;
|
|
7715
7721
|
if (this.disposed) throw new Error("Tile decoders disposed");
|
|
7716
7722
|
if (!this.draco) {
|
|
7717
7723
|
const loader = new DRACOLoader();
|
|
7718
|
-
|
|
7724
|
+
loader.decoderConfig.type = "js";
|
|
7719
7725
|
this.draco = managedLoader(loader, "_initDecoder", "decodeGeometry", "decoderPending");
|
|
7720
7726
|
}
|
|
7721
7727
|
return this.draco;
|
|
@@ -13195,14 +13201,15 @@ function applyGrayscale(material) {
|
|
|
13195
13201
|
class GlobeManager extends EventDispatcher {
|
|
13196
13202
|
constructor(scene, camera, renderer, options = {}) {
|
|
13197
13203
|
super();
|
|
13204
|
+
__privateAdd(this, _destinationTileTimeout, null);
|
|
13198
13205
|
this.scene = scene;
|
|
13199
13206
|
this.camera = camera;
|
|
13200
13207
|
this.renderer = renderer;
|
|
13201
13208
|
this.tiles = null;
|
|
13202
13209
|
this.destinationTileCamera = null;
|
|
13203
13210
|
this.destinationTileResolution = 0;
|
|
13204
|
-
this.destinationTileTimeout = null;
|
|
13205
13211
|
this.previousAutoDisableRendererCulling = null;
|
|
13212
|
+
this.parseQueueTimer = null;
|
|
13206
13213
|
this.dracoLoader = null;
|
|
13207
13214
|
this.ownsDecoders = !options.decoders;
|
|
13208
13215
|
this.decoders = options.decoders ?? new TileDecoders(renderer);
|
|
@@ -13213,6 +13220,7 @@ class GlobeManager extends EventDispatcher {
|
|
|
13213
13220
|
}
|
|
13214
13221
|
}
|
|
13215
13222
|
initTiles() {
|
|
13223
|
+
this.stopParseQueuePump();
|
|
13216
13224
|
if (this.tiles) {
|
|
13217
13225
|
this.setDestinationTilePrefetch(null);
|
|
13218
13226
|
this.scene.remove(this.tiles.group);
|
|
@@ -13236,6 +13244,19 @@ class GlobeManager extends EventDispatcher {
|
|
|
13236
13244
|
this.scene.add(this.tiles.group);
|
|
13237
13245
|
updateTilesCamera(this.tiles, this.camera, this.renderer);
|
|
13238
13246
|
this.attachTileLoadListener();
|
|
13247
|
+
this.startParseQueuePump();
|
|
13248
|
+
}
|
|
13249
|
+
startParseQueuePump() {
|
|
13250
|
+
this.stopParseQueuePump();
|
|
13251
|
+
this.parseQueueTimer = setInterval(() => {
|
|
13252
|
+
var _a3;
|
|
13253
|
+
const queue = (_a3 = this.tiles) == null ? void 0 : _a3.parseQueue;
|
|
13254
|
+
if ((queue == null ? void 0 : queue.items.length) > 0 && queue.currJobs < queue.maxJobs) queue.tryRunJobs();
|
|
13255
|
+
}, 100);
|
|
13256
|
+
}
|
|
13257
|
+
stopParseQueuePump() {
|
|
13258
|
+
if (this.parseQueueTimer !== null) clearInterval(this.parseQueueTimer);
|
|
13259
|
+
this.parseQueueTimer = null;
|
|
13239
13260
|
}
|
|
13240
13261
|
attachTileLoadListener() {
|
|
13241
13262
|
this.tiles.addEventListener("load-model", ({ scene }) => {
|
|
@@ -13252,6 +13273,8 @@ class GlobeManager extends EventDispatcher {
|
|
|
13252
13273
|
}
|
|
13253
13274
|
/** The renderer shares one cache and request scheduler between both registered cameras. */
|
|
13254
13275
|
setDestinationTilePrefetch(target) {
|
|
13276
|
+
const timeoutMs = (target == null ? void 0 : target.timeoutMs) ?? 12e3;
|
|
13277
|
+
if (target && (!Number.isFinite(timeoutMs) || timeoutMs <= 0 || timeoutMs > 3e4)) return;
|
|
13255
13278
|
this.clearDestinationTilePrefetch();
|
|
13256
13279
|
if (!target || !this.tiles) return;
|
|
13257
13280
|
let position;
|
|
@@ -13275,7 +13298,7 @@ class GlobeManager extends EventDispatcher {
|
|
|
13275
13298
|
this.destinationTileResolution = target.resolutionPixels;
|
|
13276
13299
|
this.tiles.setCamera(camera);
|
|
13277
13300
|
this.updateDestinationTileResolution();
|
|
13278
|
-
this
|
|
13301
|
+
__privateSet(this, _destinationTileTimeout, setTimeout(() => this.clearDestinationTilePrefetch(), timeoutMs));
|
|
13279
13302
|
}
|
|
13280
13303
|
updateDestinationTileResolution() {
|
|
13281
13304
|
var _a3, _b2;
|
|
@@ -13287,8 +13310,8 @@ class GlobeManager extends EventDispatcher {
|
|
|
13287
13310
|
this.tiles.setResolution(this.destinationTileCamera, pixels, pixels);
|
|
13288
13311
|
}
|
|
13289
13312
|
clearDestinationTilePrefetch() {
|
|
13290
|
-
if (this
|
|
13291
|
-
this
|
|
13313
|
+
if (__privateGet(this, _destinationTileTimeout) !== null) clearTimeout(__privateGet(this, _destinationTileTimeout));
|
|
13314
|
+
__privateSet(this, _destinationTileTimeout, null);
|
|
13292
13315
|
if (this.destinationTileCamera && this.tiles) {
|
|
13293
13316
|
this.tiles.deleteCamera(this.destinationTileCamera);
|
|
13294
13317
|
this.tiles.autoDisableRendererCulling = this.previousAutoDisableRendererCulling;
|
|
@@ -13299,12 +13322,15 @@ class GlobeManager extends EventDispatcher {
|
|
|
13299
13322
|
}
|
|
13300
13323
|
update() {
|
|
13301
13324
|
if (!this.tiles) return;
|
|
13325
|
+
const parseQueue = this.tiles.parseQueue;
|
|
13326
|
+
if ((parseQueue == null ? void 0 : parseQueue.items.length) > 0 && parseQueue.currJobs < parseQueue.maxJobs) parseQueue.tryRunJobs();
|
|
13302
13327
|
updateTilesCamera(this.tiles, this.camera, this.renderer);
|
|
13303
13328
|
this.updateDestinationTileResolution();
|
|
13304
13329
|
this.tiles.errorTarget = 20;
|
|
13305
13330
|
this.tiles.update();
|
|
13306
13331
|
}
|
|
13307
13332
|
dispose() {
|
|
13333
|
+
this.stopParseQueuePump();
|
|
13308
13334
|
this.clearDestinationTilePrefetch();
|
|
13309
13335
|
if (this.tiles) {
|
|
13310
13336
|
this.scene.remove(this.tiles.group);
|
|
@@ -13315,6 +13341,7 @@ class GlobeManager extends EventDispatcher {
|
|
|
13315
13341
|
this.listeners = {};
|
|
13316
13342
|
}
|
|
13317
13343
|
}
|
|
13344
|
+
_destinationTileTimeout = new WeakMap();
|
|
13318
13345
|
var Easing = Object.freeze({
|
|
13319
13346
|
Linear: Object.freeze({
|
|
13320
13347
|
None: function(amount) {
|
|
@@ -14367,86 +14394,32 @@ function RGBEPromise(url, options = {}) {
|
|
|
14367
14394
|
);
|
|
14368
14395
|
});
|
|
14369
14396
|
}
|
|
14370
|
-
|
|
14371
|
-
|
|
14372
|
-
var
|
|
14373
|
-
|
|
14374
|
-
|
|
14375
|
-
|
|
14376
|
-
|
|
14377
|
-
|
|
14378
|
-
|
|
14379
|
-
|
|
14380
|
-
|
|
14381
|
-
|
|
14382
|
-
|
|
14383
|
-
|
|
14384
|
-
|
|
14385
|
-
|
|
14386
|
-
|
|
14387
|
-
|
|
14388
|
-
|
|
14389
|
-
|
|
14390
|
-
|
|
14391
|
-
|
|
14392
|
-
|
|
14393
|
-
|
|
14394
|
-
|
|
14395
|
-
var k2 = (performance || Date).now(), g2 = k2, a2 = 0, r2 = e(new f2.Panel("FPS", "#0ff", "#002")), h2 = e(new f2.Panel("MS", "#0f0", "#020"));
|
|
14396
|
-
if (self.performance && self.performance.memory) var t2 = e(new f2.Panel("MB", "#f08", "#201"));
|
|
14397
|
-
u2(0);
|
|
14398
|
-
return { REVISION: 16, dom: c3, addPanel: e, showPanel: u2, begin: function() {
|
|
14399
|
-
k2 = (performance || Date).now();
|
|
14400
|
-
}, end: function() {
|
|
14401
|
-
a2++;
|
|
14402
|
-
var c4 = (performance || Date).now();
|
|
14403
|
-
h2.update(c4 - k2, 200);
|
|
14404
|
-
if (c4 > g2 + 1e3 && (r2.update(1e3 * a2 / (c4 - g2), 100), g2 = c4, a2 = 0, t2)) {
|
|
14405
|
-
var d2 = performance.memory;
|
|
14406
|
-
t2.update(d2.usedJSHeapSize / 1048576, d2.jsHeapSizeLimit / 1048576);
|
|
14407
|
-
}
|
|
14408
|
-
return c4;
|
|
14409
|
-
}, update: function() {
|
|
14410
|
-
k2 = this.end();
|
|
14411
|
-
}, domElement: c3, setMode: u2 };
|
|
14412
|
-
};
|
|
14413
|
-
f2.Panel = function(e, f3, l3) {
|
|
14414
|
-
var c3 = Infinity, k2 = 0, g2 = Math.round, a2 = g2(window.devicePixelRatio || 1), r2 = 80 * a2, h2 = 48 * a2, t2 = 3 * a2, v2 = 2 * a2, d2 = 3 * a2, m2 = 15 * a2, n2 = 74 * a2, p2 = 30 * a2, q2 = document.createElement("canvas");
|
|
14415
|
-
q2.width = r2;
|
|
14416
|
-
q2.height = h2;
|
|
14417
|
-
q2.style.cssText = "width:80px;height:48px";
|
|
14418
|
-
var b2 = q2.getContext("2d");
|
|
14419
|
-
b2.font = "bold " + 9 * a2 + "px Helvetica,Arial,sans-serif";
|
|
14420
|
-
b2.textBaseline = "top";
|
|
14421
|
-
b2.fillStyle = l3;
|
|
14422
|
-
b2.fillRect(0, 0, r2, h2);
|
|
14423
|
-
b2.fillStyle = f3;
|
|
14424
|
-
b2.fillText(e, t2, v2);
|
|
14425
|
-
b2.fillRect(d2, m2, n2, p2);
|
|
14426
|
-
b2.fillStyle = l3;
|
|
14427
|
-
b2.globalAlpha = 0.9;
|
|
14428
|
-
b2.fillRect(d2, m2, n2, p2);
|
|
14429
|
-
return { dom: q2, update: function(h3, w2) {
|
|
14430
|
-
c3 = Math.min(c3, h3);
|
|
14431
|
-
k2 = Math.max(k2, h3);
|
|
14432
|
-
b2.fillStyle = l3;
|
|
14433
|
-
b2.globalAlpha = 1;
|
|
14434
|
-
b2.fillRect(0, 0, r2, m2);
|
|
14435
|
-
b2.fillStyle = f3;
|
|
14436
|
-
b2.fillText(g2(h3) + " " + e + " (" + g2(c3) + "-" + g2(k2) + ")", t2, v2);
|
|
14437
|
-
b2.drawImage(q2, d2 + a2, m2, n2 - a2, p2, d2, m2, n2 - a2, p2);
|
|
14438
|
-
b2.fillRect(d2 + n2 - a2, m2, a2, p2);
|
|
14439
|
-
b2.fillStyle = l3;
|
|
14440
|
-
b2.globalAlpha = 0.9;
|
|
14441
|
-
b2.fillRect(d2 + n2 - a2, m2, a2, g2((1 - h3 / w2) * p2));
|
|
14442
|
-
} };
|
|
14443
|
-
};
|
|
14444
|
-
return f2;
|
|
14445
|
-
});
|
|
14446
|
-
})(stats_min$1);
|
|
14447
|
-
return stats_min$1.exports;
|
|
14397
|
+
const finite = (value) => typeof value === "number" && Number.isFinite(value) ? value : null;
|
|
14398
|
+
function readLoadingDiagnostics(viewer) {
|
|
14399
|
+
var _a3, _b2, _c, _d, _e, _f, _g, _h;
|
|
14400
|
+
const tiles = (_b2 = (_a3 = viewer.globeManager) == null ? void 0 : _a3.tiles) == null ? void 0 : _b2.stats;
|
|
14401
|
+
const pager = (_c = viewer.sparkRenderer) == null ? void 0 : _c.pager;
|
|
14402
|
+
const pendingTiles = tiles && [tiles.queued, tiles.downloading, tiles.parsing].map(finite);
|
|
14403
|
+
let pendingRad = null;
|
|
14404
|
+
if (pager && [pager.fetchPriority, pager.fetchers, pager.fetched].every(Array.isArray)) {
|
|
14405
|
+
const pending = /* @__PURE__ */ new Map();
|
|
14406
|
+
for (const { splats, chunk } of [...pager.fetchPriority, ...pager.fetchers, ...pager.fetched]) {
|
|
14407
|
+
if (!splats || !Number.isInteger(chunk) || ((_d = pager.getSplatsChunk) == null ? void 0 : _d.call(pager, splats, chunk))) continue;
|
|
14408
|
+
if (!pending.has(splats)) pending.set(splats, /* @__PURE__ */ new Set());
|
|
14409
|
+
pending.get(splats).add(chunk);
|
|
14410
|
+
}
|
|
14411
|
+
pendingRad = [...pending.values()].reduce((sum, chunks) => sum + chunks.size, 0);
|
|
14412
|
+
}
|
|
14413
|
+
return {
|
|
14414
|
+
fps: finite(viewer.diagnosticFps),
|
|
14415
|
+
tilesVisible: finite(tiles == null ? void 0 : tiles.visible),
|
|
14416
|
+
tilesPending: (pendingTiles == null ? void 0 : pendingTiles.every((value) => value !== null)) ? pendingTiles.reduce((sum, value) => sum + value, 0) : null,
|
|
14417
|
+
tilesFailed: finite(tiles == null ? void 0 : tiles.failed),
|
|
14418
|
+
radPages: finite((_e = pager == null ? void 0 : pager.pageLru) == null ? void 0 : _e.size),
|
|
14419
|
+
radPending: pendingRad,
|
|
14420
|
+
gpuTextures: finite((_h = (_g = (_f = viewer.renderer) == null ? void 0 : _f.info) == null ? void 0 : _g.memory) == null ? void 0 : _h.textures)
|
|
14421
|
+
};
|
|
14448
14422
|
}
|
|
14449
|
-
requireStats_min();
|
|
14450
14423
|
function computeUpVector(position, target) {
|
|
14451
14424
|
const forward = new Vector3().subVectors(target, position).normalize();
|
|
14452
14425
|
const referenceUp = position.clone().normalize();
|
|
@@ -14615,6 +14588,7 @@ class TilesLayer extends ContentLayer {
|
|
|
14615
14588
|
super();
|
|
14616
14589
|
this.type = "TilesLayer";
|
|
14617
14590
|
this.isTilesLayer = true;
|
|
14591
|
+
this.disposed = false;
|
|
14618
14592
|
const renderOrder = (options == null ? void 0 : options.renderOrder) ?? 0;
|
|
14619
14593
|
const implicit = (options == null ? void 0 : options.implicit) ?? false;
|
|
14620
14594
|
const overlayMode = (options == null ? void 0 : options.blendeMode) == "overlay" ? true : false;
|
|
@@ -14654,6 +14628,7 @@ class TilesLayer extends ContentLayer {
|
|
|
14654
14628
|
updateTilesCamera(tiles, this.camera, this.renderer);
|
|
14655
14629
|
tiles.addEventListener("load-model", (event) => {
|
|
14656
14630
|
var _a3;
|
|
14631
|
+
if (this.disposed) return;
|
|
14657
14632
|
if (hasOffset && !offsetApplied) {
|
|
14658
14633
|
try {
|
|
14659
14634
|
const bounds = new Sphere();
|
|
@@ -14707,6 +14682,8 @@ class TilesLayer extends ContentLayer {
|
|
|
14707
14682
|
}
|
|
14708
14683
|
}
|
|
14709
14684
|
dispose() {
|
|
14685
|
+
if (this.disposed) return;
|
|
14686
|
+
this.disposed = true;
|
|
14710
14687
|
super.dispose();
|
|
14711
14688
|
if (this.tiles) {
|
|
14712
14689
|
this.tiles.dispose();
|
|
@@ -14716,23 +14693,392 @@ class TilesLayer extends ContentLayer {
|
|
|
14716
14693
|
if (this.ownsDecoders) this.decoders.dispose();
|
|
14717
14694
|
}
|
|
14718
14695
|
}
|
|
14696
|
+
var MeshoptDecoder = function() {
|
|
14697
|
+
var wasm_base = "b9H79Tebbbe8Fv9Gbb9Gvuuuuueu9Giuuub9Geueu9Giuuueuixkbeeeddddillviebeoweuecj:Gdkr;Neqo9TW9T9VV95dbH9F9F939H79T9F9J9H229F9Jt9VV7bb8A9TW79O9V9Wt9F9KW9J9V9KW9wWVtW949c919M9MWVbeY9TW79O9V9Wt9F9KW9J9V9KW69U9KW949c919M9MWVbdE9TW79O9V9Wt9F9KW9J9V9KW69U9KW949tWG91W9U9JWbiL9TW79O9V9Wt9F9KW9J9V9KWS9P2tWV9p9JtblK9TW79O9V9Wt9F9KW9J9V9KWS9P2tWV9r919HtbvL9TW79O9V9Wt9F9KW9J9V9KWS9P2tWVT949WboY9TW79O9V9Wt9F9KW9J9V9KWS9P2tWVJ9V29VVbrl79IV9Rbwq:VZkdbk:XYi5ud9:du8Jjjjjbcj;kb9Rgv8Kjjjjbc9:hodnalTmbcuhoaiRbbgrc;WeGc:Ge9hmbarcsGgwce0mbc9:hoalcufadcd4cbawEgDadfgrcKcaawEgqaraq0Egk6mbaicefhxcj;abad9Uc;WFbGcjdadca0EhmaialfgPar9Rgoadfhsavaoadz:jjjjbgzceVhHcbhOdndninaeaO9nmeaPax9RaD6mdamaeaO9RaOamfgoae6EgAcsfglc9WGhCabaOad2fhXaAcethQaxaDfhiaOaeaoaeao6E9RhLalcl4cifcd4hKazcj;cbfaAfhYcbh8AazcjdfhEaHh3incbh5dnawTmbaxa8Acd4fRbbh5kcbh8Eazcj;cbfhqinaih8Fdndndndna5a8Ecet4ciGgoc9:fPdebdkaPa8F9RaA6mrazcj;cbfa8EaA2fa8FaAz:jjjjb8Aa8FaAfhixdkazcj;cbfa8EaA2fcbaAz:kjjjb8Aa8FhixekaPa8F9RaK6mva8FaKfhidnaCTmbaPai9RcK6mbaocdtc:q:G:cjbfcj:G:cjbawEhaczhrcbhlinargoc9Wfghaqfhrdndndndndndnaaa8Fahco4fRbbalcoG4ciGcdtfydbPDbedvivvvlvkar9cb83bwar9cb83bbxlkarcbaiRbdai8Xbb9c:c:qj:bw9:9c:q;c1:I1e:d9c:b:c:e1z9:gg9cjjjjjz:dg8J9qE86bbaqaofgrcGfcbaicdfa8J9c8N1:NfghRbbag9cjjjjjw:dg8J9qE86bbarcVfcbaha8J9c8M1:NfghRbbag9cjjjjjl:dg8J9qE86bbarc7fcbaha8J9c8L1:NfghRbbag9cjjjjjd:dg8J9qE86bbarctfcbaha8J9c8K1:NfghRbbag9cjjjjje:dg8J9qE86bbarc91fcbaha8J9c8J1:NfghRbbag9cjjjj;ab:dg8J9qE86bbarc4fcbaha8J9cg1:NfghRbbag9cjjjja:dg8J9qE86bbarc93fcbaha8J9ch1:NfghRbbag9cjjjjz:dgg9qE86bbarc94fcbahag9ca1:NfghRbbai8Xbe9c:c:qj:bw9:9c:q;c1:I1e:d9c:b:c:e1z9:gg9cjjjjjz:dg8J9qE86bbarc95fcbaha8J9c8N1:NfgiRbbag9cjjjjjw:dg8J9qE86bbarc96fcbaia8J9c8M1:NfgiRbbag9cjjjjjl:dg8J9qE86bbarc97fcbaia8J9c8L1:NfgiRbbag9cjjjjjd:dg8J9qE86bbarc98fcbaia8J9c8K1:NfgiRbbag9cjjjjje:dg8J9qE86bbarc99fcbaia8J9c8J1:NfgiRbbag9cjjjj;ab:dg8J9qE86bbarc9:fcbaia8J9cg1:NfgiRbbag9cjjjja:dg8J9qE86bbarcufcbaia8J9ch1:NfgiRbbag9cjjjjz:dgg9qE86bbaiag9ca1:NfhixikaraiRblaiRbbghco4g8Ka8KciSg8KE86bbaqaofgrcGfaiclfa8Kfg8KRbbahcl4ciGg8La8LciSg8LE86bbarcVfa8Ka8Lfg8KRbbahcd4ciGg8La8LciSg8LE86bbarc7fa8Ka8Lfg8KRbbahciGghahciSghE86bbarctfa8Kahfg8KRbbaiRbeghco4g8La8LciSg8LE86bbarc91fa8Ka8Lfg8KRbbahcl4ciGg8La8LciSg8LE86bbarc4fa8Ka8Lfg8KRbbahcd4ciGg8La8LciSg8LE86bbarc93fa8Ka8Lfg8KRbbahciGghahciSghE86bbarc94fa8Kahfg8KRbbaiRbdghco4g8La8LciSg8LE86bbarc95fa8Ka8Lfg8KRbbahcl4ciGg8La8LciSg8LE86bbarc96fa8Ka8Lfg8KRbbahcd4ciGg8La8LciSg8LE86bbarc97fa8Ka8Lfg8KRbbahciGghahciSghE86bbarc98fa8KahfghRbbaiRbigico4g8Ka8KciSg8KE86bbarc99faha8KfghRbbaicl4ciGg8Ka8KciSg8KE86bbarc9:faha8KfghRbbaicd4ciGg8Ka8KciSg8KE86bbarcufaha8KfgrRbbaiciGgiaiciSgiE86bbaraifhixdkaraiRbwaiRbbghcl4g8Ka8KcsSg8KE86bbaqaofgrcGfaicwfa8Kfg8KRbbahcsGghahcsSghE86bbarcVfa8KahfghRbbaiRbeg8Kcl4g8La8LcsSg8LE86bbarc7faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarctfaha8KfghRbbaiRbdg8Kcl4g8La8LcsSg8LE86bbarc91faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarc4faha8KfghRbbaiRbig8Kcl4g8La8LcsSg8LE86bbarc93faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarc94faha8KfghRbbaiRblg8Kcl4g8La8LcsSg8LE86bbarc95faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarc96faha8KfghRbbaiRbvg8Kcl4g8La8LcsSg8LE86bbarc97faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarc98faha8KfghRbbaiRbog8Kcl4g8La8LcsSg8LE86bbarc99faha8LfghRbba8KcsGg8Ka8KcsSg8KE86bbarc9:faha8KfghRbbaiRbrgicl4g8Ka8KcsSg8KE86bbarcufaha8KfgrRbbaicsGgiaicsSgiE86bbaraifhixekarai8Pbw83bwarai8Pbb83bbaiczfhikdnaoaC9pmbalcdfhlaoczfhraPai9RcL0mekkaoaC6moaimexokaCmva8FTmvkaqaAfhqa8Ecefg8Ecl9hmbkdndndndnawTmbasa8Acd4fRbbgociGPlbedrbkaATmdaza8Afh8Fazcj;cbfhhcbh8EaEhaina8FRbbhraahocbhlinaoahalfRbbgqce4cbaqceG9R7arfgr86bbaoadfhoaAalcefgl9hmbkaacefhaa8Fcefh8FahaAfhha8Ecefg8Ecl9hmbxikkaATmeaza8Afhaazcj;cbfhhcbhoceh8EaYh8FinaEaofhlaa8Vbbhrcbhoinala8FaofRbbcwtahaofRbbgqVc;:FiGce4cbaqceG9R7arfgr87bbaladfhlaLaocefgofmbka8FaQfh8FcdhoaacdfhaahaQfhha8EceGhlcbh8EalmbxdkkaATmbaocl4h8Eaza8AfRbbhqcwhoa3hlinalRbbaotaqVhqalcefhlaocwfgoca9hmbkcbhhaEh8FaYhainazcj;cbfahfRbbhrcwhoaahlinalRbbaotarVhralaAfhlaocwfgoca9hmbkara8E94aq7hqcbhoa8Fhlinalaqao486bbalcefhlaocwfgoca9hmbka8Fadfh8FaacefhaahcefghaA9hmbkkaEclfhEa3clfh3a8Aclfg8Aad6mbkaXazcjdfaAad2z:jjjjb8AazazcjdfaAcufad2fadz:jjjjb8AaAaOfhOaihxaimbkc9:hoxdkcbc99aPax9RakSEhoxekc9:hokavcj;kbf8Kjjjjbaok:ysezu8Jjjjjbc;ae9Rgv8Kjjjjbc9:hodnalaeci9UgrcHf6mbcuhoaiRbbgwc;WeGc;Ge9hmbawcsGgDce0mbavc;abfcFecjez:kjjjb8Aav9cu83iUav9cu83i8Wav9cu83iyav9cu83iaav9cu83iKav9cu83izav9cu83iwav9cu83ibaialfc9WfhqaicefgwarfhldnaeTmbcmcsaDceSEhkcbhxcbhmcbhrcbhicbhoindnalaq9nmbc9:hoxikdndnawRbbgDc;Ve0mbavc;abfaoaDcu7gPcl4fcsGcitfgsydlhzasydbhHdndnaDcsGgsak9pmbavaiaPfcsGcdtfydbaxasEhDaxasTgOfhxxekdndnascsSmbcehOasc987asamffcefhDxekalcefhDal8SbbgscFeGhPdndnascu9mmbaDhlxekalcvfhlaPcFbGhPcrhsdninaD8SbbgOcFbGastaPVhPaOcu9kmeaDcefhDascrfgsc8J9hmbxdkkaDcefhlkcehOaPce4cbaPceG9R7amfhDkaDhmkavc;abfaocitfgsaDBdbasazBdlavaicdtfaDBdbavc;abfaocefcsGcitfgsaHBdbasaDBdlaocdfhoaOaifhidnadcd9hmbabarcetfgsaH87ebasclfaD87ebascdfaz87ebxdkabarcdtfgsaHBdbascwfaDBdbasclfazBdbxekdnaDcpe0mbavaiaqaDcsGfRbbgscl4gP9RcsGcdtfydbaxcefgOaPEhDavaias9RcsGcdtfydbaOaPTgzfgOascsGgPEhsaPThPdndnadcd9hmbabarcetfgHax87ebaHclfas87ebaHcdfaD87ebxekabarcdtfgHaxBdbaHcwfasBdbaHclfaDBdbkavaicdtfaxBdbavc;abfaocitfgHaDBdbaHaxBdlavaicefgicsGcdtfaDBdbavc;abfaocefcsGcitfgHasBdbaHaDBdlavaiazfgicsGcdtfasBdbavc;abfaocdfcsGcitfgDaxBdbaDasBdlaocifhoaiaPfhiaOaPfhxxekaxcbalRbbgsEgHaDc;:eSgDfhOascsGhAdndnascl4gCmbaOcefhzxekaOhzavaiaC9RcsGcdtfydbhOkdndnaAmbazcefhxxekazhxavaias9RcsGcdtfydbhzkdndnaDTmbalcefhDxekalcdfhDal8SbegPcFeGhsdnaPcu9kmbalcofhHascFbGhscrhldninaD8SbbgPcFbGaltasVhsaPcu9kmeaDcefhDalcrfglc8J9hmbkaHhDxekaDcefhDkasce4cbasceG9R7amfgmhHkdndnaCcsSmbaDhsxekaDcefhsaD8SbbglcFeGhPdnalcu9kmbaDcvfhOaPcFbGhPcrhldninas8SbbgDcFbGaltaPVhPaDcu9kmeascefhsalcrfglc8J9hmbkaOhsxekascefhskaPce4cbaPceG9R7amfgmhOkdndnaAcsSmbashlxekascefhlas8SbbgDcFeGhPdnaDcu9kmbascvfhzaPcFbGhPcrhDdninal8SbbgscFbGaDtaPVhPascu9kmealcefhlaDcrfgDc8J9hmbkazhlxekalcefhlkaPce4cbaPceG9R7amfgmhzkdndnadcd9hmbabarcetfgDaH87ebaDclfaz87ebaDcdfaO87ebxekabarcdtfgDaHBdbaDcwfazBdbaDclfaOBdbkavc;abfaocitfgDaOBdbaDaHBdlavaicdtfaHBdbavc;abfaocefcsGcitfgDazBdbaDaOBdlavaicefgicsGcdtfaOBdbavc;abfaocdfcsGcitfgDaHBdbaDazBdlavaiaCTaCcsSVfgicsGcdtfazBdbaiaATaAcsSVfhiaocifhokawcefhwaocsGhoaicsGhiarcifgrae6mbkkcbc99alaqSEhokavc;aef8Kjjjjbaok:clevu8Jjjjjbcz9Rhvdnalaecvf9pmbc9:skdnaiRbbc;:eGc;qeSmbcuskav9cb83iwaicefhoaialfc98fhrdnaeTmbdnadcdSmbcbhwindnaoar6mbc9:skaocefhlao8SbbgicFeGhddndnaicu9mmbalhoxekaocvfhoadcFbGhdcrhidninal8SbbgDcFbGaitadVhdaDcu9kmealcefhlaicrfgic8J9hmbxdkkalcefhokabawcdtfadc8Etc8F91adcd47avcwfadceGcdtVglydbfgiBdbalaiBdbawcefgwae9hmbxdkkcbhwindnaoar6mbc9:skaocefhlao8SbbgicFeGhddndnaicu9mmbalhoxekaocvfhoadcFbGhdcrhidninal8SbbgDcFbGaitadVhdaDcu9kmealcefhlaicrfgic8J9hmbxdkkalcefhokabawcetfadc8Etc8F91adcd47avcwfadceGcdtVglydbfgi87ebalaiBdbawcefgwae9hmbkkcbc99aoarSEk:Lvoeue99dud99eud99dndnadcl9hmbaeTmeindndnabcdfgd8Sbb:Yab8Sbbgi:Ygl:l:tabcefgv8Sbbgo:Ygr:l:tgwJbb;:9cawawNJbbbbawawJbbbb9GgDEgq:mgkaqaicb9iEalMgwawNakaqaocb9iEarMgqaqNMM:r:vglNJbbbZJbbb:;aDEMgr:lJbbb9p9DTmbar:Ohixekcjjjj94hikadai86bbdndnaqalNJbbbZJbbb:;aqJbbbb9GEMgq:lJbbb9p9DTmbaq:Ohdxekcjjjj94hdkavad86bbdndnawalNJbbbZJbbb:;awJbbbb9GEMgw:lJbbb9p9DTmbaw:Ohdxekcjjjj94hdkabad86bbabclfhbaecufgembxdkkaeTmbindndnabclfgd8Ueb:Yab8Uebgi:Ygl:l:tabcdfgv8Uebgo:Ygr:l:tgwJb;:FSawawNJbbbbawawJbbbb9GgDEgq:mgkaqaicb9iEalMgwawNakaqaocb9iEarMgqaqNMM:r:vglNJbbbZJbbb:;aDEMgr:lJbbb9p9DTmbar:Ohixekcjjjj94hikadai87ebdndnaqalNJbbbZJbbb:;aqJbbbb9GEMgq:lJbbb9p9DTmbaq:Ohdxekcjjjj94hdkavad87ebdndnawalNJbbbZJbbb:;awJbbbb9GEMgw:lJbbb9p9DTmbaw:Ohdxekcjjjj94hdkabad87ebabcwfhbaecufgembkkk:4ioiue99dud99dud99dnaeTmbcbhiabhlindndnal8Uebgv:YgoJ:ji:1Salcof8UebgrciVgw:Y:vgDNJbbbZJbbb:;avcu9kEMgq:lJbbb9p9DTmbaq:Ohkxekcjjjj94hkkalclf8Uebhvalcdf8UebhxalarcefciGcetfak87ebdndnax:YgqaDNJbbbZJbbb:;axcu9kEMgm:lJbbb9p9DTmbam:Ohxxekcjjjj94hxkabaiarciGgkfcd7cetfax87ebdndnav:YgmaDNJbbbZJbbb:;avcu9kEMgP:lJbbb9p9DTmbaP:Ohvxekcjjjj94hvkalarcufciGcetfav87ebdndnawaw2:ZgPaPMaoaoN:taqaqN:tamamN:tgoJbbbbaoJbbbb9GE:raDNJbbbZMgD:lJbbb9p9DTmbaD:Ohrxekcjjjj94hrkalakcetfar87ebalcwfhlaiclfhiaecufgembkkk9mbdnadcd4ae2gdTmbinababydbgecwtcw91:Yaece91cjjj98Gcjjj;8if::NUdbabclfhbadcufgdmbkkk:Tvirud99eudndnadcl9hmbaeTmeindndnabRbbgiabcefgl8Sbbgvabcdfgo8Sbbgrf9R:YJbbuJabcifgwRbbgdce4adVgDcd4aDVgDcl4aDVgD:Z:vgqNJbbbZMgk:lJbbb9p9DTmbak:Ohxxekcjjjj94hxkaoax86bbdndnaraif:YaqNJbbbZMgk:lJbbb9p9DTmbak:Ohoxekcjjjj94hokalao86bbdndnavaifar9R:YaqNJbbbZMgk:lJbbb9p9DTmbak:Ohixekcjjjj94hikabai86bbdndnaDadcetGadceGV:ZaqNJbbbZMgq:lJbbb9p9DTmbaq:Ohdxekcjjjj94hdkawad86bbabclfhbaecufgembxdkkaeTmbindndnab8Vebgiabcdfgl8Uebgvabclfgo8Uebgrf9R:YJbFu9habcofgw8Vebgdce4adVgDcd4aDVgDcl4aDVgDcw4aDVgD:Z:vgqNJbbbZMgk:lJbbb9p9DTmbak:Ohxxekcjjjj94hxkaoax87ebdndnaraif:YaqNJbbbZMgk:lJbbb9p9DTmbak:Ohoxekcjjjj94hokalao87ebdndnavaifar9R:YaqNJbbbZMgk:lJbbb9p9DTmbak:Ohixekcjjjj94hikabai87ebdndnaDadcetGadceGV:ZaqNJbbbZMgq:lJbbb9p9DTmbaq:Ohdxekcjjjj94hdkawad87ebabcwfhbaecufgembkkk9teiucbcbyd:K:G:cjbgeabcifc98GfgbBd:K:G:cjbdndnabZbcztgd9nmbcuhiabad9RcFFifcz4nbcuSmekaehikaik;LeeeudndnaeabVciGTmbabhixekdndnadcz9pmbabhixekabhiinaiaeydbBdbaiclfaeclfydbBdbaicwfaecwfydbBdbaicxfaecxfydbBdbaeczfheaiczfhiadc9Wfgdcs0mbkkadcl6mbinaiaeydbBdbaeclfheaiclfhiadc98fgdci0mbkkdnadTmbinaiaeRbb86bbaicefhiaecefheadcufgdmbkkabk;aeedudndnabciGTmbabhixekaecFeGc:b:c:ew2hldndnadcz9pmbabhixekabhiinaialBdbaicxfalBdbaicwfalBdbaiclfalBdbaiczfhiadc9Wfgdcs0mbkkadcl6mbinaialBdbaiclfhiadc98fgdci0mbkkdnadTmbinaiae86bbaicefhiadcufgdmbkkabkk83dbcj:Gdk8Kbbbbdbbblbbbwbbbbbbbebbbdbbblbbbwbbbbc:K:Gdkl8W:qbb";
|
|
14698
|
+
var wasm_simd = "b9H79TebbbeKl9Gbb9Gvuuuuueu9Giuuub9Geueuixkbbebeeddddilve9Weeeviebeoweuecj:Gdkr;Neqo9TW9T9VV95dbH9F9F939H79T9F9J9H229F9Jt9VV7bb8A9TW79O9V9Wt9F9KW9J9V9KW9wWVtW949c919M9MWVbdY9TW79O9V9Wt9F9KW9J9V9KW69U9KW949c919M9MWVblE9TW79O9V9Wt9F9KW9J9V9KW69U9KW949tWG91W9U9JWbvL9TW79O9V9Wt9F9KW9J9V9KWS9P2tWV9p9JtboK9TW79O9V9Wt9F9KW9J9V9KWS9P2tWV9r919HtbrL9TW79O9V9Wt9F9KW9J9V9KWS9P2tWVT949WbwY9TW79O9V9Wt9F9KW9J9V9KWS9P2tWVJ9V29VVbDl79IV9Rbqq:W9Dklbzik94evu8Jjjjjbcz9Rhbcbheincbhdcbhiinabcwfadfaicjuaead4ceGglE86bbaialfhiadcefgdcw9hmbkaeai86b:q:W:cjbaecitab8Piw83i:q:G:cjbaecefgecjd9hmbkk:JBl8Aud97dur978Jjjjjbcj;kb9Rgv8Kjjjjbc9:hodnalTmbcuhoaiRbbgrc;WeGc:Ge9hmbarcsGgwce0mbc9:hoalcufadcd4cbawEgDadfgrcKcaawEgqaraq0Egk6mbaialfgxar9RhodnadTgmmbavaoad;8qbbkaicefhPcj;abad9Uc;WFbGcjdadca0EhsdndndnadTmbaoadfhzcbhHinaeaH9nmdaxaP9RaD6miabaHad2fhOaPaDfhAasaeaH9RaHasfae6EgCcsfgocl4cifcd4hXavcj;cbfaoc9WGgQcetfhLavcj;cbfaQci2fhKavcj;cbfaQfhYcbh8Aaoc;ab6hEincbh3dnawTmbaPa8Acd4fRbbh3kcbh5avcj;cbfh8Eindndndndna3a5cet4ciGgoc9:fPdebdkaxaA9RaQ6mwdnaQTmbavcj;cbfa5aQ2faAaQ;8qbbkaAaCfhAxdkaQTmeavcj;cbfa5aQ2fcbaQ;8kbxekaxaA9RaX6moaoclVcbawEhraAaXfhocbhidnaEmbaxao9Rc;Gb6mbcbhlina8EalfhidndndndndndnaAalco4fRbbgqciGarfPDbedibledibkaipxbbbbbbbbbbbbbbbbpklbxlkaiaopbblaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLg8Fcdp:mea8FpmbzeHdOiAlCvXoQrLpxiiiiiiiiiiiiiiiip9ogapxiiiiiiiiiiiiiiiip8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaoclffagRb:q:W:cjbfhoxikaiaopbbwaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLpxssssssssssssssssp9ogapxssssssssssssssssp8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaocwffagRb:q:W:cjbfhoxdkaiaopbbbpklbaoczfhoxekaiaopbbdaoRbbghcitpbi:q:G:cjbahRb:q:W:cjbghpsaoRbeggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPpklbahaocdffagRb:q:W:cjbfhokdndndndndndnaqcd4ciGarfPDbedibledibkaiczfpxbbbbbbbbbbbbbbbbpklbxlkaiczfaopbblaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLg8Fcdp:mea8FpmbzeHdOiAlCvXoQrLpxiiiiiiiiiiiiiiiip9ogapxiiiiiiiiiiiiiiiip8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaoclffagRb:q:W:cjbfhoxikaiczfaopbbwaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLpxssssssssssssssssp9ogapxssssssssssssssssp8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaocwffagRb:q:W:cjbfhoxdkaiczfaopbbbpklbaoczfhoxekaiczfaopbbdaoRbbghcitpbi:q:G:cjbahRb:q:W:cjbghpsaoRbeggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPpklbahaocdffagRb:q:W:cjbfhokdndndndndndnaqcl4ciGarfPDbedibledibkaicafpxbbbbbbbbbbbbbbbbpklbxlkaicafaopbblaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLg8Fcdp:mea8FpmbzeHdOiAlCvXoQrLpxiiiiiiiiiiiiiiiip9ogapxiiiiiiiiiiiiiiiip8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaoclffagRb:q:W:cjbfhoxikaicafaopbbwaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLpxssssssssssssssssp9ogapxssssssssssssssssp8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbahaocwffagRb:q:W:cjbfhoxdkaicafaopbbbpklbaoczfhoxekaicafaopbbdaoRbbghcitpbi:q:G:cjbahRb:q:W:cjbghpsaoRbeggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPpklbahaocdffagRb:q:W:cjbfhokdndndndndndnaqco4arfPDbedibledibkaic8Wfpxbbbbbbbbbbbbbbbbpklbxlkaic8Wfaopbblaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLg8Fcdp:mea8FpmbzeHdOiAlCvXoQrLpxiiiiiiiiiiiiiiiip9ogapxiiiiiiiiiiiiiiiip8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Ngicitpbi:q:G:cjbaiRb:q:W:cjbgipsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Ngqcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbaiaoclffaqRb:q:W:cjbfhoxikaic8Wfaopbbwaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLpxssssssssssssssssp9ogapxssssssssssssssssp8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Ngicitpbi:q:G:cjbaiRb:q:W:cjbgipsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Ngqcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spklbaiaocwffaqRb:q:W:cjbfhoxdkaic8Wfaopbbbpklbaoczfhoxekaic8WfaopbbdaoRbbgicitpbi:q:G:cjbaiRb:q:W:cjbgipsaoRbegqcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPpklbaiaocdffaqRb:q:W:cjbfhokalc;abfhialcjefaQ0meaihlaxao9Rc;Fb0mbkkdnaiaQ9pmbaici4hlinaxao9RcK6mwa8EaifhqdndndndndndnaAaico4fRbbalcoG4ciGarfPDbedibledibkaqpxbbbbbbbbbbbbbbbbpkbbxlkaqaopbblaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLg8Fcdp:mea8FpmbzeHdOiAlCvXoQrLpxiiiiiiiiiiiiiiiip9ogapxiiiiiiiiiiiiiiiip8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spkbbahaoclffagRb:q:W:cjbfhoxikaqaopbbwaopbbbg8Fclp:mea8FpmbzeHdOiAlCvXoQrLpxssssssssssssssssp9ogapxssssssssssssssssp8Jg8Fp5b9cjF;8;4;W;G;ab9:9cU1:Nghcitpbi:q:G:cjbahRb:q:W:cjbghpsa8Fp5e9cjF;8;4;W;G;ab9:9cU1:Nggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPaaa8Fp9spkbbahaocwffagRb:q:W:cjbfhoxdkaqaopbbbpkbbaoczfhoxekaqaopbbdaoRbbghcitpbi:q:G:cjbahRb:q:W:cjbghpsaoRbeggcitpbi:q:G:cjbp9UpmbedilvorzHOACXQLpPpkbbahaocdffagRb:q:W:cjbfhokalcdfhlaiczfgiaQ6mbkkaohAaoTmoka8EaQfh8Ea5cefg5cl9hmbkdndndndnawTmbaza8Acd4fRbbglciGPlbedwbkaQTmdavcjdfa8Afhlava8Afpbdbh8Jcbhoinalavcj;cbfaofpblbg8KaYaofpblbg8LpmbzeHdOiAlCvXoQrLg8MaLaofpblbg8NaKaofpblbgypmbzeHdOiAlCvXoQrLg8PpmbezHdiOAlvCXorQLg8Fcep9Ta8Fpxeeeeeeeeeeeeeeeegap9op9Hp9rg8Fa8Jp9Ug8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp9Ug8Jp9Abbbaladfgla8Ja8Ma8PpmwDKYqk8AExm35Ps8E8Fg8Fcep9Ta8Faap9op9Hp9rg8Fp9Ug8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp9Ug8Jp9Abbbaladfgla8Ja8Ka8LpmwKDYq8AkEx3m5P8Es8Fg8Ka8NaypmwKDYq8AkEx3m5P8Es8Fg8LpmbezHdiOAlvCXorQLg8Fcep9Ta8Faap9op9Hp9rg8Fp9Ug8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp9Ug8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp9Ug8Jp9Abbbaladfgla8Ja8Ka8LpmwDKYqk8AExm35Ps8E8Fg8Fcep9Ta8Faap9op9Hp9rg8Fp9Ugap9Abbbaladfglaaa8Fa8Fpmlvorlvorlvorlvorp9Ugap9Abbbaladfglaaa8Fa8FpmwDqkwDqkwDqkwDqkp9Ugap9Abbbaladfglaaa8Fa8FpmxmPsxmPsxmPsxmPsp9Ug8Jp9AbbbaladfhlaoczfgoaQ6mbxikkaQTmeavcjdfa8Afhlava8Afpbdbh8Jcbhoinalavcj;cbfaofpblbg8KaYaofpblbg8LpmbzeHdOiAlCvXoQrLg8MaLaofpblbg8NaKaofpblbgypmbzeHdOiAlCvXoQrLg8PpmbezHdiOAlvCXorQLg8Fcep:nea8Fpxebebebebebebebebgap9op:bep9rg8Fa8Jp:oeg8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp:oeg8Jp9Abbbaladfgla8Ja8Ma8PpmwDKYqk8AExm35Ps8E8Fg8Fcep:nea8Faap9op:bep9rg8Fp:oeg8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp:oeg8Jp9Abbbaladfgla8Ja8Ka8LpmwKDYq8AkEx3m5P8Es8Fg8Ka8NaypmwKDYq8AkEx3m5P8Es8Fg8LpmbezHdiOAlvCXorQLg8Fcep:nea8Faap9op:bep9rg8Fp:oeg8Jp9Abbbaladfgla8Ja8Fa8Fpmlvorlvorlvorlvorp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmwDqkwDqkwDqkwDqkp:oeg8Jp9Abbbaladfgla8Ja8Fa8FpmxmPsxmPsxmPsxmPsp:oeg8Jp9Abbbaladfgla8Ja8Ka8LpmwDKYqk8AExm35Ps8E8Fg8Fcep:nea8Faap9op:bep9rg8Fp:oegap9Abbbaladfglaaa8Fa8Fpmlvorlvorlvorlvorp:oegap9Abbbaladfglaaa8Fa8FpmwDqkwDqkwDqkwDqkp:oegap9Abbbaladfglaaa8Fa8FpmxmPsxmPsxmPsxmPsp:oeg8Jp9AbbbaladfhlaoczfgoaQ6mbxdkkaQTmbcbhocbalcl4gl9Rc8FGhiavcjdfa8Afhrava8Afpbdbhainaravcj;cbfaofpblbg8JaYaofpblbg8KpmbzeHdOiAlCvXoQrLg8LaLaofpblbg8MaKaofpblbg8NpmbzeHdOiAlCvXoQrLgypmbezHdiOAlvCXorQLg8Faip:Rea8Falp:Tep9qg8Faap9rgap9Abbbaradfgraaa8Fa8Fpmlvorlvorlvorlvorp9rgap9Abbbaradfgraaa8Fa8FpmwDqkwDqkwDqkwDqkp9rgap9Abbbaradfgraaa8Fa8FpmxmPsxmPsxmPsxmPsp9rgap9Abbbaradfgraaa8LaypmwDKYqk8AExm35Ps8E8Fg8Faip:Rea8Falp:Tep9qg8Fp9rgap9Abbbaradfgraaa8Fa8Fpmlvorlvorlvorlvorp9rgap9Abbbaradfgraaa8Fa8FpmwDqkwDqkwDqkwDqkp9rgap9Abbbaradfgraaa8Fa8FpmxmPsxmPsxmPsxmPsp9rgap9Abbbaradfgraaa8Ja8KpmwKDYq8AkEx3m5P8Es8Fg8Ja8Ma8NpmwKDYq8AkEx3m5P8Es8Fg8KpmbezHdiOAlvCXorQLg8Faip:Rea8Falp:Tep9qg8Fp9rgap9Abbbaradfgraaa8Fa8Fpmlvorlvorlvorlvorp9rgap9Abbbaradfgraaa8Fa8FpmwDqkwDqkwDqkwDqkp9rgap9Abbbaradfgraaa8Fa8FpmxmPsxmPsxmPsxmPsp9rgap9Abbbaradfgraaa8Ja8KpmwDKYqk8AExm35Ps8E8Fg8Faip:Rea8Falp:Tep9qg8Fp9rgap9Abbbaradfgraaa8Fa8Fpmlvorlvorlvorlvorp9rgap9Abbbaradfgraaa8Fa8FpmwDqkwDqkwDqkwDqkp9rgap9Abbbaradfgraaa8Fa8FpmxmPsxmPsxmPsxmPsp9rgap9AbbbaradfhraoczfgoaQ6mbkka8Aclfg8Aad6mbkdnaCad2goTmbaOavcjdfao;8qbbkdnammbavavcjdfaCcufad2fad;8qbbkaCaHfhHc9:hoaAhPaAmbxlkkaeTmbaDalfhrcbhocuhlinaralaD9RglfaD6mdasaeao9Raoasfae6Eaofgoae6mbkaial9RhPkcbc99axaP9RakSEhoxekc9:hokavcj;kbf8Kjjjjbaokwbz:bjjjbkNsezu8Jjjjjbc;ae9Rgv8Kjjjjbc9:hodnalaeci9UgrcHf6mbcuhoaiRbbgwc;WeGc;Ge9hmbawcsGgDce0mbavc;abfcFecje;8kbav9cu83iUav9cu83i8Wav9cu83iyav9cu83iaav9cu83iKav9cu83izav9cu83iwav9cu83ibaialfc9WfhqaicefgwarfhldnaeTmbcmcsaDceSEhkcbhxcbhmcbhrcbhicbhoindnalaq9nmbc9:hoxikdndnawRbbgDc;Ve0mbavc;abfaoaDcu7gPcl4fcsGcitfgsydlhzasydbhHdndnaDcsGgsak9pmbavaiaPfcsGcdtfydbaxasEhDaxasTgOfhxxekdndnascsSmbcehOasc987asamffcefhDxekalcefhDal8SbbgscFeGhPdndnascu9mmbaDhlxekalcvfhlaPcFbGhPcrhsdninaD8SbbgOcFbGastaPVhPaOcu9kmeaDcefhDascrfgsc8J9hmbxdkkaDcefhlkcehOaPce4cbaPceG9R7amfhDkaDhmkavc;abfaocitfgsaDBdbasazBdlavaicdtfaDBdbavc;abfaocefcsGcitfgsaHBdbasaDBdlaocdfhoaOaifhidnadcd9hmbabarcetfgsaH87ebasclfaD87ebascdfaz87ebxdkabarcdtfgsaHBdbascwfaDBdbasclfazBdbxekdnaDcpe0mbavaiaqaDcsGfRbbgscl4gP9RcsGcdtfydbaxcefgOaPEhDavaias9RcsGcdtfydbaOaPTgzfgOascsGgPEhsaPThPdndnadcd9hmbabarcetfgHax87ebaHclfas87ebaHcdfaD87ebxekabarcdtfgHaxBdbaHcwfasBdbaHclfaDBdbkavaicdtfaxBdbavc;abfaocitfgHaDBdbaHaxBdlavaicefgicsGcdtfaDBdbavc;abfaocefcsGcitfgHasBdbaHaDBdlavaiazfgicsGcdtfasBdbavc;abfaocdfcsGcitfgDaxBdbaDasBdlaocifhoaiaPfhiaOaPfhxxekaxcbalRbbgsEgHaDc;:eSgDfhOascsGhAdndnascl4gCmbaOcefhzxekaOhzavaiaC9RcsGcdtfydbhOkdndnaAmbazcefhxxekazhxavaias9RcsGcdtfydbhzkdndnaDTmbalcefhDxekalcdfhDal8SbegPcFeGhsdnaPcu9kmbalcofhHascFbGhscrhldninaD8SbbgPcFbGaltasVhsaPcu9kmeaDcefhDalcrfglc8J9hmbkaHhDxekaDcefhDkasce4cbasceG9R7amfgmhHkdndnaCcsSmbaDhsxekaDcefhsaD8SbbglcFeGhPdnalcu9kmbaDcvfhOaPcFbGhPcrhldninas8SbbgDcFbGaltaPVhPaDcu9kmeascefhsalcrfglc8J9hmbkaOhsxekascefhskaPce4cbaPceG9R7amfgmhOkdndnaAcsSmbashlxekascefhlas8SbbgDcFeGhPdnaDcu9kmbascvfhzaPcFbGhPcrhDdninal8SbbgscFbGaDtaPVhPascu9kmealcefhlaDcrfgDc8J9hmbkazhlxekalcefhlkaPce4cbaPceG9R7amfgmhzkdndnadcd9hmbabarcetfgDaH87ebaDclfaz87ebaDcdfaO87ebxekabarcdtfgDaHBdbaDcwfazBdbaDclfaOBdbkavc;abfaocitfgDaOBdbaDaHBdlavaicdtfaHBdbavc;abfaocefcsGcitfgDazBdbaDaOBdlavaicefgicsGcdtfaOBdbavc;abfaocdfcsGcitfgDaHBdbaDazBdlavaiaCTaCcsSVfgicsGcdtfazBdbaiaATaAcsSVfhiaocifhokawcefhwaocsGhoaicsGhiarcifgrae6mbkkcbc99alaqSEhokavc;aef8Kjjjjbaok:clevu8Jjjjjbcz9Rhvdnalaecvf9pmbc9:skdnaiRbbc;:eGc;qeSmbcuskav9cb83iwaicefhoaialfc98fhrdnaeTmbdnadcdSmbcbhwindnaoar6mbc9:skaocefhlao8SbbgicFeGhddndnaicu9mmbalhoxekaocvfhoadcFbGhdcrhidninal8SbbgDcFbGaitadVhdaDcu9kmealcefhlaicrfgic8J9hmbxdkkalcefhokabawcdtfadc8Etc8F91adcd47avcwfadceGcdtVglydbfgiBdbalaiBdbawcefgwae9hmbxdkkcbhwindnaoar6mbc9:skaocefhlao8SbbgicFeGhddndnaicu9mmbalhoxekaocvfhoadcFbGhdcrhidninal8SbbgDcFbGaitadVhdaDcu9kmealcefhlaicrfgic8J9hmbxdkkalcefhokabawcetfadc8Etc8F91adcd47avcwfadceGcdtVglydbfgi87ebalaiBdbawcefgwae9hmbkkcbc99aoarSEk;Toio97eue97aec98Ghedndnadcl9hmbaeTmecbhdinababpbbbgicKp:RecKp:Sep;6eglaicwp:RecKp:Sep;6ealp;Geaiczp:RecKp:Sep;6egvp;Gep;Kep;Legopxbbbbbbbbbbbbbbbbp:2egralpxbbbjbbbjbbbjbbbjgwp9op9rp;Keglpxbb;:9cbb;:9cbb;:9cbb;:9calalp;Meaoaop;Meavaravawp9op9rp;Keglalp;Mep;Kep;Kep;Jep;Negvp;Mepxbbn0bbn0bbn0bbn0grp;KepxFbbbFbbbFbbbFbbbp9oaipxbbbFbbbFbbbFbbbFp9op9qalavp;Mearp;Kecwp:RepxbFbbbFbbbFbbbFbbp9op9qaoavp;Mearp;Keczp:RepxbbFbbbFbbbFbbbFbp9op9qpkbbabczfhbadclfgdae6mbxdkkaeTmbcbhdinabczfgDaDpbbbgipxbbbbbbFFbbbbbbFFgwp9oabpbbbgoaipmbediwDqkzHOAKY8AEgvczp:Reczp:Sep;6eglaoaipmlvorxmPsCXQL358E8FpxFubbFubbFubbFubbp9op;6eavczp:Sep;6egvp;Gealp;Gep;Kep;Legipxbbbbbbbbbbbbbbbbp:2egralpxbbbjbbbjbbbjbbbjgqp9op9rp;Keglpxb;:FSb;:FSb;:FSb;:FSalalp;Meaiaip;Meavaravaqp9op9rp;Keglalp;Mep;Kep;Kep;Jep;Negvp;Mepxbbn0bbn0bbn0bbn0grp;KepxFFbbFFbbFFbbFFbbp9oaiavp;Mearp;Keczp:Rep9qgialavp;Mearp;KepxFFbbFFbbFFbbFFbbp9oglpmwDKYqk8AExm35Ps8E8Fp9qpkbbabaoawp9oaialpmbezHdiOAlvCXorQLp9qpkbbabcafhbadclfgdae6mbkkk;2ileue97euo97dnaec98GgiTmbcbheinabcKfpx:ji:1S:ji:1S:ji:1S:ji:1SabpbbbglabczfgvpbbbgopmlvorxmPsCXQL358E8Fgrczp:Segwpxibbbibbbibbbibbbp9qp;6egDp;NegqaDaDp;MegDaDp;KealaopmbediwDqkzHOAKY8AEgDczp:Reczp:Sep;6eglalp;MeaDczp:Sep;6egoaop;Mearczp:Reczp:Sep;6egrarp;Mep;Kep;Kep;Lepxbbbbbbbbbbbbbbbbp:4ep;Jep;Mepxbbn0bbn0bbn0bbn0gDp;KepxFFbbFFbbFFbbFFbbgkp9oaqaop;MeaDp;Keczp:Rep9qgoaqalp;MeaDp;Keakp9oaqarp;MeaDp;Keczp:Rep9qgDpmwDKYqk8AExm35Ps8E8Fglp5eawclp:RegqpEi:T:j83ibavalp5baqpEd:T:j83ibabcwfaoaDpmbezHdiOAlvCXorQLgDp5eaqpEe:T:j83ibabaDp5baqpEb:T:j83ibabcafhbaeclfgeai6mbkkkuee97dnadcd4ae2c98GgeTmbcbhdinababpbbbgicwp:Recwp:Sep;6eaicep:SepxbbjFbbjFbbjFbbjFp9opxbbjZbbjZbbjZbbjZp:Uep;Mepkbbabczfhbadclfgdae6mbkkk:Sodw97euaec98Ghedndnadcl9hmbaeTmecbhdinabpxbbuJbbuJbbuJbbuJabpbbbgicKp:TeglaicYp:Tep9qgvcdp:Teavp9qgvclp:Teavp9qgop;6ep;Negvaicwp:RecKp:SegraipxFbbbFbbbFbbbFbbbgwp9ogDp:Uep;6ep;Mepxbbn0bbn0bbn0bbn0gqp;Kecwp:RepxbFbbbFbbbFbbbFbbp9oavaDarp:Xeaiczp:RecKp:Segip:Uep;6ep;Meaqp;Keawp9op9qavaDaraip:Uep:Xep;6ep;Meaqp;Keczp:RepxbbFbbbFbbbFbbbFbp9op9qavaoalcep:Rep9oalpxebbbebbbebbbebbbp9op9qp;6ep;Meaqp;KecKp:Rep9qpkbbabczfhbadclfgdae6mbxdkkaeTmbcbhdinabczfgkpxbFu9hbFu9hbFu9hbFu9habpbbbglakpbbbgrpmlvorxmPsCXQL358E8Fgvczp:TegqavcHp:Tep9qgicdp:Teaip9qgiclp:Teaip9qgicwp:Teaip9qgop;6ep;NegialarpmbediwDqkzHOAKY8AEgDpxFFbbFFbbFFbbFFbbglp9ograDczp:Segwp:Ueavczp:Reczp:SegDp:Xep;6ep;Mepxbbn0bbn0bbn0bbn0gvp;Kealp9oaiarawaDp:Uep:Xep;6ep;Meavp;Keczp:Rep9qgwaiaoaqcep:Rep9oaqpxebbbebbbebbbebbbp9op9qp;6ep;Meavp;Keczp:ReaiaDarp:Uep;6ep;Meavp;Kealp9op9qgipmwDKYqk8AExm35Ps8E8FpkbbabawaipmbezHdiOAlvCXorQLpkbbabcafhbadclfgdae6mbkkk9teiucbcbydj:G:cjbgeabcifc98GfgbBdj:G:cjbdndnabZbcztgd9nmbcuhiabad9RcFFifcz4nbcuSmekaehikaikkxebcj:Gdklz:zbb";
|
|
14699
|
+
var detector = new Uint8Array([
|
|
14700
|
+
0,
|
|
14701
|
+
97,
|
|
14702
|
+
115,
|
|
14703
|
+
109,
|
|
14704
|
+
1,
|
|
14705
|
+
0,
|
|
14706
|
+
0,
|
|
14707
|
+
0,
|
|
14708
|
+
1,
|
|
14709
|
+
4,
|
|
14710
|
+
1,
|
|
14711
|
+
96,
|
|
14712
|
+
0,
|
|
14713
|
+
0,
|
|
14714
|
+
3,
|
|
14715
|
+
3,
|
|
14716
|
+
2,
|
|
14717
|
+
0,
|
|
14718
|
+
0,
|
|
14719
|
+
5,
|
|
14720
|
+
3,
|
|
14721
|
+
1,
|
|
14722
|
+
0,
|
|
14723
|
+
1,
|
|
14724
|
+
12,
|
|
14725
|
+
1,
|
|
14726
|
+
0,
|
|
14727
|
+
10,
|
|
14728
|
+
22,
|
|
14729
|
+
2,
|
|
14730
|
+
12,
|
|
14731
|
+
0,
|
|
14732
|
+
65,
|
|
14733
|
+
0,
|
|
14734
|
+
65,
|
|
14735
|
+
0,
|
|
14736
|
+
65,
|
|
14737
|
+
0,
|
|
14738
|
+
252,
|
|
14739
|
+
10,
|
|
14740
|
+
0,
|
|
14741
|
+
0,
|
|
14742
|
+
11,
|
|
14743
|
+
7,
|
|
14744
|
+
0,
|
|
14745
|
+
65,
|
|
14746
|
+
0,
|
|
14747
|
+
253,
|
|
14748
|
+
15,
|
|
14749
|
+
26,
|
|
14750
|
+
11
|
|
14751
|
+
]);
|
|
14752
|
+
var wasmpack = new Uint8Array([
|
|
14753
|
+
32,
|
|
14754
|
+
0,
|
|
14755
|
+
65,
|
|
14756
|
+
2,
|
|
14757
|
+
1,
|
|
14758
|
+
106,
|
|
14759
|
+
34,
|
|
14760
|
+
33,
|
|
14761
|
+
3,
|
|
14762
|
+
128,
|
|
14763
|
+
11,
|
|
14764
|
+
4,
|
|
14765
|
+
13,
|
|
14766
|
+
64,
|
|
14767
|
+
6,
|
|
14768
|
+
253,
|
|
14769
|
+
10,
|
|
14770
|
+
7,
|
|
14771
|
+
15,
|
|
14772
|
+
116,
|
|
14773
|
+
127,
|
|
14774
|
+
5,
|
|
14775
|
+
8,
|
|
14776
|
+
12,
|
|
14777
|
+
40,
|
|
14778
|
+
16,
|
|
14779
|
+
19,
|
|
14780
|
+
54,
|
|
14781
|
+
20,
|
|
14782
|
+
9,
|
|
14783
|
+
27,
|
|
14784
|
+
255,
|
|
14785
|
+
113,
|
|
14786
|
+
17,
|
|
14787
|
+
42,
|
|
14788
|
+
67,
|
|
14789
|
+
24,
|
|
14790
|
+
23,
|
|
14791
|
+
146,
|
|
14792
|
+
148,
|
|
14793
|
+
18,
|
|
14794
|
+
14,
|
|
14795
|
+
22,
|
|
14796
|
+
45,
|
|
14797
|
+
70,
|
|
14798
|
+
69,
|
|
14799
|
+
56,
|
|
14800
|
+
114,
|
|
14801
|
+
101,
|
|
14802
|
+
21,
|
|
14803
|
+
25,
|
|
14804
|
+
63,
|
|
14805
|
+
75,
|
|
14806
|
+
136,
|
|
14807
|
+
108,
|
|
14808
|
+
28,
|
|
14809
|
+
118,
|
|
14810
|
+
29,
|
|
14811
|
+
73,
|
|
14812
|
+
115
|
|
14813
|
+
]);
|
|
14814
|
+
if (typeof WebAssembly !== "object") {
|
|
14815
|
+
return {
|
|
14816
|
+
supported: false
|
|
14817
|
+
};
|
|
14818
|
+
}
|
|
14819
|
+
var wasm = WebAssembly.validate(detector) ? unpack(wasm_simd) : unpack(wasm_base);
|
|
14820
|
+
var instance;
|
|
14821
|
+
var ready = WebAssembly.instantiate(wasm, {}).then(function(result) {
|
|
14822
|
+
instance = result.instance;
|
|
14823
|
+
instance.exports.__wasm_call_ctors();
|
|
14824
|
+
});
|
|
14825
|
+
function unpack(data) {
|
|
14826
|
+
var result = new Uint8Array(data.length);
|
|
14827
|
+
for (var i2 = 0; i2 < data.length; ++i2) {
|
|
14828
|
+
var ch = data.charCodeAt(i2);
|
|
14829
|
+
result[i2] = ch > 96 ? ch - 97 : ch > 64 ? ch - 39 : ch + 4;
|
|
14830
|
+
}
|
|
14831
|
+
var write = 0;
|
|
14832
|
+
for (var i2 = 0; i2 < data.length; ++i2) {
|
|
14833
|
+
result[write++] = result[i2] < 60 ? wasmpack[result[i2]] : (result[i2] - 60) * 64 + result[++i2];
|
|
14834
|
+
}
|
|
14835
|
+
return result.buffer.slice(0, write);
|
|
14836
|
+
}
|
|
14837
|
+
function decode(instance2, fun, target, count, size, source, filter) {
|
|
14838
|
+
var sbrk = instance2.exports.sbrk;
|
|
14839
|
+
var count4 = count + 3 & -4;
|
|
14840
|
+
var tp = sbrk(count4 * size);
|
|
14841
|
+
var sp = sbrk(source.length);
|
|
14842
|
+
var heap = new Uint8Array(instance2.exports.memory.buffer);
|
|
14843
|
+
heap.set(source, sp);
|
|
14844
|
+
var res = fun(tp, count, size, sp, source.length);
|
|
14845
|
+
if (res == 0 && filter) {
|
|
14846
|
+
filter(tp, count4, size);
|
|
14847
|
+
}
|
|
14848
|
+
target.set(heap.subarray(tp, tp + count * size));
|
|
14849
|
+
sbrk(tp - sbrk(0));
|
|
14850
|
+
if (res != 0) {
|
|
14851
|
+
throw new Error("Malformed buffer data: " + res);
|
|
14852
|
+
}
|
|
14853
|
+
}
|
|
14854
|
+
var filters = {
|
|
14855
|
+
NONE: "",
|
|
14856
|
+
OCTAHEDRAL: "meshopt_decodeFilterOct",
|
|
14857
|
+
QUATERNION: "meshopt_decodeFilterQuat",
|
|
14858
|
+
EXPONENTIAL: "meshopt_decodeFilterExp",
|
|
14859
|
+
COLOR: "meshopt_decodeFilterColor"
|
|
14860
|
+
};
|
|
14861
|
+
var decoders = {
|
|
14862
|
+
ATTRIBUTES: "meshopt_decodeVertexBuffer",
|
|
14863
|
+
TRIANGLES: "meshopt_decodeIndexBuffer",
|
|
14864
|
+
INDICES: "meshopt_decodeIndexSequence"
|
|
14865
|
+
};
|
|
14866
|
+
var workers = [];
|
|
14867
|
+
var requestId = 0;
|
|
14868
|
+
function createWorker(url) {
|
|
14869
|
+
var worker = {
|
|
14870
|
+
object: new Worker(url),
|
|
14871
|
+
pending: 0,
|
|
14872
|
+
requests: {}
|
|
14873
|
+
};
|
|
14874
|
+
worker.object.onmessage = function(event) {
|
|
14875
|
+
var data = event.data;
|
|
14876
|
+
worker.pending -= data.count;
|
|
14877
|
+
worker.requests[data.id][data.action](data.value);
|
|
14878
|
+
delete worker.requests[data.id];
|
|
14879
|
+
};
|
|
14880
|
+
return worker;
|
|
14881
|
+
}
|
|
14882
|
+
function initWorkers(count) {
|
|
14883
|
+
var source = "self.ready = WebAssembly.instantiate(new Uint8Array([" + new Uint8Array(wasm) + "]), {}).then(function(result) { result.instance.exports.__wasm_call_ctors(); return result.instance; });self.onmessage = " + workerProcess.name + ";" + decode.toString() + workerProcess.toString();
|
|
14884
|
+
var blob = new Blob([source], { type: "text/javascript" });
|
|
14885
|
+
var url = URL.createObjectURL(blob);
|
|
14886
|
+
for (var i2 = workers.length; i2 < count; ++i2) {
|
|
14887
|
+
workers[i2] = createWorker(url);
|
|
14888
|
+
}
|
|
14889
|
+
for (var i2 = count; i2 < workers.length; ++i2) {
|
|
14890
|
+
workers[i2].object.postMessage({});
|
|
14891
|
+
}
|
|
14892
|
+
workers.length = count;
|
|
14893
|
+
URL.revokeObjectURL(url);
|
|
14894
|
+
}
|
|
14895
|
+
function decodeWorker(count, size, source, mode, filter) {
|
|
14896
|
+
var worker = workers[0];
|
|
14897
|
+
for (var i2 = 1; i2 < workers.length; ++i2) {
|
|
14898
|
+
if (workers[i2].pending < worker.pending) {
|
|
14899
|
+
worker = workers[i2];
|
|
14900
|
+
}
|
|
14901
|
+
}
|
|
14902
|
+
return new Promise(function(resolve, reject) {
|
|
14903
|
+
var data = new Uint8Array(source);
|
|
14904
|
+
var id = ++requestId;
|
|
14905
|
+
worker.pending += count;
|
|
14906
|
+
worker.requests[id] = { resolve, reject };
|
|
14907
|
+
worker.object.postMessage({ id, count, size, source: data, mode, filter }, [data.buffer]);
|
|
14908
|
+
});
|
|
14909
|
+
}
|
|
14910
|
+
function workerProcess(event) {
|
|
14911
|
+
var data = event.data;
|
|
14912
|
+
self.ready.then(function(instance2) {
|
|
14913
|
+
if (!data.id) {
|
|
14914
|
+
return self.close();
|
|
14915
|
+
}
|
|
14916
|
+
try {
|
|
14917
|
+
var target = new Uint8Array(data.count * data.size);
|
|
14918
|
+
decode(instance2, instance2.exports[data.mode], target, data.count, data.size, data.source, instance2.exports[data.filter]);
|
|
14919
|
+
self.postMessage({ id: data.id, count: data.count, action: "resolve", value: target }, [target.buffer]);
|
|
14920
|
+
} catch (error) {
|
|
14921
|
+
self.postMessage({ id: data.id, count: data.count, action: "reject", value: error });
|
|
14922
|
+
}
|
|
14923
|
+
});
|
|
14924
|
+
}
|
|
14925
|
+
return {
|
|
14926
|
+
ready,
|
|
14927
|
+
supported: true,
|
|
14928
|
+
useWorkers: function(count) {
|
|
14929
|
+
initWorkers(count);
|
|
14930
|
+
},
|
|
14931
|
+
decodeVertexBuffer: function(target, count, size, source, filter) {
|
|
14932
|
+
decode(instance, instance.exports.meshopt_decodeVertexBuffer, target, count, size, source, instance.exports[filters[filter]]);
|
|
14933
|
+
},
|
|
14934
|
+
decodeIndexBuffer: function(target, count, size, source) {
|
|
14935
|
+
decode(instance, instance.exports.meshopt_decodeIndexBuffer, target, count, size, source);
|
|
14936
|
+
},
|
|
14937
|
+
decodeIndexSequence: function(target, count, size, source) {
|
|
14938
|
+
decode(instance, instance.exports.meshopt_decodeIndexSequence, target, count, size, source);
|
|
14939
|
+
},
|
|
14940
|
+
decodeGltfBuffer: function(target, count, size, source, mode, filter) {
|
|
14941
|
+
decode(instance, instance.exports[decoders[mode]], target, count, size, source, instance.exports[filters[filter]]);
|
|
14942
|
+
},
|
|
14943
|
+
decodeGltfBufferAsync: function(count, size, source, mode, filter) {
|
|
14944
|
+
if (workers.length > 0) {
|
|
14945
|
+
return decodeWorker(count, size, source, decoders[mode], filters[filter]);
|
|
14946
|
+
}
|
|
14947
|
+
return ready.then(function() {
|
|
14948
|
+
var target = new Uint8Array(count * size);
|
|
14949
|
+
decode(instance, instance.exports[decoders[mode]], target, count, size, source, instance.exports[filters[filter]]);
|
|
14950
|
+
return target;
|
|
14951
|
+
});
|
|
14952
|
+
}
|
|
14953
|
+
};
|
|
14954
|
+
}();
|
|
14719
14955
|
var patch_default = "uniform vec3 diffuse;uniform float opacity;\n#ifndef FLAT_SHADED\nvarying vec3 vNormal;\n#endif\n#include <common>\n#include <dithering_pars_fragment>\n#include <color_pars_fragment>\n#include <uv_pars_fragment>\n#include <map_pars_fragment>\n#include <alphamap_pars_fragment>\n#include <alphatest_pars_fragment>\n#include <alphahash_pars_fragment>\n#include <aomap_pars_fragment>\n#include <lightmap_pars_fragment>\n#include <envmap_common_pars_fragment>\n#include <envmap_pars_fragment>\n#include <fog_pars_fragment>\n#include <specularmap_pars_fragment>\n#include <logdepthbuf_pars_fragment>\n#include <clipping_planes_pars_fragment>\nvoid main(){vec4 diffuseColor=vec4(diffuse,opacity);\n#include <clipping_planes_fragment>\n#include <logdepthbuf_fragment>\n#include <map_fragment>\n#include <alphamap_fragment>\n#include <alphatest_fragment>\n#include <alphahash_fragment>\n#include <specularmap_fragment>\nReflectedLight reflectedLight=ReflectedLight(vec3(0.0),vec3(0.0),vec3(0.0),vec3(0.0));\n#ifdef USE_LIGHTMAP\nvec4 lightMapTexel=texture2D(lightMap,vLightMapUv);reflectedLight.indirectDiffuse+=lightMapTexel.rgb*lightMapIntensity*RECIPROCAL_PI;\n#else\nreflectedLight.indirectDiffuse+=vec3(1.0);\n#endif\n#include <aomap_fragment>\nreflectedLight.indirectDiffuse*=diffuseColor.rgb;vec3 outgoingLight=reflectedLight.indirectDiffuse;\n#include <envmap_fragment>\n#include <opaque_fragment>\n#include <tonemapping_fragment>\n#include <colorspace_fragment>\n#include <fog_fragment>\n#include <premultiplied_alpha_fragment>\n#include <dithering_fragment>\n#ifdef USE_COLOR\ngl_FragColor.a=vColor.r;\n#endif\n}";
|
|
14956
|
+
const GAUSSIAN_FORMATS = /* @__PURE__ */ new Set(["ply", "sog", "spz", "rad"]);
|
|
14957
|
+
function requireNonEmptyString(value, field) {
|
|
14958
|
+
if (typeof value !== "string" || value.trim().length === 0) {
|
|
14959
|
+
throw new Error(`${field} must be a non-empty string.`);
|
|
14960
|
+
}
|
|
14961
|
+
}
|
|
14962
|
+
function validateGaussianSplatLayerDefinition(definition) {
|
|
14963
|
+
var _a3, _b2, _c, _d;
|
|
14964
|
+
if (!definition || typeof definition !== "object") {
|
|
14965
|
+
throw new Error("Gaussian splat layer definition must be an object.");
|
|
14966
|
+
}
|
|
14967
|
+
requireNonEmptyString(definition.id, "id");
|
|
14968
|
+
requireNonEmptyString(definition.name, "name");
|
|
14969
|
+
if (definition.type !== "gaussian-splat") {
|
|
14970
|
+
throw new Error('type must be "gaussian-splat".');
|
|
14971
|
+
}
|
|
14972
|
+
if (!Array.isArray(definition.labels) || !definition.labels.every((label) => typeof label === "string")) {
|
|
14973
|
+
throw new Error("labels must be an array of strings.");
|
|
14974
|
+
}
|
|
14975
|
+
requireNonEmptyString((_a3 = definition.data) == null ? void 0 : _a3.url, "data.url");
|
|
14976
|
+
if (!GAUSSIAN_FORMATS.has((_b2 = definition.data) == null ? void 0 : _b2.format)) {
|
|
14977
|
+
throw new Error('data.format must be "ply", "sog", "spz", or "rad".');
|
|
14978
|
+
}
|
|
14979
|
+
const renderOrder = ((_c = definition.options) == null ? void 0 : _c.renderOrder) ?? 0;
|
|
14980
|
+
if (renderOrder !== 0) {
|
|
14981
|
+
throw new Error("Gaussian splat layers only support renderOrder 0.");
|
|
14982
|
+
}
|
|
14983
|
+
const transform = (_d = definition.options) == null ? void 0 : _d.transform;
|
|
14984
|
+
const anchor = transform == null ? void 0 : transform.anchor;
|
|
14985
|
+
if (!anchor) {
|
|
14986
|
+
throw new Error("options.transform.anchor must contain finite longitude, latitude, and altitude values.");
|
|
14987
|
+
}
|
|
14988
|
+
validateGeodeticPosition(anchor.longitude, anchor.latitude, anchor.altitude, "Gaussian anchor");
|
|
14989
|
+
const translationENU = transform.translationENU ?? [0, 0, 0];
|
|
14990
|
+
const rotationDegrees = transform.rotationDegrees ?? [0, 0, 0];
|
|
14991
|
+
const scale = transform.scale ?? 1;
|
|
14992
|
+
validateTuple(translationENU, "translationENU");
|
|
14993
|
+
validateTuple(rotationDegrees, "rotationDegrees");
|
|
14994
|
+
validateScale(scale, "scale");
|
|
14995
|
+
return {
|
|
14996
|
+
...definition,
|
|
14997
|
+
labels: [...definition.labels],
|
|
14998
|
+
data: { ...definition.data },
|
|
14999
|
+
options: {
|
|
15000
|
+
...definition.options,
|
|
15001
|
+
renderOrder: 0,
|
|
15002
|
+
transform: {
|
|
15003
|
+
anchor: { ...anchor },
|
|
15004
|
+
translationENU: [...translationENU],
|
|
15005
|
+
rotationDegrees: [...rotationDegrees],
|
|
15006
|
+
scale
|
|
15007
|
+
}
|
|
15008
|
+
}
|
|
15009
|
+
};
|
|
15010
|
+
}
|
|
15011
|
+
function makeGaussianSplatTransform(transform) {
|
|
15012
|
+
const { anchor, translationENU, rotationDegrees, scale } = transform;
|
|
15013
|
+
const basis = getEnuBasis(anchor.longitude, anchor.latitude);
|
|
15014
|
+
const east = new Vector3().fromArray(basis.east);
|
|
15015
|
+
const north = new Vector3().fromArray(basis.north);
|
|
15016
|
+
const up = new Vector3().fromArray(basis.up);
|
|
15017
|
+
const enuFrame = new Matrix4().makeBasis(east, north, up);
|
|
15018
|
+
enuFrame.setPosition(new Vector3().fromArray(geodeticToEcefPosition(anchor.longitude, anchor.latitude, anchor.altitude)));
|
|
15019
|
+
const rotation = new Quaternion().setFromEuler(new Euler(rotationDegrees[0] * Math.PI / 180, rotationDegrees[1] * Math.PI / 180, rotationDegrees[2] * Math.PI / 180, "XYZ"));
|
|
15020
|
+
const localTransform = new Matrix4().compose(new Vector3().fromArray(translationENU), rotation, new Vector3(scale, scale, scale));
|
|
15021
|
+
return enuFrame.multiply(localTransform);
|
|
15022
|
+
}
|
|
15023
|
+
function normalizeLocalMeshTransform(transform) {
|
|
15024
|
+
if (!transform || typeof transform !== "object") {
|
|
15025
|
+
throw new Error("Mesh transform must be an object.");
|
|
15026
|
+
}
|
|
15027
|
+
const anchor = transform.anchor;
|
|
15028
|
+
if (!anchor) {
|
|
15029
|
+
throw new Error("Mesh transform anchor is required.");
|
|
15030
|
+
}
|
|
15031
|
+
validateGeodeticPosition(anchor.longitude, anchor.latitude, anchor.altitude, "Mesh transform anchor");
|
|
15032
|
+
const translationENU = transform.translationENU ?? [0, 0, 0];
|
|
15033
|
+
const rotationDegrees = transform.rotationDegrees ?? [90, 0, 0];
|
|
15034
|
+
const scale = transform.scale ?? 1;
|
|
15035
|
+
validateTuple(translationENU, "Mesh translationENU");
|
|
15036
|
+
validateTuple(rotationDegrees, "Mesh rotationDegrees");
|
|
15037
|
+
validateScale(scale, "Mesh scale");
|
|
15038
|
+
return { anchor: { ...anchor }, translationENU: [...translationENU], rotationDegrees: [...rotationDegrees], scale };
|
|
15039
|
+
}
|
|
14720
15040
|
class MeshLayer extends ContentLayer {
|
|
14721
15041
|
constructor(url, options = {}, callbacks = {}) {
|
|
14722
15042
|
super();
|
|
14723
15043
|
this.type = "MeshLayer";
|
|
14724
15044
|
this.isMeshLayer = true;
|
|
14725
15045
|
const renderOrder = (options == null ? void 0 : options.renderOrder) ?? 0;
|
|
14726
|
-
|
|
15046
|
+
if (options.transform !== void 0 && (options.offset !== void 0 || options.offsetOrigin !== void 0)) {
|
|
15047
|
+
throw new Error("Mesh transform and legacy offset/offsetOrigin are mutually exclusive.");
|
|
15048
|
+
}
|
|
15049
|
+
const transform = options.transform === void 0 ? null : normalizeLocalMeshTransform(options.transform);
|
|
15050
|
+
const renderLayer = transform ? 0 : 6;
|
|
15051
|
+
this.xrRenderLayer = renderLayer;
|
|
15052
|
+
const offset = transform ? { lon: 0, lat: 0, alt: 0 } : normalizeLayerOffset(options.offset, "Mesh offset");
|
|
14727
15053
|
const hasOffset = offset.lon !== 0 || offset.lat !== 0 || offset.alt !== 0;
|
|
15054
|
+
if (transform) {
|
|
15055
|
+
this.matrix.copy(makeGaussianSplatTransform(transform));
|
|
15056
|
+
this.matrix.decompose(this.position, this.quaternion, this.scale);
|
|
15057
|
+
}
|
|
15058
|
+
this.abortController = new AbortController();
|
|
15059
|
+
this.disposed = false;
|
|
14728
15060
|
const loader = new GLTFLoader();
|
|
14729
|
-
loader.
|
|
14730
|
-
|
|
14731
|
-
(
|
|
14732
|
-
|
|
14733
|
-
|
|
14734
|
-
|
|
14735
|
-
|
|
15061
|
+
loader.setMeshoptDecoder(MeshoptDecoder);
|
|
15062
|
+
if (options.decoders) {
|
|
15063
|
+
loader.setDRACOLoader(options.decoders.getDraco());
|
|
15064
|
+
loader.setKTX2Loader(options.decoders.getKTX2());
|
|
15065
|
+
}
|
|
15066
|
+
const reportError = (error) => {
|
|
15067
|
+
var _a3;
|
|
15068
|
+
if (!this.disposed && (error == null ? void 0 : error.name) !== "AbortError") {
|
|
15069
|
+
(_a3 = callbacks.onError) == null ? void 0 : _a3.call(callbacks, error instanceof Error ? error : new Error(String(error)));
|
|
15070
|
+
}
|
|
15071
|
+
};
|
|
15072
|
+
const onLoad = (gltf) => {
|
|
15073
|
+
var _a3;
|
|
15074
|
+
const root = gltf.scene;
|
|
15075
|
+
if (this.disposed) {
|
|
15076
|
+
this.disposeObjectResources(root);
|
|
15077
|
+
return;
|
|
15078
|
+
}
|
|
15079
|
+
root.traverse((child) => {
|
|
15080
|
+
child.layers.set(renderLayer);
|
|
15081
|
+
if (!transform) {
|
|
14736
15082
|
const materials = Array.isArray(child.material) ? child.material : child.material ? [child.material] : [];
|
|
14737
15083
|
for (const material of materials) {
|
|
14738
15084
|
material.transparent = true;
|
|
@@ -14740,28 +15086,32 @@ class MeshLayer extends ContentLayer {
|
|
|
14740
15086
|
program.fragmentShader = patch_default;
|
|
14741
15087
|
};
|
|
14742
15088
|
}
|
|
14743
|
-
});
|
|
14744
|
-
this.mesh = root;
|
|
14745
|
-
this.add(root);
|
|
14746
|
-
if (hasOffset) {
|
|
14747
|
-
try {
|
|
14748
|
-
const origin = options.offsetOrigin;
|
|
14749
|
-
const position = validateGeodeticPosition(origin == null ? void 0 : origin.longitude, origin == null ? void 0 : origin.latitude, origin == null ? void 0 : origin.altitude, "Mesh offset origin");
|
|
14750
|
-
this.position.fromArray(geodeticOffsetToEcefDelta({ lon: position.longitude, lat: position.latitude, alt: position.altitude }, offset));
|
|
14751
|
-
} catch (error) {
|
|
14752
|
-
(_a3 = callbacks.onError) == null ? void 0 : _a3.call(callbacks, error instanceof Error ? error : new Error(String(error)));
|
|
14753
|
-
}
|
|
14754
15089
|
}
|
|
14755
|
-
}
|
|
14756
|
-
|
|
14757
|
-
(
|
|
14758
|
-
|
|
14759
|
-
|
|
15090
|
+
});
|
|
15091
|
+
this.mesh = root;
|
|
15092
|
+
this.add(root);
|
|
15093
|
+
if (hasOffset) {
|
|
15094
|
+
try {
|
|
15095
|
+
const origin = options.offsetOrigin;
|
|
15096
|
+
const position = validateGeodeticPosition(origin == null ? void 0 : origin.longitude, origin == null ? void 0 : origin.latitude, origin == null ? void 0 : origin.altitude, "Mesh offset origin");
|
|
15097
|
+
this.position.fromArray(geodeticOffsetToEcefDelta({ lon: position.longitude, lat: position.latitude, alt: position.altitude }, offset));
|
|
15098
|
+
} catch (error) {
|
|
15099
|
+
(_a3 = callbacks.onError) == null ? void 0 : _a3.call(callbacks, error instanceof Error ? error : new Error(String(error)));
|
|
15100
|
+
}
|
|
14760
15101
|
}
|
|
14761
|
-
|
|
14762
|
-
this.
|
|
15102
|
+
};
|
|
15103
|
+
void fetch(url, { signal: this.abortController.signal }).then(async (response) => {
|
|
15104
|
+
if (!response.ok) throw new Error(`Failed to load mesh: ${response.status} ${response.statusText}`);
|
|
15105
|
+
const bytes = await response.arrayBuffer();
|
|
15106
|
+
if (this.disposed) return;
|
|
15107
|
+
loader.parse(bytes, url.slice(0, url.lastIndexOf("/") + 1), onLoad, reportError);
|
|
15108
|
+
}).catch(reportError);
|
|
15109
|
+
this.layers.set(transform ? 0 : renderOrder);
|
|
14763
15110
|
}
|
|
14764
15111
|
dispose() {
|
|
15112
|
+
if (this.disposed) return;
|
|
15113
|
+
this.disposed = true;
|
|
15114
|
+
this.abortController.abort();
|
|
14765
15115
|
super.dispose();
|
|
14766
15116
|
if (this.mesh) {
|
|
14767
15117
|
this.disposeObjectResources(this.mesh);
|
|
@@ -14770,19 +15120,24 @@ class MeshLayer extends ContentLayer {
|
|
|
14770
15120
|
}
|
|
14771
15121
|
}
|
|
14772
15122
|
}
|
|
15123
|
+
function abortError() {
|
|
15124
|
+
return new DOMException("Worker job canceled", "AbortError");
|
|
15125
|
+
}
|
|
14773
15126
|
class WorkerPool2 {
|
|
14774
15127
|
constructor(limit = 4) {
|
|
14775
15128
|
this.limit = limit;
|
|
14776
15129
|
this.queue = [];
|
|
14777
15130
|
this.workers = [];
|
|
14778
|
-
this.
|
|
15131
|
+
this.active = [];
|
|
14779
15132
|
this.workerStatus = 0;
|
|
14780
15133
|
this.workerCreator = null;
|
|
15134
|
+
this.disposed = false;
|
|
14781
15135
|
}
|
|
14782
15136
|
initWorker(workerId) {
|
|
14783
15137
|
if (!this.workers[workerId]) {
|
|
14784
15138
|
const worker = this.workerCreator();
|
|
14785
|
-
worker.addEventListener("message", this.onMessage
|
|
15139
|
+
worker.addEventListener("message", (event) => this.onMessage(workerId, worker, event));
|
|
15140
|
+
worker.addEventListener("error", (event) => this.onError(workerId, worker, event));
|
|
14786
15141
|
this.workers[workerId] = worker;
|
|
14787
15142
|
}
|
|
14788
15143
|
}
|
|
@@ -14790,15 +15145,63 @@ class WorkerPool2 {
|
|
|
14790
15145
|
for (let i2 = 0; i2 < this.limit; i2++) if (!(this.workerStatus & 1 << i2)) return i2;
|
|
14791
15146
|
return -1;
|
|
14792
15147
|
}
|
|
14793
|
-
|
|
14794
|
-
|
|
14795
|
-
|
|
14796
|
-
|
|
14797
|
-
|
|
14798
|
-
|
|
14799
|
-
|
|
14800
|
-
|
|
14801
|
-
|
|
15148
|
+
finishJob(workerId, job) {
|
|
15149
|
+
var _a3;
|
|
15150
|
+
if (this.active[workerId] !== job) return false;
|
|
15151
|
+
(_a3 = job.signal) == null ? void 0 : _a3.removeEventListener("abort", job.onAbort);
|
|
15152
|
+
this.active[workerId] = null;
|
|
15153
|
+
this.workerStatus &= ~(1 << workerId);
|
|
15154
|
+
return true;
|
|
15155
|
+
}
|
|
15156
|
+
onMessage(workerId, worker, event) {
|
|
15157
|
+
if (this.workers[workerId] !== worker) return;
|
|
15158
|
+
const job = this.active[workerId];
|
|
15159
|
+
if (!job || !this.finishJob(workerId, job)) return;
|
|
15160
|
+
job.resolve(event);
|
|
15161
|
+
this.drain();
|
|
15162
|
+
}
|
|
15163
|
+
onError(workerId, worker, event) {
|
|
15164
|
+
if (this.workers[workerId] !== worker) return;
|
|
15165
|
+
const job = this.active[workerId];
|
|
15166
|
+
if (!job || !this.finishJob(workerId, job)) return;
|
|
15167
|
+
worker.terminate();
|
|
15168
|
+
this.workers[workerId] = null;
|
|
15169
|
+
job.reject((event == null ? void 0 : event.error) ?? new Error("Worker job failed"));
|
|
15170
|
+
this.drain();
|
|
15171
|
+
}
|
|
15172
|
+
cancelJob(job) {
|
|
15173
|
+
var _a3, _b2;
|
|
15174
|
+
if (job.workerId === null) {
|
|
15175
|
+
const index = this.queue.indexOf(job);
|
|
15176
|
+
if (index < 0) return;
|
|
15177
|
+
this.queue.splice(index, 1);
|
|
15178
|
+
(_a3 = job.signal) == null ? void 0 : _a3.removeEventListener("abort", job.onAbort);
|
|
15179
|
+
job.reject(abortError());
|
|
15180
|
+
return;
|
|
15181
|
+
}
|
|
15182
|
+
const workerId = job.workerId;
|
|
15183
|
+
if (!this.finishJob(workerId, job)) return;
|
|
15184
|
+
(_b2 = this.workers[workerId]) == null ? void 0 : _b2.terminate();
|
|
15185
|
+
this.workers[workerId] = null;
|
|
15186
|
+
job.reject(abortError());
|
|
15187
|
+
this.drain();
|
|
15188
|
+
}
|
|
15189
|
+
startJob(workerId, job) {
|
|
15190
|
+
this.initWorker(workerId);
|
|
15191
|
+
job.workerId = workerId;
|
|
15192
|
+
this.active[workerId] = job;
|
|
15193
|
+
this.workerStatus |= 1 << workerId;
|
|
15194
|
+
try {
|
|
15195
|
+
this.workers[workerId].postMessage(job.msg, job.transfer);
|
|
15196
|
+
} catch (error) {
|
|
15197
|
+
this.onError(workerId, this.workers[workerId], { error });
|
|
15198
|
+
}
|
|
15199
|
+
}
|
|
15200
|
+
drain() {
|
|
15201
|
+
while (this.queue.length) {
|
|
15202
|
+
const workerId = this.getIdleWorker();
|
|
15203
|
+
if (workerId < 0) return;
|
|
15204
|
+
this.startJob(workerId, this.queue.shift());
|
|
14802
15205
|
}
|
|
14803
15206
|
}
|
|
14804
15207
|
setWorkerCreator(workerCreator) {
|
|
@@ -14806,25 +15209,35 @@ class WorkerPool2 {
|
|
|
14806
15209
|
}
|
|
14807
15210
|
setWorkerLimit(limit) {
|
|
14808
15211
|
this.limit = limit;
|
|
15212
|
+
this.drain();
|
|
14809
15213
|
}
|
|
14810
|
-
postMessage(msg, transfer) {
|
|
14811
|
-
return
|
|
14812
|
-
|
|
14813
|
-
|
|
14814
|
-
|
|
14815
|
-
|
|
14816
|
-
|
|
14817
|
-
|
|
14818
|
-
} else {
|
|
14819
|
-
this.queue.push({ resolve, msg, transfer });
|
|
14820
|
-
}
|
|
15214
|
+
postMessage(msg, transfer, { signal } = {}) {
|
|
15215
|
+
if (this.disposed || (signal == null ? void 0 : signal.aborted)) return Promise.reject(abortError());
|
|
15216
|
+
return new Promise((resolve, reject) => {
|
|
15217
|
+
const job = { msg, transfer, signal, resolve, reject, workerId: null, onAbort: null };
|
|
15218
|
+
job.onAbort = () => this.cancelJob(job);
|
|
15219
|
+
signal == null ? void 0 : signal.addEventListener("abort", job.onAbort, { once: true });
|
|
15220
|
+
this.queue.push(job);
|
|
15221
|
+
this.drain();
|
|
14821
15222
|
});
|
|
14822
15223
|
}
|
|
14823
15224
|
dispose() {
|
|
14824
|
-
|
|
14825
|
-
this.
|
|
15225
|
+
var _a3;
|
|
15226
|
+
if (this.disposed) return;
|
|
15227
|
+
this.disposed = true;
|
|
15228
|
+
for (const job of this.queue.splice(0)) {
|
|
15229
|
+
(_a3 = job.signal) == null ? void 0 : _a3.removeEventListener("abort", job.onAbort);
|
|
15230
|
+
job.reject(abortError());
|
|
15231
|
+
}
|
|
15232
|
+
for (let i2 = 0; i2 < this.active.length; i2++) {
|
|
15233
|
+
const job = this.active[i2];
|
|
15234
|
+
if (job) {
|
|
15235
|
+
this.finishJob(i2, job);
|
|
15236
|
+
job.reject(abortError());
|
|
15237
|
+
}
|
|
15238
|
+
}
|
|
15239
|
+
this.workers.forEach((worker) => worker == null ? void 0 : worker.terminate());
|
|
14826
15240
|
this.workers.length = 0;
|
|
14827
|
-
this.queue.length = 0;
|
|
14828
15241
|
this.workerStatus = 0;
|
|
14829
15242
|
}
|
|
14830
15243
|
}
|
|
@@ -14850,7 +15263,33 @@ function intersectsTimeFrame(timeFrameStart = /* @__PURE__ */ new Date(-864e13),
|
|
|
14850
15263
|
}
|
|
14851
15264
|
return true;
|
|
14852
15265
|
}
|
|
14853
|
-
class
|
|
15266
|
+
class WorkerFeature extends Object3D {
|
|
15267
|
+
constructor() {
|
|
15268
|
+
super();
|
|
15269
|
+
this.workerAbortController = new AbortController();
|
|
15270
|
+
this.disposed = false;
|
|
15271
|
+
}
|
|
15272
|
+
runWorker(message, callbacks, onSuccess) {
|
|
15273
|
+
geoWorkerPool.postMessage(message, void 0, { signal: this.workerAbortController.signal }).then((response) => {
|
|
15274
|
+
var _a3;
|
|
15275
|
+
if (this.disposed) return;
|
|
15276
|
+
const { success, error } = response.data;
|
|
15277
|
+
if (success) onSuccess(response.data);
|
|
15278
|
+
else (_a3 = callbacks.onError) == null ? void 0 : _a3.call(callbacks, new Error((error == null ? void 0 : error.message) ?? String(error)));
|
|
15279
|
+
}).catch((error) => {
|
|
15280
|
+
var _a3;
|
|
15281
|
+
if (!this.disposed && (error == null ? void 0 : error.name) !== "AbortError") {
|
|
15282
|
+
(_a3 = callbacks.onError) == null ? void 0 : _a3.call(callbacks, error instanceof Error ? error : new Error(String(error)));
|
|
15283
|
+
}
|
|
15284
|
+
});
|
|
15285
|
+
}
|
|
15286
|
+
dispose() {
|
|
15287
|
+
if (this.disposed) return;
|
|
15288
|
+
this.disposed = true;
|
|
15289
|
+
this.workerAbortController.abort();
|
|
15290
|
+
}
|
|
15291
|
+
}
|
|
15292
|
+
class ArrowFeature extends WorkerFeature {
|
|
14854
15293
|
constructor(data, options = {}, callbacks = {}) {
|
|
14855
15294
|
var _a3, _b2, _c;
|
|
14856
15295
|
super();
|
|
@@ -14861,28 +15300,22 @@ class ArrowFeature extends Object3D {
|
|
|
14861
15300
|
const type = "arrow";
|
|
14862
15301
|
const renderOrder = (options == null ? void 0 : options.renderOrder) ?? 0;
|
|
14863
15302
|
const color = ((_c = data == null ? void 0 : data.properties) == null ? void 0 : _c.color) ?? 15955057;
|
|
14864
|
-
|
|
14865
|
-
|
|
14866
|
-
const
|
|
14867
|
-
|
|
14868
|
-
|
|
14869
|
-
|
|
14870
|
-
|
|
14871
|
-
|
|
14872
|
-
|
|
14873
|
-
|
|
14874
|
-
|
|
14875
|
-
|
|
14876
|
-
const mesh = new Mesh(meshGeometry, meshMaterial);
|
|
14877
|
-
mesh.layers.set(renderOrder);
|
|
14878
|
-
this.add(mesh);
|
|
14879
|
-
} else {
|
|
14880
|
-
(_a4 = callbacks.onError) == null ? void 0 : _a4.call(callbacks, new Error((error == null ? void 0 : error.message) ?? String(error)));
|
|
14881
|
-
}
|
|
15303
|
+
this.runWorker({ type, data, color }, callbacks, ({ origin, meshVertexBuffer }) => {
|
|
15304
|
+
this.position.fromArray(origin);
|
|
15305
|
+
const meshGeometry = new BufferGeometry();
|
|
15306
|
+
meshGeometry.setAttribute("position", new BufferAttribute(meshVertexBuffer, 3));
|
|
15307
|
+
const meshMaterial = new MeshBasicMaterial({ color, side: DoubleSide, depthTest: false, opacity: 0.75, transparent: true, toneMapped: false });
|
|
15308
|
+
meshMaterial.onBeforeCompile = (program) => {
|
|
15309
|
+
program.vertexShader = annotation_default$1;
|
|
15310
|
+
program.fragmentShader = annotation_default;
|
|
15311
|
+
};
|
|
15312
|
+
const mesh = new Mesh(meshGeometry, meshMaterial);
|
|
15313
|
+
mesh.layers.set(renderOrder);
|
|
15314
|
+
this.add(mesh);
|
|
14882
15315
|
});
|
|
14883
15316
|
}
|
|
14884
15317
|
}
|
|
14885
|
-
class PerimeterFeature extends
|
|
15318
|
+
class PerimeterFeature extends WorkerFeature {
|
|
14886
15319
|
constructor(data, options = {}, callbacks = {}) {
|
|
14887
15320
|
var _a3, _b2, _c;
|
|
14888
15321
|
super();
|
|
@@ -14893,32 +15326,26 @@ class PerimeterFeature extends Object3D {
|
|
|
14893
15326
|
const type = "perimeter";
|
|
14894
15327
|
const renderOrder = (options == null ? void 0 : options.renderOrder) ?? 0;
|
|
14895
15328
|
const color = ((_c = data == null ? void 0 : data.properties) == null ? void 0 : _c.color) ?? 15955057;
|
|
14896
|
-
|
|
14897
|
-
|
|
14898
|
-
const
|
|
14899
|
-
|
|
14900
|
-
|
|
14901
|
-
|
|
14902
|
-
|
|
14903
|
-
|
|
14904
|
-
|
|
14905
|
-
|
|
14906
|
-
|
|
14907
|
-
|
|
14908
|
-
|
|
14909
|
-
|
|
14910
|
-
|
|
14911
|
-
|
|
14912
|
-
|
|
14913
|
-
|
|
14914
|
-
|
|
14915
|
-
|
|
14916
|
-
line.layers.set(renderOrder);
|
|
14917
|
-
line.add(mesh);
|
|
14918
|
-
this.add(line);
|
|
14919
|
-
} else {
|
|
14920
|
-
(_a4 = callbacks.onError) == null ? void 0 : _a4.call(callbacks, new Error((error == null ? void 0 : error.message) ?? String(error)));
|
|
14921
|
-
}
|
|
15329
|
+
this.runWorker({ type, data, color }, callbacks, ({ origin, lineVertexBuffer, lineVertexRGBBuffer, meshVertexBuffer, meshVertexRGBBuffer, meshIndexBuffer }) => {
|
|
15330
|
+
this.position.fromArray(origin);
|
|
15331
|
+
const meshGeometry = new BufferGeometry();
|
|
15332
|
+
meshGeometry.setAttribute("position", new BufferAttribute(meshVertexBuffer, 3));
|
|
15333
|
+
meshGeometry.setAttribute("color", new BufferAttribute(meshVertexRGBBuffer, 3, true));
|
|
15334
|
+
meshGeometry.setIndex(new BufferAttribute(meshIndexBuffer, 1));
|
|
15335
|
+
const meshMaterial = new MeshBasicMaterial({ opacity: 0.2, transparent: true, side: DoubleSide, depthTest: false, vertexColors: true, toneMapped: false });
|
|
15336
|
+
meshMaterial.onBeforeCompile = (program) => {
|
|
15337
|
+
program.vertexShader = annotation_default$1;
|
|
15338
|
+
program.fragmentShader = annotation_default;
|
|
15339
|
+
};
|
|
15340
|
+
const mesh = new Mesh(meshGeometry, meshMaterial);
|
|
15341
|
+
mesh.layers.set(renderOrder);
|
|
15342
|
+
const lineGeometry = new BufferGeometry();
|
|
15343
|
+
lineGeometry.setAttribute("position", new BufferAttribute(lineVertexBuffer, 3));
|
|
15344
|
+
lineGeometry.setAttribute("color", new BufferAttribute(lineVertexRGBBuffer, 3, true));
|
|
15345
|
+
const line = new LineSegments(lineGeometry, new LineBasicMaterial({ vertexColors: true, toneMapped: false }));
|
|
15346
|
+
line.layers.set(renderOrder);
|
|
15347
|
+
line.add(mesh);
|
|
15348
|
+
this.add(line);
|
|
14922
15349
|
});
|
|
14923
15350
|
}
|
|
14924
15351
|
}
|
|
@@ -14928,6 +15355,7 @@ class GeojsonLayer extends ContentLayer {
|
|
|
14928
15355
|
super();
|
|
14929
15356
|
this.type = "GeojsonLayer";
|
|
14930
15357
|
this.isGeojsonLayer = true;
|
|
15358
|
+
this.disposed = false;
|
|
14931
15359
|
for (let i2 = 0; i2 < ((_a3 = data.features) == null ? void 0 : _a3.length); i2++) {
|
|
14932
15360
|
const feature = data.features[i2];
|
|
14933
15361
|
switch (feature.properties.type) {
|
|
@@ -14957,78 +15385,13 @@ class GeojsonLayer extends ContentLayer {
|
|
|
14957
15385
|
}
|
|
14958
15386
|
}
|
|
14959
15387
|
dispose() {
|
|
15388
|
+
if (this.disposed) return;
|
|
15389
|
+
this.disposed = true;
|
|
14960
15390
|
super.dispose();
|
|
14961
15391
|
this.disposeObjectResources();
|
|
14962
15392
|
this.clear();
|
|
14963
15393
|
}
|
|
14964
15394
|
}
|
|
14965
|
-
const GAUSSIAN_FORMATS = /* @__PURE__ */ new Set(["ply", "sog", "spz", "rad"]);
|
|
14966
|
-
function requireNonEmptyString(value, field) {
|
|
14967
|
-
if (typeof value !== "string" || value.trim().length === 0) {
|
|
14968
|
-
throw new Error(`${field} must be a non-empty string.`);
|
|
14969
|
-
}
|
|
14970
|
-
}
|
|
14971
|
-
function validateGaussianSplatLayerDefinition(definition) {
|
|
14972
|
-
var _a3, _b2, _c, _d;
|
|
14973
|
-
if (!definition || typeof definition !== "object") {
|
|
14974
|
-
throw new Error("Gaussian splat layer definition must be an object.");
|
|
14975
|
-
}
|
|
14976
|
-
requireNonEmptyString(definition.id, "id");
|
|
14977
|
-
requireNonEmptyString(definition.name, "name");
|
|
14978
|
-
if (definition.type !== "gaussian-splat") {
|
|
14979
|
-
throw new Error('type must be "gaussian-splat".');
|
|
14980
|
-
}
|
|
14981
|
-
if (!Array.isArray(definition.labels) || !definition.labels.every((label) => typeof label === "string")) {
|
|
14982
|
-
throw new Error("labels must be an array of strings.");
|
|
14983
|
-
}
|
|
14984
|
-
requireNonEmptyString((_a3 = definition.data) == null ? void 0 : _a3.url, "data.url");
|
|
14985
|
-
if (!GAUSSIAN_FORMATS.has((_b2 = definition.data) == null ? void 0 : _b2.format)) {
|
|
14986
|
-
throw new Error('data.format must be "ply", "sog", "spz", or "rad".');
|
|
14987
|
-
}
|
|
14988
|
-
const renderOrder = ((_c = definition.options) == null ? void 0 : _c.renderOrder) ?? 0;
|
|
14989
|
-
if (renderOrder !== 0) {
|
|
14990
|
-
throw new Error("Gaussian splat layers only support renderOrder 0.");
|
|
14991
|
-
}
|
|
14992
|
-
const transform = (_d = definition.options) == null ? void 0 : _d.transform;
|
|
14993
|
-
const anchor = transform == null ? void 0 : transform.anchor;
|
|
14994
|
-
if (!anchor) {
|
|
14995
|
-
throw new Error("options.transform.anchor must contain finite longitude, latitude, and altitude values.");
|
|
14996
|
-
}
|
|
14997
|
-
validateGeodeticPosition(anchor.longitude, anchor.latitude, anchor.altitude, "Gaussian anchor");
|
|
14998
|
-
const translationENU = transform.translationENU ?? [0, 0, 0];
|
|
14999
|
-
const rotationDegrees = transform.rotationDegrees ?? [0, 0, 0];
|
|
15000
|
-
const scale = transform.scale ?? 1;
|
|
15001
|
-
validateTuple(translationENU, "translationENU");
|
|
15002
|
-
validateTuple(rotationDegrees, "rotationDegrees");
|
|
15003
|
-
validateScale(scale, "scale");
|
|
15004
|
-
return {
|
|
15005
|
-
...definition,
|
|
15006
|
-
labels: [...definition.labels],
|
|
15007
|
-
data: { ...definition.data },
|
|
15008
|
-
options: {
|
|
15009
|
-
...definition.options,
|
|
15010
|
-
renderOrder: 0,
|
|
15011
|
-
transform: {
|
|
15012
|
-
anchor: { ...anchor },
|
|
15013
|
-
translationENU: [...translationENU],
|
|
15014
|
-
rotationDegrees: [...rotationDegrees],
|
|
15015
|
-
scale
|
|
15016
|
-
}
|
|
15017
|
-
}
|
|
15018
|
-
};
|
|
15019
|
-
}
|
|
15020
|
-
function makeGaussianSplatTransform(transform) {
|
|
15021
|
-
const { anchor, translationENU, rotationDegrees, scale } = transform;
|
|
15022
|
-
const basis = getEnuBasis(anchor.longitude, anchor.latitude);
|
|
15023
|
-
const east = new Vector3().fromArray(basis.east);
|
|
15024
|
-
const north = new Vector3().fromArray(basis.north);
|
|
15025
|
-
const up = new Vector3().fromArray(basis.up);
|
|
15026
|
-
const enuFrame = new Matrix4().makeBasis(east, north, up);
|
|
15027
|
-
enuFrame.setPosition(new Vector3().fromArray(geodeticToEcefPosition(anchor.longitude, anchor.latitude, anchor.altitude)));
|
|
15028
|
-
const rotation = new Quaternion().setFromEuler(new Euler(rotationDegrees[0] * Math.PI / 180, rotationDegrees[1] * Math.PI / 180, rotationDegrees[2] * Math.PI / 180, "XYZ"));
|
|
15029
|
-
const localTransform = new Matrix4().compose(new Vector3().fromArray(translationENU), rotation, new Vector3(scale, scale, scale));
|
|
15030
|
-
return enuFrame.multiply(localTransform);
|
|
15031
|
-
}
|
|
15032
15395
|
function formatType(spark, format) {
|
|
15033
15396
|
return { ply: spark.SplatFileType.PLY, sog: spark.SplatFileType.PCSOGSZIP, spz: spark.SplatFileType.SPZ, rad: spark.SplatFileType.RAD }[format];
|
|
15034
15397
|
}
|
|
@@ -15054,6 +15417,10 @@ class GaussianSplatLayer extends ContentLayer {
|
|
|
15054
15417
|
}
|
|
15055
15418
|
setEnabled(enabled) {
|
|
15056
15419
|
if (this.loadState === "disposed") return;
|
|
15420
|
+
if (!enabled) {
|
|
15421
|
+
this.dispose();
|
|
15422
|
+
return;
|
|
15423
|
+
}
|
|
15057
15424
|
const wasEnabled = this.visible;
|
|
15058
15425
|
this.visible = enabled;
|
|
15059
15426
|
if (enabled && !wasEnabled && (this.loadState === "idle" || this.loadState === "error")) {
|
|
@@ -15141,9 +15508,11 @@ class GaussianSplatLayer extends ContentLayer {
|
|
|
15141
15508
|
});
|
|
15142
15509
|
}
|
|
15143
15510
|
disposeMesh(mesh) {
|
|
15511
|
+
var _a3, _b2;
|
|
15144
15512
|
if (!mesh || mesh.userData.gaussianSplatDisposed) return;
|
|
15145
15513
|
mesh.userData.gaussianSplatDisposed = true;
|
|
15146
15514
|
mesh.removeFromParent();
|
|
15515
|
+
if (mesh.paged) (_b2 = (_a3 = this.callbacks).releasePagedSplats) == null ? void 0 : _b2.call(_a3, mesh.paged);
|
|
15147
15516
|
mesh.dispose();
|
|
15148
15517
|
if (this.splatMesh === mesh) this.splatMesh = null;
|
|
15149
15518
|
}
|
|
@@ -15159,6 +15528,197 @@ class GaussianSplatLayer extends ContentLayer {
|
|
|
15159
15528
|
super.dispose();
|
|
15160
15529
|
}
|
|
15161
15530
|
}
|
|
15531
|
+
class ContentLayerRegistry {
|
|
15532
|
+
/** @param {{ group?: import('three').Group, createLayer?: (definition: any) => any, onError?: (definition: any, error: Error) => void, onAllSplatsDisabled?: () => void }} [options] */
|
|
15533
|
+
constructor({ group, createLayer, onError, onAllSplatsDisabled } = {}) {
|
|
15534
|
+
this.group = group;
|
|
15535
|
+
this.createLayer = createLayer;
|
|
15536
|
+
this.onError = onError;
|
|
15537
|
+
this.onAllSplatsDisabled = onAllSplatsDisabled;
|
|
15538
|
+
this.definitions = [];
|
|
15539
|
+
this.enabledLabels = /* @__PURE__ */ new Set();
|
|
15540
|
+
this.active = /* @__PURE__ */ new Map();
|
|
15541
|
+
this.timeFrameStart = null;
|
|
15542
|
+
this.timeFrameEnd = null;
|
|
15543
|
+
this.disposed = false;
|
|
15544
|
+
}
|
|
15545
|
+
setDefinitions(definitions = []) {
|
|
15546
|
+
if (this.disposed) return;
|
|
15547
|
+
this.clear();
|
|
15548
|
+
this.definitions = [...definitions];
|
|
15549
|
+
this.reconcile();
|
|
15550
|
+
}
|
|
15551
|
+
setEnabledLabels(labels = []) {
|
|
15552
|
+
if (this.disposed) return;
|
|
15553
|
+
this.enabledLabels = new Set(labels);
|
|
15554
|
+
this.reconcile();
|
|
15555
|
+
}
|
|
15556
|
+
setTimeFrame(start, end) {
|
|
15557
|
+
var _a3;
|
|
15558
|
+
if (this.disposed) return;
|
|
15559
|
+
this.timeFrameStart = start;
|
|
15560
|
+
this.timeFrameEnd = end;
|
|
15561
|
+
for (const layer of this.active.values()) (_a3 = layer.setTimeFrame) == null ? void 0 : _a3.call(layer, start, end);
|
|
15562
|
+
}
|
|
15563
|
+
getActiveLayer(id) {
|
|
15564
|
+
return this.active.get(id) ?? null;
|
|
15565
|
+
}
|
|
15566
|
+
createActiveLayer(definition) {
|
|
15567
|
+
var _a3, _b2, _c, _d, _e;
|
|
15568
|
+
const layer = this.createLayer(definition);
|
|
15569
|
+
try {
|
|
15570
|
+
layer.contentLayerId = definition.id;
|
|
15571
|
+
layer.setLabels(definition.labels);
|
|
15572
|
+
layer.contentRenderOrder = definition.type === "mesh" && ((_a3 = definition.options) == null ? void 0 : _a3.transform) ? 0 : ((_b2 = definition.options) == null ? void 0 : _b2.renderOrder) ?? 0;
|
|
15573
|
+
layer.xrRenderLayer = layer.xrRenderLayer ?? (definition.type === "mesh" && ((_c = definition.options) == null ? void 0 : _c.transform) ? 0 : definition.type === "mesh" ? 6 : layer.contentRenderOrder);
|
|
15574
|
+
(_d = layer.setTimeFrame) == null ? void 0 : _d.call(layer, this.timeFrameStart, this.timeFrameEnd);
|
|
15575
|
+
layer.setEnabled(true);
|
|
15576
|
+
return layer;
|
|
15577
|
+
} catch (error) {
|
|
15578
|
+
(_e = layer.dispose) == null ? void 0 : _e.call(layer);
|
|
15579
|
+
throw error;
|
|
15580
|
+
}
|
|
15581
|
+
}
|
|
15582
|
+
orderActiveLayers() {
|
|
15583
|
+
const order = new Map(this.definitions.map((definition, index) => [definition.id, index]));
|
|
15584
|
+
this.group.children.sort((a2, b2) => (order.get(a2.contentLayerId) ?? 0) - (order.get(b2.contentLayerId) ?? 0));
|
|
15585
|
+
}
|
|
15586
|
+
/** Replace one definition while preserving unrelated live layers. */
|
|
15587
|
+
replaceDefinition(id, definition) {
|
|
15588
|
+
var _a3, _b2, _c, _d;
|
|
15589
|
+
if (this.disposed) return false;
|
|
15590
|
+
const index = this.definitions.findIndex((item) => item.id === id);
|
|
15591
|
+
const wanted = ((_a3 = definition == null ? void 0 : definition.labels) == null ? void 0 : _a3.some((label) => this.enabledLabels.has(label))) ?? false;
|
|
15592
|
+
let incoming = null;
|
|
15593
|
+
if (wanted) {
|
|
15594
|
+
try {
|
|
15595
|
+
incoming = this.createActiveLayer(definition);
|
|
15596
|
+
} catch (error) {
|
|
15597
|
+
(_b2 = this.onError) == null ? void 0 : _b2.call(this, definition, error);
|
|
15598
|
+
return false;
|
|
15599
|
+
}
|
|
15600
|
+
}
|
|
15601
|
+
const outgoing = this.active.get(id);
|
|
15602
|
+
const hadSplats = [...this.active.values()].some((layer) => layer.isGaussianSplatLayer);
|
|
15603
|
+
if (outgoing) {
|
|
15604
|
+
(_c = outgoing.dispose) == null ? void 0 : _c.call(outgoing);
|
|
15605
|
+
this.group.remove(outgoing);
|
|
15606
|
+
this.active.delete(id);
|
|
15607
|
+
}
|
|
15608
|
+
if (definition) {
|
|
15609
|
+
if (index < 0) this.definitions.push(definition);
|
|
15610
|
+
else this.definitions[index] = definition;
|
|
15611
|
+
} else if (index >= 0) this.definitions.splice(index, 1);
|
|
15612
|
+
if (incoming) {
|
|
15613
|
+
this.group.add(incoming);
|
|
15614
|
+
this.active.set(id, incoming);
|
|
15615
|
+
}
|
|
15616
|
+
this.orderActiveLayers();
|
|
15617
|
+
if (hadSplats && ![...this.active.values()].some((layer) => layer.isGaussianSplatLayer)) (_d = this.onAllSplatsDisabled) == null ? void 0 : _d.call(this);
|
|
15618
|
+
return true;
|
|
15619
|
+
}
|
|
15620
|
+
reconcile() {
|
|
15621
|
+
var _a3, _b2, _c;
|
|
15622
|
+
const wanted = new Set(this.definitions.filter((definition) => {
|
|
15623
|
+
var _a4;
|
|
15624
|
+
return (_a4 = definition.labels) == null ? void 0 : _a4.some((label) => this.enabledLabels.has(label));
|
|
15625
|
+
}).map((definition) => definition.id));
|
|
15626
|
+
const hadSplats = [...this.active.values()].some((layer) => layer.isGaussianSplatLayer);
|
|
15627
|
+
for (const [id, layer] of this.active) {
|
|
15628
|
+
if (!wanted.has(id)) {
|
|
15629
|
+
(_a3 = layer.dispose) == null ? void 0 : _a3.call(layer);
|
|
15630
|
+
this.group.remove(layer);
|
|
15631
|
+
this.active.delete(id);
|
|
15632
|
+
}
|
|
15633
|
+
}
|
|
15634
|
+
for (const definition of this.definitions) {
|
|
15635
|
+
if (!wanted.has(definition.id) || this.active.has(definition.id)) continue;
|
|
15636
|
+
try {
|
|
15637
|
+
const layer = this.createActiveLayer(definition);
|
|
15638
|
+
this.group.add(layer);
|
|
15639
|
+
this.active.set(definition.id, layer);
|
|
15640
|
+
} catch (error) {
|
|
15641
|
+
(_b2 = this.onError) == null ? void 0 : _b2.call(this, definition, error);
|
|
15642
|
+
}
|
|
15643
|
+
}
|
|
15644
|
+
this.orderActiveLayers();
|
|
15645
|
+
if (hadSplats && ![...this.active.values()].some((layer) => layer.isGaussianSplatLayer)) (_c = this.onAllSplatsDisabled) == null ? void 0 : _c.call(this);
|
|
15646
|
+
}
|
|
15647
|
+
clear() {
|
|
15648
|
+
var _a3, _b2;
|
|
15649
|
+
for (const layer of this.active.values()) {
|
|
15650
|
+
(_a3 = layer.dispose) == null ? void 0 : _a3.call(layer);
|
|
15651
|
+
this.group.remove(layer);
|
|
15652
|
+
}
|
|
15653
|
+
const hadSplats = [...this.active.values()].some((layer) => layer.isGaussianSplatLayer);
|
|
15654
|
+
this.active.clear();
|
|
15655
|
+
this.definitions = [];
|
|
15656
|
+
if (hadSplats) (_b2 = this.onAllSplatsDisabled) == null ? void 0 : _b2.call(this);
|
|
15657
|
+
}
|
|
15658
|
+
dispose() {
|
|
15659
|
+
if (this.disposed) return;
|
|
15660
|
+
this.clear();
|
|
15661
|
+
this.disposed = true;
|
|
15662
|
+
}
|
|
15663
|
+
}
|
|
15664
|
+
class SplatDestinationPrefetch {
|
|
15665
|
+
constructor({ getRenderer, getLayer }) {
|
|
15666
|
+
this.getRenderer = getRenderer;
|
|
15667
|
+
this.getLayer = getLayer;
|
|
15668
|
+
this.target = null;
|
|
15669
|
+
this.boundRenderer = null;
|
|
15670
|
+
this.boundMeshes = [];
|
|
15671
|
+
this.timeoutId = null;
|
|
15672
|
+
this.disposed = false;
|
|
15673
|
+
}
|
|
15674
|
+
set(target) {
|
|
15675
|
+
if (this.disposed || !target || !Number.isFinite(target.timeoutMs) || target.timeoutMs <= 0 || target.timeoutMs > 3e4) return;
|
|
15676
|
+
this.clear("cancel");
|
|
15677
|
+
this.target = target;
|
|
15678
|
+
this.timeoutId = setTimeout(() => this.clear("timeout"), target.timeoutMs);
|
|
15679
|
+
this.sync();
|
|
15680
|
+
}
|
|
15681
|
+
sync() {
|
|
15682
|
+
var _a3;
|
|
15683
|
+
if (this.disposed || !this.target) return;
|
|
15684
|
+
const renderer = this.getRenderer();
|
|
15685
|
+
const meshes = [...new Set(this.target.layerIds)].map((id) => this.getLayer(id)).filter(
|
|
15686
|
+
(layer) => {
|
|
15687
|
+
var _a4, _b2, _c;
|
|
15688
|
+
return (layer == null ? void 0 : layer.isGaussianSplatLayer) && layer.visible && ((_b2 = (_a4 = layer.definition) == null ? void 0 : _a4.data) == null ? void 0 : _b2.format) === "rad" && ((_c = layer.splatMesh) == null ? void 0 : _c.paged) && layer.loadState !== "disposed";
|
|
15689
|
+
}
|
|
15690
|
+
).map((layer) => layer.splatMesh);
|
|
15691
|
+
if (renderer === this.boundRenderer && meshes.length === this.boundMeshes.length && meshes.every((mesh, i2) => mesh === this.boundMeshes[i2])) return;
|
|
15692
|
+
(_a3 = this.boundRenderer) == null ? void 0 : _a3.clearDestinationHint(false);
|
|
15693
|
+
this.boundRenderer = null;
|
|
15694
|
+
this.boundMeshes = [];
|
|
15695
|
+
if (!renderer || meshes.length === 0) return;
|
|
15696
|
+
const target = this.target;
|
|
15697
|
+
renderer.setDestinationHint({
|
|
15698
|
+
position: new Vector3().fromArray(geodeticToEcefPosition(target.longitude, target.latitude, target.altitude)),
|
|
15699
|
+
quaternion: geodeticToEcefRotation(target.longitude, target.latitude, target.pitch, target.yaw, target.roll),
|
|
15700
|
+
meshes,
|
|
15701
|
+
maxChunks: target.mode === "xr" ? 1 : 4,
|
|
15702
|
+
maxSplats: 3e4
|
|
15703
|
+
});
|
|
15704
|
+
this.boundRenderer = renderer;
|
|
15705
|
+
this.boundMeshes = meshes;
|
|
15706
|
+
}
|
|
15707
|
+
clear(reason = "cancel") {
|
|
15708
|
+
var _a3;
|
|
15709
|
+
if (this.timeoutId !== null) clearTimeout(this.timeoutId);
|
|
15710
|
+
this.timeoutId = null;
|
|
15711
|
+
this.target = null;
|
|
15712
|
+
(_a3 = this.boundRenderer) == null ? void 0 : _a3.clearDestinationHint(reason === "arrival");
|
|
15713
|
+
this.boundRenderer = null;
|
|
15714
|
+
this.boundMeshes = [];
|
|
15715
|
+
}
|
|
15716
|
+
dispose() {
|
|
15717
|
+
if (this.disposed) return;
|
|
15718
|
+
this.clear("cancel");
|
|
15719
|
+
this.disposed = true;
|
|
15720
|
+
}
|
|
15721
|
+
}
|
|
15162
15722
|
function applyKeyboardMovement(position, forward, right, up, state, deltaTime, movementSpeed, boostMultiplier) {
|
|
15163
15723
|
const boost = state.BOOST ? boostMultiplier : 1;
|
|
15164
15724
|
const distance = movementSpeed * deltaTime * boost;
|
|
@@ -15533,127 +16093,47 @@ class XRNavigationCue {
|
|
|
15533
16093
|
this.scene.remove(this.group);
|
|
15534
16094
|
}
|
|
15535
16095
|
}
|
|
15536
|
-
const
|
|
15537
|
-
|
|
15538
|
-
const HEAD_PANEL_OFFSET = new Matrix4().makeTranslation(-0.35, -0.55, -1.2);
|
|
15539
|
-
function attributionText(tileAttributions = [], terrainCredits = []) {
|
|
15540
|
-
const values = [
|
|
15541
|
-
...tileAttributions.filter(({ type, value }) => type === "string" && typeof value === "string").map(({ value }) => value),
|
|
15542
|
-
...terrainCredits.filter((value) => typeof value === "string")
|
|
15543
|
-
];
|
|
15544
|
-
return [...new Set(values.map((value) => value.replace(/<[^>]+>/g, "").replace(/&/g, "&").replace(/ /g, " ").replace(/</g, "<").replace(/>/g, ">").trim()).filter(Boolean))];
|
|
15545
|
-
}
|
|
15546
|
-
function wrap(ctx, value, maxWidth) {
|
|
15547
|
-
const lines = [];
|
|
15548
|
-
let line = "";
|
|
15549
|
-
const words = value.split(/\s+/).flatMap((word) => {
|
|
15550
|
-
if (ctx.measureText(word).width <= maxWidth) return [word];
|
|
15551
|
-
const pieces = [];
|
|
15552
|
-
let piece = "";
|
|
15553
|
-
for (const character of word) {
|
|
15554
|
-
if (piece && ctx.measureText(piece + character).width > maxWidth) {
|
|
15555
|
-
pieces.push(piece);
|
|
15556
|
-
piece = "";
|
|
15557
|
-
}
|
|
15558
|
-
piece += character;
|
|
15559
|
-
}
|
|
15560
|
-
if (piece) pieces.push(piece);
|
|
15561
|
-
return pieces;
|
|
15562
|
-
});
|
|
15563
|
-
for (const word of words) {
|
|
15564
|
-
const candidate = line ? `${line} ${word}` : word;
|
|
15565
|
-
if (line && ctx.measureText(candidate).width > maxWidth) {
|
|
15566
|
-
lines.push(line);
|
|
15567
|
-
line = word;
|
|
15568
|
-
} else line = candidate;
|
|
15569
|
-
}
|
|
15570
|
-
if (line) lines.push(line);
|
|
15571
|
-
return lines;
|
|
15572
|
-
}
|
|
15573
|
-
function layoutAttributionLines(ctx, values) {
|
|
15574
|
-
const lines = values.flatMap((value) => wrap(ctx, value, 540));
|
|
15575
|
-
const rows = Math.max(1, Math.ceil(lines.length / 2));
|
|
15576
|
-
const lineHeight = Math.min(38, 230 / rows);
|
|
15577
|
-
const fontSize = Math.min(32, lineHeight - 4);
|
|
15578
|
-
return lines.map((text, index) => ({
|
|
15579
|
-
text,
|
|
15580
|
-
x: index < rows ? 30 : 630,
|
|
15581
|
-
y: 120 + index % rows * lineHeight,
|
|
15582
|
-
fontSize
|
|
15583
|
-
}));
|
|
15584
|
-
}
|
|
15585
|
-
class XRAttributionPanel {
|
|
16096
|
+
const HEAD_OFFSET = new Matrix4().makeTranslation(0.35, -0.32, -0.9);
|
|
16097
|
+
class XRDiagnosticsPanel {
|
|
15586
16098
|
constructor() {
|
|
15587
16099
|
const canvas = document.createElement("canvas");
|
|
15588
|
-
canvas.width =
|
|
15589
|
-
canvas.height =
|
|
15590
|
-
this.canvas = canvas;
|
|
16100
|
+
canvas.width = 480;
|
|
16101
|
+
canvas.height = 220;
|
|
15591
16102
|
this.context = canvas.getContext("2d");
|
|
15592
16103
|
this.texture = new CanvasTexture(canvas);
|
|
15593
16104
|
this.texture.colorSpace = SRGBColorSpace;
|
|
15594
|
-
this.mesh = new Mesh(new PlaneGeometry(
|
|
15595
|
-
this.mesh.name = "
|
|
16105
|
+
this.mesh = new Mesh(new PlaneGeometry(0.42, 0.1925), new MeshBasicMaterial({ map: this.texture, transparent: true, depthTest: false, depthWrite: false, side: DoubleSide, toneMapped: false }));
|
|
16106
|
+
this.mesh.name = "XRDiagnosticsPanel";
|
|
15596
16107
|
this.mesh.matrixAutoUpdate = false;
|
|
15597
16108
|
this.mesh.layers.set(31);
|
|
15598
|
-
this.mesh.renderOrder =
|
|
15599
|
-
this.
|
|
15600
|
-
this.lastText = "";
|
|
15601
|
-
this.lastTileCheckMs = -Infinity;
|
|
15602
|
-
this.tileCredits = [];
|
|
15603
|
-
this.logos = [];
|
|
15604
|
-
for (const url of [cesiumLogoUrl, googleLogoUrl]) {
|
|
15605
|
-
const image = new Image();
|
|
15606
|
-
image.onload = () => this.draw();
|
|
15607
|
-
image.src = url;
|
|
15608
|
-
this.logos.push(image);
|
|
15609
|
-
}
|
|
15610
|
-
this.draw();
|
|
15611
|
-
}
|
|
15612
|
-
setTerrainCredits(credits) {
|
|
15613
|
-
this.terrainCredits = Array.isArray(credits) ? credits : [];
|
|
15614
|
-
this.draw();
|
|
15615
|
-
}
|
|
15616
|
-
update(headMatrix, tiles, timeMs) {
|
|
15617
|
-
var _a3;
|
|
15618
|
-
this.mesh.matrix.copy(headMatrix).multiply(HEAD_PANEL_OFFSET);
|
|
15619
|
-
this.mesh.matrixWorldNeedsUpdate = true;
|
|
15620
|
-
if (timeMs - this.lastTileCheckMs >= 1e3) {
|
|
15621
|
-
this.lastTileCheckMs = timeMs;
|
|
15622
|
-
this.tileCredits = ((_a3 = tiles == null ? void 0 : tiles.getAttributions) == null ? void 0 : _a3.call(tiles)) ?? [];
|
|
15623
|
-
this.draw();
|
|
15624
|
-
}
|
|
16109
|
+
this.mesh.renderOrder = 10003;
|
|
16110
|
+
this.rows = [];
|
|
15625
16111
|
}
|
|
15626
|
-
|
|
15627
|
-
|
|
16112
|
+
setRows(rows) {
|
|
16113
|
+
this.rows = rows.slice(0, 5).map(String);
|
|
15628
16114
|
const ctx = this.context;
|
|
15629
16115
|
if (!ctx) return;
|
|
15630
|
-
|
|
15631
|
-
|
|
15632
|
-
|
|
15633
|
-
|
|
15634
|
-
ctx.
|
|
15635
|
-
ctx.fillStyle = "
|
|
15636
|
-
ctx.fillRect(0, 0, 1200, 360);
|
|
15637
|
-
ctx.fillStyle = "#1b2430";
|
|
15638
|
-
ctx.font = "bold 28px Arial, sans-serif";
|
|
15639
|
-
if (((_a3 = this.logos[0]) == null ? void 0 : _a3.complete) && this.logos[0].naturalWidth > 0) ctx.drawImage(this.logos[0], 30, 22, 294, 50);
|
|
15640
|
-
else ctx.fillText("Cesium ion", 30, 61);
|
|
15641
|
-
if (((_b2 = this.logos[1]) == null ? void 0 : _b2.complete) && this.logos[1].naturalWidth > 0) ctx.drawImage(this.logos[1], 390, 28, 272, 50);
|
|
15642
|
-
else ctx.fillText("Google Maps", 390, 61);
|
|
16116
|
+
ctx.clearRect(0, 0, 480, 220);
|
|
16117
|
+
ctx.fillStyle = "rgba(17,24,39,0.9)";
|
|
16118
|
+
ctx.beginPath();
|
|
16119
|
+
ctx.roundRect(0, 0, 480, 220, 24);
|
|
16120
|
+
ctx.fill();
|
|
16121
|
+
ctx.fillStyle = "#e5e7eb";
|
|
15643
16122
|
ctx.font = "32px Arial, sans-serif";
|
|
15644
|
-
|
|
15645
|
-
ctx.font = `${line.fontSize}px Arial, sans-serif`;
|
|
15646
|
-
ctx.fillText(line.text, line.x, line.y);
|
|
15647
|
-
}
|
|
16123
|
+
this.rows.forEach((row, index) => ctx.fillText(row, 24, 45 + index * 39, 432));
|
|
15648
16124
|
this.texture.needsUpdate = true;
|
|
15649
16125
|
}
|
|
16126
|
+
update(headMatrix) {
|
|
16127
|
+
this.mesh.matrix.copy(headMatrix).multiply(HEAD_OFFSET);
|
|
16128
|
+
this.mesh.matrixWorldNeedsUpdate = true;
|
|
16129
|
+
}
|
|
15650
16130
|
dispose() {
|
|
15651
16131
|
this.mesh.geometry.dispose();
|
|
15652
16132
|
this.mesh.material.dispose();
|
|
15653
16133
|
this.texture.dispose();
|
|
15654
16134
|
}
|
|
15655
16135
|
}
|
|
15656
|
-
function createXRRenderBridge(viewer, initialHeadPose,
|
|
16136
|
+
function createXRRenderBridge(viewer, initialHeadPose, _options = {}) {
|
|
15657
16137
|
const { camera, renderer } = viewer;
|
|
15658
16138
|
if (camera.parent !== null) throw new Error("WebXR camera bridge requires an unparented viewer camera");
|
|
15659
16139
|
camera.updateMatrixWorld(true);
|
|
@@ -15668,24 +16148,22 @@ function createXRRenderBridge(viewer, initialHeadPose, { showAttribution = true
|
|
|
15668
16148
|
let currentHead = camera.matrix.clone().fromArray(initialHeadPose.matrix);
|
|
15669
16149
|
let disposed = false;
|
|
15670
16150
|
const comfort = new XRComfortOverlay();
|
|
15671
|
-
|
|
16151
|
+
let diagnostics = null;
|
|
15672
16152
|
const navigationCue = new XRNavigationCue(viewer.scene);
|
|
15673
16153
|
anchor.add(comfort.mesh);
|
|
15674
|
-
if (attribution) anchor.add(attribution.mesh);
|
|
15675
16154
|
const restoreWorldPose = (world) => {
|
|
15676
16155
|
if (camera.parent === anchor) anchor.remove(camera);
|
|
15677
16156
|
world.decompose(camera.position, camera.quaternion, camera.scale);
|
|
15678
16157
|
camera.updateMatrixWorld(true);
|
|
15679
16158
|
};
|
|
15680
16159
|
const renderBridge = (scene, renderCamera) => {
|
|
15681
|
-
var _a3;
|
|
15682
16160
|
if (disposed || renderCamera !== camera) return originalRender.call(renderer, scene, renderCamera);
|
|
15683
16161
|
camera.updateMatrixWorld(true);
|
|
15684
16162
|
const worldBeforeRender = camera.matrixWorld.clone();
|
|
15685
16163
|
anchor.matrix.copy(rig.getVisualWorldFromLocalMatrix());
|
|
15686
16164
|
anchor.updateMatrixWorld(true);
|
|
15687
16165
|
comfort.update(currentHead);
|
|
15688
|
-
|
|
16166
|
+
diagnostics == null ? void 0 : diagnostics.update(currentHead);
|
|
15689
16167
|
anchor.add(camera);
|
|
15690
16168
|
currentHead.decompose(camera.position, camera.quaternion, camera.scale);
|
|
15691
16169
|
camera.updateMatrixWorld(true);
|
|
@@ -15708,7 +16186,26 @@ function createXRRenderBridge(viewer, initialHeadPose, { showAttribution = true
|
|
|
15708
16186
|
getHeadForward: () => rig.getVisualHeadForward(),
|
|
15709
16187
|
getControllerWorldRay: (controller) => rig.getControllerWorldRay(controller),
|
|
15710
16188
|
setNavigationCue: (cue) => navigationCue.set(cue),
|
|
15711
|
-
setTerrainCredits: (
|
|
16189
|
+
setTerrainCredits: () => {
|
|
16190
|
+
},
|
|
16191
|
+
setDiagnosticsRows(rows) {
|
|
16192
|
+
if (disposed) return;
|
|
16193
|
+
if (!Array.isArray(rows) || rows.length === 0) {
|
|
16194
|
+
if (diagnostics) {
|
|
16195
|
+
anchor.remove(diagnostics.mesh);
|
|
16196
|
+
diagnostics.dispose();
|
|
16197
|
+
diagnostics = null;
|
|
16198
|
+
}
|
|
16199
|
+
return;
|
|
16200
|
+
}
|
|
16201
|
+
if (!diagnostics) {
|
|
16202
|
+
if (typeof document === "undefined") return;
|
|
16203
|
+
diagnostics = new XRDiagnosticsPanel();
|
|
16204
|
+
anchor.add(diagnostics.mesh);
|
|
16205
|
+
}
|
|
16206
|
+
diagnostics.setRows(rows);
|
|
16207
|
+
diagnostics.update(currentHead);
|
|
16208
|
+
},
|
|
15712
16209
|
setPlayerPose(pose) {
|
|
15713
16210
|
if (disposed) return;
|
|
15714
16211
|
rig.setPose(pose);
|
|
@@ -15720,7 +16217,7 @@ function createXRRenderBridge(viewer, initialHeadPose, { showAttribution = true
|
|
|
15720
16217
|
restoreWorldPose(rig.getVisualWorldHeadMatrix());
|
|
15721
16218
|
},
|
|
15722
16219
|
hasUi() {
|
|
15723
|
-
return Boolean(
|
|
16220
|
+
return Boolean(diagnostics) || comfort.moving || comfort.navigationLimit !== null || comfort.fade > 0;
|
|
15724
16221
|
},
|
|
15725
16222
|
setNavigationLimit(reason) {
|
|
15726
16223
|
if (comfort.setNavigationLimit(reason)) comfort.update(currentHead);
|
|
@@ -15748,9 +16245,10 @@ function createXRRenderBridge(viewer, initialHeadPose, { showAttribution = true
|
|
|
15748
16245
|
if (camera.parent === anchor) restoreWorldPose(rig.getVisualWorldHeadMatrix());
|
|
15749
16246
|
anchor.remove(comfort.mesh);
|
|
15750
16247
|
comfort.dispose();
|
|
15751
|
-
if (
|
|
15752
|
-
anchor.remove(
|
|
15753
|
-
|
|
16248
|
+
if (diagnostics) {
|
|
16249
|
+
anchor.remove(diagnostics.mesh);
|
|
16250
|
+
diagnostics.dispose();
|
|
16251
|
+
diagnostics = null;
|
|
15754
16252
|
}
|
|
15755
16253
|
navigationCue.dispose();
|
|
15756
16254
|
viewer.scene.remove(anchor);
|
|
@@ -15763,7 +16261,6 @@ class WebXRSession {
|
|
|
15763
16261
|
this.viewer = viewer;
|
|
15764
16262
|
this.onFrame = options.onFrame;
|
|
15765
16263
|
this.onStateChange = options.onStateChange;
|
|
15766
|
-
this.showAttribution = options.showAttribution !== false;
|
|
15767
16264
|
this.session = null;
|
|
15768
16265
|
this.starting = null;
|
|
15769
16266
|
this.bridge = null;
|
|
@@ -15873,8 +16370,10 @@ class WebXRSession {
|
|
|
15873
16370
|
if (!referenceSpace) return;
|
|
15874
16371
|
const pose = frame.getViewerPose(referenceSpace);
|
|
15875
16372
|
if (!pose) return;
|
|
15876
|
-
if (!this.bridge)
|
|
15877
|
-
|
|
16373
|
+
if (!this.bridge) {
|
|
16374
|
+
this.bridge = createXRRenderBridge(this.viewer, pose.transform, { showAttribution: false });
|
|
16375
|
+
this.bridge.setDiagnosticsRows(this.viewer.xrDiagnosticsRows);
|
|
16376
|
+
} else this.bridge.updateHeadPose(pose.transform);
|
|
15878
16377
|
(_a3 = this.onFrame) == null ? void 0 : _a3.call(this, { time, frame, pose });
|
|
15879
16378
|
this.applySparkProfile(this.viewer.sparkRenderer);
|
|
15880
16379
|
this.viewer.animate(time);
|
|
@@ -15980,6 +16479,85 @@ function readXRFrameInput(frame, referenceSpace) {
|
|
|
15980
16479
|
});
|
|
15981
16480
|
return { head, controllers };
|
|
15982
16481
|
}
|
|
16482
|
+
class DesktopLookControls {
|
|
16483
|
+
constructor(canvas, onLook) {
|
|
16484
|
+
var _a3;
|
|
16485
|
+
this.canvas = canvas;
|
|
16486
|
+
this.onLook = onLook;
|
|
16487
|
+
this.root = canvas.ownerDocument ?? canvas.getRootNode();
|
|
16488
|
+
this.window = this.root.defaultView ?? (typeof window === "undefined" ? null : window);
|
|
16489
|
+
this.pointer = null;
|
|
16490
|
+
this.down = (event) => {
|
|
16491
|
+
if (event.pointerType !== "mouse" || event.buttons !== 1 && event.buttons !== 2 || this.pointer) return;
|
|
16492
|
+
this.pointer = { id: event.pointerId, startX: event.clientX, startY: event.clientY, x: event.clientX, y: event.clientY, dragging: false };
|
|
16493
|
+
};
|
|
16494
|
+
this.move = (event) => {
|
|
16495
|
+
var _a4, _b2;
|
|
16496
|
+
const pointer = this.pointer;
|
|
16497
|
+
if (!pointer || event.pointerId !== pointer.id) return;
|
|
16498
|
+
if (!pointer.dragging) {
|
|
16499
|
+
if (Math.hypot(event.clientX - pointer.startX, event.clientY - pointer.startY) < 4) return;
|
|
16500
|
+
pointer.dragging = true;
|
|
16501
|
+
(_b2 = (_a4 = this.canvas).setPointerCapture) == null ? void 0 : _b2.call(_a4, pointer.id);
|
|
16502
|
+
}
|
|
16503
|
+
const dx = event.clientX - pointer.x;
|
|
16504
|
+
const dy = event.clientY - pointer.y;
|
|
16505
|
+
pointer.x = event.clientX;
|
|
16506
|
+
pointer.y = event.clientY;
|
|
16507
|
+
if (dx || dy) this.onLook(dx, dy);
|
|
16508
|
+
event.preventDefault();
|
|
16509
|
+
};
|
|
16510
|
+
this.end = (event) => {
|
|
16511
|
+
var _a4, _b2;
|
|
16512
|
+
if (!this.pointer || event.pointerId !== void 0 && event.pointerId !== this.pointer.id) return;
|
|
16513
|
+
if (this.pointer.dragging) {
|
|
16514
|
+
try {
|
|
16515
|
+
(_b2 = (_a4 = this.canvas).releasePointerCapture) == null ? void 0 : _b2.call(_a4, this.pointer.id);
|
|
16516
|
+
} catch {
|
|
16517
|
+
}
|
|
16518
|
+
}
|
|
16519
|
+
this.pointer = null;
|
|
16520
|
+
};
|
|
16521
|
+
this.wheel = (event) => event.preventDefault();
|
|
16522
|
+
this.contextMenu = (event) => event.preventDefault();
|
|
16523
|
+
canvas.addEventListener("pointerdown", this.down);
|
|
16524
|
+
canvas.addEventListener("wheel", this.wheel, { passive: false });
|
|
16525
|
+
canvas.addEventListener("contextmenu", this.contextMenu);
|
|
16526
|
+
this.root.addEventListener("pointermove", this.move);
|
|
16527
|
+
this.root.addEventListener("pointerup", this.end);
|
|
16528
|
+
this.root.addEventListener("pointercancel", this.end);
|
|
16529
|
+
this.root.addEventListener("lostpointercapture", this.end);
|
|
16530
|
+
(_a3 = this.window) == null ? void 0 : _a3.addEventListener("blur", this.end);
|
|
16531
|
+
}
|
|
16532
|
+
handleKeyDown(event) {
|
|
16533
|
+
if (event.altKey || event.ctrlKey || event.metaKey || event.shiftKey) return false;
|
|
16534
|
+
const target = event.target;
|
|
16535
|
+
if ((target == null ? void 0 : target.isContentEditable) || ["INPUT", "TEXTAREA", "SELECT"].includes(target == null ? void 0 : target.tagName)) return false;
|
|
16536
|
+
if (target !== this.canvas && target !== this.root.body && target !== this.root.documentElement) return false;
|
|
16537
|
+
const delta = {
|
|
16538
|
+
ArrowLeft: [-16, 0],
|
|
16539
|
+
ArrowRight: [16, 0],
|
|
16540
|
+
ArrowUp: [0, -16],
|
|
16541
|
+
ArrowDown: [0, 16]
|
|
16542
|
+
}[event.key];
|
|
16543
|
+
if (!delta) return false;
|
|
16544
|
+
event.preventDefault();
|
|
16545
|
+
this.onLook(delta[0], delta[1]);
|
|
16546
|
+
return true;
|
|
16547
|
+
}
|
|
16548
|
+
dispose() {
|
|
16549
|
+
var _a3;
|
|
16550
|
+
this.end({});
|
|
16551
|
+
this.canvas.removeEventListener("pointerdown", this.down);
|
|
16552
|
+
this.canvas.removeEventListener("wheel", this.wheel);
|
|
16553
|
+
this.canvas.removeEventListener("contextmenu", this.contextMenu);
|
|
16554
|
+
this.root.removeEventListener("pointermove", this.move);
|
|
16555
|
+
this.root.removeEventListener("pointerup", this.end);
|
|
16556
|
+
this.root.removeEventListener("pointercancel", this.end);
|
|
16557
|
+
this.root.removeEventListener("lostpointercapture", this.end);
|
|
16558
|
+
(_a3 = this.window) == null ? void 0 : _a3.removeEventListener("blur", this.end);
|
|
16559
|
+
}
|
|
16560
|
+
}
|
|
15983
16561
|
const shadowCanvas = document.createElement("canvas");
|
|
15984
16562
|
shadowCanvas.width = 128;
|
|
15985
16563
|
shadowCanvas.height = 128;
|
|
@@ -16020,6 +16598,11 @@ class Viewer extends EventDispatcher {
|
|
|
16020
16598
|
this.type = "viewer";
|
|
16021
16599
|
this.disposed = false;
|
|
16022
16600
|
this.xrSession = null;
|
|
16601
|
+
this.xrDiagnosticsRows = null;
|
|
16602
|
+
this.loadingDiagnosticsEnabled = false;
|
|
16603
|
+
this.diagnosticFps = null;
|
|
16604
|
+
this.diagnosticWindowStart = null;
|
|
16605
|
+
this.diagnosticFrameCount = 0;
|
|
16023
16606
|
this.sparkRenderer = null;
|
|
16024
16607
|
this.transparentBackground = options.transparentBackground ?? true;
|
|
16025
16608
|
Tokens.CESIUM = options.cesiumToken || void 0;
|
|
@@ -16058,14 +16641,33 @@ class Viewer extends EventDispatcher {
|
|
|
16058
16641
|
this.scene = new Scene();
|
|
16059
16642
|
this.content = new Group$1();
|
|
16060
16643
|
this.scene.add(this.content);
|
|
16644
|
+
this.contentLayerRegistry = new ContentLayerRegistry({
|
|
16645
|
+
group: this.content,
|
|
16646
|
+
createLayer: (definition) => this.createContentLayer(definition),
|
|
16647
|
+
onError: (definition, error) => this.dispatchEvent({
|
|
16648
|
+
type: ViewerEvents.CONTENT_LAYER_ERROR,
|
|
16649
|
+
layerId: typeof (definition == null ? void 0 : definition.id) === "string" && definition.id.length > 0 ? definition.id : null,
|
|
16650
|
+
error: error instanceof Error ? error : new Error(String(error))
|
|
16651
|
+
}),
|
|
16652
|
+
onAllSplatsDisabled: () => this.disposeSparkRenderer()
|
|
16653
|
+
});
|
|
16654
|
+
this.splatDestinationPrefetch = new SplatDestinationPrefetch({
|
|
16655
|
+
getRenderer: () => this.sparkRenderer,
|
|
16656
|
+
getLayer: (id) => this.contentLayerRegistry.getActiveLayer(id)
|
|
16657
|
+
});
|
|
16061
16658
|
this.topLayerIndex = 0;
|
|
16062
16659
|
this.enabledLayers = [];
|
|
16063
16660
|
this.labels = /* @__PURE__ */ new Map();
|
|
16064
16661
|
this.features = /* @__PURE__ */ new Map();
|
|
16065
16662
|
this.globeControls = new GlobeControls(this.scene, this.camera, this.renderer.domElement);
|
|
16066
16663
|
this.globeControls.enableDamping = true;
|
|
16664
|
+
this._viewModeState = { version: 0, confirmedRotationSpeed: this.globeControls.rotationSpeed };
|
|
16665
|
+
this.desktopNavigationController = null;
|
|
16666
|
+
this._desktopControlsBefore = null;
|
|
16667
|
+
this.desktopLookControls = null;
|
|
16067
16668
|
this._onGlobeControlsStart = () => {
|
|
16068
16669
|
this.transitionControls.cancel();
|
|
16670
|
+
this.globeControls.adjustHeight = true;
|
|
16069
16671
|
};
|
|
16070
16672
|
this.globeControls.addEventListener("start", this._onGlobeControlsStart);
|
|
16071
16673
|
this.transitionControls = new TransitionControls(this.camera);
|
|
@@ -16104,6 +16706,8 @@ class Viewer extends EventDispatcher {
|
|
|
16104
16706
|
DOWN: false
|
|
16105
16707
|
};
|
|
16106
16708
|
this._onKeyDown = (event) => {
|
|
16709
|
+
var _a3;
|
|
16710
|
+
if (this.desktopNavigationController && this.keysEnabled && ((_a3 = this.desktopLookControls) == null ? void 0 : _a3.handleKeyDown(event))) return;
|
|
16107
16711
|
if (event.repeat && !this.keysDown[event.code]) return;
|
|
16108
16712
|
this.keysDown[event.code] = true;
|
|
16109
16713
|
this.updateMovementState();
|
|
@@ -16115,9 +16719,15 @@ class Viewer extends EventDispatcher {
|
|
|
16115
16719
|
this._onResize = (event) => {
|
|
16116
16720
|
this.resizeView(event);
|
|
16117
16721
|
};
|
|
16722
|
+
this._onWindowBlur = () => this._clearHeldKeys();
|
|
16723
|
+
this._onVisibilityChange = () => {
|
|
16724
|
+
if (document.hidden) this._clearHeldKeys();
|
|
16725
|
+
};
|
|
16118
16726
|
window.addEventListener("keydown", this._onKeyDown);
|
|
16119
16727
|
window.addEventListener("keyup", this._onKeyUp);
|
|
16120
16728
|
window.addEventListener("resize", this._onResize);
|
|
16729
|
+
window.addEventListener("blur", this._onWindowBlur);
|
|
16730
|
+
document.addEventListener("visibilitychange", this._onVisibilityChange);
|
|
16121
16731
|
if (container) this.appendTo(container);
|
|
16122
16732
|
this.sky = new Sky();
|
|
16123
16733
|
this.sky.scale.setScalar(2e7);
|
|
@@ -16159,12 +16769,13 @@ class Viewer extends EventDispatcher {
|
|
|
16159
16769
|
}
|
|
16160
16770
|
/** @param {{ onFrame?: (input: { time: number, frame: XRFrame, pose: XRViewerPose }) => void, onStateChange?: (active: boolean) => void, showAttribution?: boolean }} [options] */
|
|
16161
16771
|
startXRSession(options = {}) {
|
|
16772
|
+
var _a3, _b2;
|
|
16162
16773
|
if (this.disposed) return Promise.reject(new Error("Viewer has been disposed"));
|
|
16774
|
+
(_b2 = (_a3 = this.desktopNavigationController) == null ? void 0 : _a3.interrupt) == null ? void 0 : _b2.call(_a3, "XR session started");
|
|
16163
16775
|
if (!this.xrSession) this.xrSession = new WebXRSession(this, options);
|
|
16164
16776
|
else {
|
|
16165
16777
|
this.xrSession.onFrame = options.onFrame;
|
|
16166
16778
|
this.xrSession.onStateChange = options.onStateChange;
|
|
16167
|
-
this.xrSession.showAttribution = options.showAttribution !== false;
|
|
16168
16779
|
}
|
|
16169
16780
|
return this.xrSession.start();
|
|
16170
16781
|
}
|
|
@@ -16234,6 +16845,9 @@ class Viewer extends EventDispatcher {
|
|
|
16234
16845
|
set keysEnabled(enabled) {
|
|
16235
16846
|
if (enabled === this._keysEnabled) return;
|
|
16236
16847
|
this._keysEnabled = enabled;
|
|
16848
|
+
this._clearHeldKeys();
|
|
16849
|
+
}
|
|
16850
|
+
_clearHeldKeys() {
|
|
16237
16851
|
this.keysDown = {};
|
|
16238
16852
|
for (const key in this.movementState) this.movementState[key] = false;
|
|
16239
16853
|
}
|
|
@@ -16249,6 +16863,82 @@ class Viewer extends EventDispatcher {
|
|
|
16249
16863
|
}
|
|
16250
16864
|
}
|
|
16251
16865
|
}
|
|
16866
|
+
if (this.movementState.FRONT || this.movementState.BACK || this.movementState.LEFT || this.movementState.RIGHT || this.movementState.UP || this.movementState.DOWN) {
|
|
16867
|
+
if (this.globeControls) this.globeControls.adjustHeight = true;
|
|
16868
|
+
}
|
|
16869
|
+
}
|
|
16870
|
+
/** Install one desktop camera owner. A null controller restores the prior globe controls. @param {DesktopNavigationController | null} controller */
|
|
16871
|
+
setDesktopNavigationController(controller) {
|
|
16872
|
+
var _a3, _b2, _c, _d;
|
|
16873
|
+
if (this.desktopNavigationController === controller) return;
|
|
16874
|
+
if (controller && this.xrActive) return;
|
|
16875
|
+
this._clearHeldKeys();
|
|
16876
|
+
if (controller) {
|
|
16877
|
+
this.transitionControls.cancel();
|
|
16878
|
+
if (this.desktopNavigationController) (_b2 = (_a3 = this.desktopNavigationController).interrupt) == null ? void 0 : _b2.call(_a3, "replaced");
|
|
16879
|
+
if (!this._desktopControlsBefore) {
|
|
16880
|
+
this._desktopControlsBefore = { enabled: this.globeControls.enabled, rotationSpeed: this.globeControls.rotationSpeed };
|
|
16881
|
+
}
|
|
16882
|
+
this.globeControls.enabled = false;
|
|
16883
|
+
this.globeControls.adjustHeight = false;
|
|
16884
|
+
this.globeControls.globeInertiaFactor = 0;
|
|
16885
|
+
this.globeControls.globeInertia.identity();
|
|
16886
|
+
this.desktopNavigationController = controller;
|
|
16887
|
+
const canvas = (_c = this.renderer) == null ? void 0 : _c.domElement;
|
|
16888
|
+
if ((canvas == null ? void 0 : canvas.getRootNode) && !this.desktopLookControls) this.desktopLookControls = new DesktopLookControls(canvas, (dx, dy) => this._applyDesktopLook(dx, dy));
|
|
16889
|
+
if (canvas == null ? void 0 : canvas.focus) {
|
|
16890
|
+
if (canvas.tabIndex < 0) canvas.tabIndex = 0;
|
|
16891
|
+
canvas.focus({ preventScroll: true });
|
|
16892
|
+
}
|
|
16893
|
+
} else {
|
|
16894
|
+
this.desktopNavigationController = null;
|
|
16895
|
+
(_d = this.desktopLookControls) == null ? void 0 : _d.dispose();
|
|
16896
|
+
this.desktopLookControls = null;
|
|
16897
|
+
if (this._desktopControlsBefore) {
|
|
16898
|
+
this.globeControls.adjustHeight = true;
|
|
16899
|
+
this.globeControls.rotationSpeed = this._desktopControlsBefore.rotationSpeed;
|
|
16900
|
+
this.globeControls.enabled = this._desktopControlsBefore.enabled;
|
|
16901
|
+
this._desktopControlsBefore = null;
|
|
16902
|
+
}
|
|
16903
|
+
}
|
|
16904
|
+
}
|
|
16905
|
+
/** Rotate Walk view around its eye; pointer delta is CSS pixels. */
|
|
16906
|
+
_applyDesktopLook(dx, dy) {
|
|
16907
|
+
var _a3, _b2;
|
|
16908
|
+
if (!this.desktopNavigationController || ((_b2 = (_a3 = this.desktopNavigationController).canLook) == null ? void 0 : _b2.call(_a3)) === false || this.xrActive) return;
|
|
16909
|
+
const { lon, lat, pitch, yaw, roll } = this.cameraCoords;
|
|
16910
|
+
if (![lon, lat, pitch, yaw, roll, dx, dy].every(Number.isFinite)) return;
|
|
16911
|
+
const nextPitch = MathUtils.clamp(pitch - dy * 0.15, -80, 80);
|
|
16912
|
+
const nextYaw = yaw - dx * 0.15;
|
|
16913
|
+
this.camera.quaternion.copy(geodeticToEcefRotation(lon, lat, nextPitch, nextYaw, roll));
|
|
16914
|
+
this.camera.updateMatrixWorld(true);
|
|
16915
|
+
this.cameraCoords = ecefToGeodeticRotation(this.camera.position.x, this.camera.position.y, this.camera.position.z, this.camera.quaternion);
|
|
16916
|
+
}
|
|
16917
|
+
/** Turn Walk toward north without moving its eye or leaving Walk. */
|
|
16918
|
+
turnDesktopNorth() {
|
|
16919
|
+
if (!this.desktopNavigationController || this.xrActive) return false;
|
|
16920
|
+
const { lon, lat, pitch, roll } = this.cameraCoords;
|
|
16921
|
+
if (![lon, lat, pitch, roll].every(Number.isFinite)) return false;
|
|
16922
|
+
this.camera.quaternion.copy(geodeticToEcefRotation(lon, lat, pitch, 0, roll));
|
|
16923
|
+
this.camera.updateMatrixWorld(true);
|
|
16924
|
+
this.cameraCoords = ecefToGeodeticRotation(this.camera.position.x, this.camera.position.y, this.camera.position.z, this.camera.quaternion);
|
|
16925
|
+
return true;
|
|
16926
|
+
}
|
|
16927
|
+
/** Invoke the desktop controller after globe input and before tiles/content/render. Invalid results leave the previous eye intact. */
|
|
16928
|
+
_applyDesktopNavigationFrame(timeMs, deltaSeconds) {
|
|
16929
|
+
const controller = this.desktopNavigationController;
|
|
16930
|
+
if (!controller || this.xrActive) return;
|
|
16931
|
+
const pose = this.cameraCoords;
|
|
16932
|
+
const result = controller.update({ timeMs, deltaSeconds, pose: { lon: pose.lon, lat: pose.lat, alt: pose.alt, pitch: pose.pitch, yaw: pose.yaw, roll: pose.roll }, movement: { ...this.movementState } });
|
|
16933
|
+
const { longitude, latitude, altitude } = (result == null ? void 0 : result.position) ?? {};
|
|
16934
|
+
if (![longitude, latitude, altitude].every(Number.isFinite) || longitude < -180 || longitude > 180 || latitude < -90 || latitude > 90 || result.pitch !== void 0 && !Number.isFinite(result.pitch)) {
|
|
16935
|
+
console.error("Desktop navigation returned an invalid camera pose");
|
|
16936
|
+
return;
|
|
16937
|
+
}
|
|
16938
|
+
this.camera.position.fromArray(geodeticToEcefPosition(longitude, latitude, altitude));
|
|
16939
|
+
if (result.pitch !== void 0) this.camera.quaternion.copy(geodeticToEcefRotation(longitude, latitude, result.pitch, pose.yaw, pose.roll));
|
|
16940
|
+
this.camera.updateMatrixWorld(true);
|
|
16941
|
+
this.cameraCoords = ecefToGeodeticRotation(this.camera.position.x, this.camera.position.y, this.camera.position.z, this.camera.quaternion);
|
|
16252
16942
|
}
|
|
16253
16943
|
/**
|
|
16254
16944
|
* @param {number} lon
|
|
@@ -16327,11 +17017,8 @@ class Viewer extends EventDispatcher {
|
|
|
16327
17017
|
}
|
|
16328
17018
|
clearContentLayers() {
|
|
16329
17019
|
var _a3;
|
|
16330
|
-
|
|
16331
|
-
|
|
16332
|
-
(_a3 = layer.dispose) == null ? void 0 : _a3.call(layer);
|
|
16333
|
-
this.content.remove(layer);
|
|
16334
|
-
}
|
|
17020
|
+
(_a3 = this.splatDestinationPrefetch) == null ? void 0 : _a3.clear("cancel");
|
|
17021
|
+
this.contentLayerRegistry.clear();
|
|
16335
17022
|
this.disposeSparkRenderer();
|
|
16336
17023
|
}
|
|
16337
17024
|
async ensureSparkRenderer() {
|
|
@@ -16347,110 +17034,111 @@ class Viewer extends EventDispatcher {
|
|
|
16347
17034
|
return this.sparkRenderer;
|
|
16348
17035
|
}
|
|
16349
17036
|
disposeSparkRenderer() {
|
|
16350
|
-
var _a3, _b2;
|
|
17037
|
+
var _a3, _b2, _c;
|
|
16351
17038
|
this.sparkRendererGeneration = (this.sparkRendererGeneration ?? 0) + 1;
|
|
16352
17039
|
if (!this.sparkRenderer) return;
|
|
17040
|
+
(_a3 = this.splatDestinationPrefetch) == null ? void 0 : _a3.sync();
|
|
16353
17041
|
this.sparkRenderer.removeFromParent();
|
|
16354
|
-
(
|
|
17042
|
+
(_c = (_b2 = this.sparkRenderer).clearSplats) == null ? void 0 : _c.call(_b2);
|
|
16355
17043
|
this.sparkRenderer.dispose();
|
|
16356
17044
|
this.sparkRenderer = null;
|
|
16357
17045
|
}
|
|
17046
|
+
/** @private @param {import('../main.js').ContentLayerDefinition} sourceLayerData */
|
|
17047
|
+
prepareContentLayerDefinition(sourceLayerData) {
|
|
17048
|
+
const layerData = (sourceLayerData == null ? void 0 : sourceLayerData.type) === "gaussian-splat" ? validateGaussianSplatLayerDefinition(sourceLayerData) : sourceLayerData;
|
|
17049
|
+
if (typeof (layerData == null ? void 0 : layerData.id) !== "string" || !layerData.id || !Array.isArray(layerData.labels)) {
|
|
17050
|
+
throw new Error("Content layer requires a non-empty id and labels array.");
|
|
17051
|
+
}
|
|
17052
|
+
if (!["3d-tiles", "mesh", "geojson", "gaussian-splat"].includes(layerData.type)) {
|
|
17053
|
+
throw new Error(`Unsupported content layer type: ${String(layerData.type)}`);
|
|
17054
|
+
}
|
|
17055
|
+
return layerData;
|
|
17056
|
+
}
|
|
17057
|
+
/** @private @param {import('../main.js').ContentLayerDefinition} layerData */
|
|
17058
|
+
createContentLayer(layerData) {
|
|
17059
|
+
const onError = (error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layerData.id, error });
|
|
17060
|
+
switch (layerData.type) {
|
|
17061
|
+
case "3d-tiles":
|
|
17062
|
+
return new TilesLayer(layerData.data.url, { camera: this.camera, renderer: this.renderer, ...layerData.options, decoders: this.tileDecoders }, { onError });
|
|
17063
|
+
case "mesh":
|
|
17064
|
+
return new MeshLayer(layerData.data.url, { ...layerData.options, decoders: this.tileDecoders }, { onError });
|
|
17065
|
+
case "geojson":
|
|
17066
|
+
return new GeojsonLayer(layerData.data, layerData.options, { onError });
|
|
17067
|
+
case "gaussian-splat":
|
|
17068
|
+
return new GaussianSplatLayer(layerData, {
|
|
17069
|
+
ensureRenderer: () => this.ensureSparkRenderer(),
|
|
17070
|
+
releasePagedSplats: (paged) => {
|
|
17071
|
+
var _a3, _b2;
|
|
17072
|
+
return (_b2 = (_a3 = this.sparkRenderer) == null ? void 0 : _a3.releasePagedSplats) == null ? void 0 : _b2.call(_a3, paged);
|
|
17073
|
+
},
|
|
17074
|
+
onStart: (layer) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_LOAD_START, layerId: layer.contentLayerId }),
|
|
17075
|
+
onProgress: (layer, progress) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_LOAD_PROGRESS, layerId: layer.contentLayerId, progress }),
|
|
17076
|
+
onReady: (layer) => {
|
|
17077
|
+
this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_READY, layerId: layer.contentLayerId });
|
|
17078
|
+
this.splatDestinationPrefetch.sync();
|
|
17079
|
+
},
|
|
17080
|
+
onError: (layer, error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layer.contentLayerId, error })
|
|
17081
|
+
});
|
|
17082
|
+
default:
|
|
17083
|
+
throw new Error(`Unsupported content layer type: ${String(layerData.type)}`);
|
|
17084
|
+
}
|
|
17085
|
+
}
|
|
17086
|
+
/** @private */
|
|
17087
|
+
reportContentLayerError(sourceLayerData, error) {
|
|
17088
|
+
this.dispatchEvent({
|
|
17089
|
+
type: ViewerEvents.CONTENT_LAYER_ERROR,
|
|
17090
|
+
layerId: typeof (sourceLayerData == null ? void 0 : sourceLayerData.id) === "string" && sourceLayerData.id.length > 0 ? sourceLayerData.id : null,
|
|
17091
|
+
error: error instanceof Error ? error : new Error(String(error))
|
|
17092
|
+
});
|
|
17093
|
+
}
|
|
17094
|
+
/** @private */
|
|
17095
|
+
refreshContentLayerDepth() {
|
|
17096
|
+
this.topLayerIndex = Math.max(0, ...this.content.children.map((layer) => Math.max(layer.contentRenderOrder ?? 0, layer.xrRenderLayer ?? 0)));
|
|
17097
|
+
this.globeControls.pivotMesh.layers.set(this.topLayerIndex);
|
|
17098
|
+
}
|
|
16358
17099
|
/** @param {import('../main.js').ContentLayerDefinition[]} content */
|
|
16359
17100
|
defineContentLayers(content = []) {
|
|
16360
|
-
|
|
16361
|
-
|
|
16362
|
-
this.clearContentLayers();
|
|
16363
|
-
for (let i2 = 0; i2 < content.length; i2++) {
|
|
16364
|
-
const sourceLayerData = content[i2];
|
|
17101
|
+
const definitions = [];
|
|
17102
|
+
for (const sourceLayerData of content) {
|
|
16365
17103
|
try {
|
|
16366
|
-
|
|
16367
|
-
this.topLayerIndex = Math.max(this.topLayerIndex, ((_a3 = layerData == null ? void 0 : layerData.options) == null ? void 0 : _a3.renderOrder) ?? 0);
|
|
16368
|
-
switch (layerData == null ? void 0 : layerData.type) {
|
|
16369
|
-
case "3d-tiles": {
|
|
16370
|
-
const tilesLayer = new TilesLayer(
|
|
16371
|
-
layerData.data.url,
|
|
16372
|
-
{ camera: this.camera, renderer: this.renderer, ...layerData.options, decoders: this.tileDecoders },
|
|
16373
|
-
{ onError: (error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layerData.id, error }) }
|
|
16374
|
-
);
|
|
16375
|
-
tilesLayer.contentLayerId = layerData.id;
|
|
16376
|
-
tilesLayer.setLabels(layerData.labels);
|
|
16377
|
-
(_b2 = tilesLayer.setTimeFrame) == null ? void 0 : _b2.call(tilesLayer, this.timeFrameStart, this.timeFrameEnd);
|
|
16378
|
-
tilesLayer.setEnabled(false);
|
|
16379
|
-
this.content.add(tilesLayer);
|
|
16380
|
-
break;
|
|
16381
|
-
}
|
|
16382
|
-
case "mesh": {
|
|
16383
|
-
const meshLayer = new MeshLayer(
|
|
16384
|
-
layerData.data.url,
|
|
16385
|
-
{ ...layerData.options },
|
|
16386
|
-
{ onError: (error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layerData.id, error }) }
|
|
16387
|
-
);
|
|
16388
|
-
meshLayer.contentLayerId = layerData.id;
|
|
16389
|
-
meshLayer.setLabels(layerData.labels);
|
|
16390
|
-
meshLayer.setEnabled(false);
|
|
16391
|
-
this.content.add(meshLayer);
|
|
16392
|
-
break;
|
|
16393
|
-
}
|
|
16394
|
-
case "geojson": {
|
|
16395
|
-
const geojsonLayer = new GeojsonLayer(layerData.data, layerData.options, {
|
|
16396
|
-
onError: (error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layerData.id, error })
|
|
16397
|
-
});
|
|
16398
|
-
geojsonLayer.contentLayerId = layerData.id;
|
|
16399
|
-
geojsonLayer.setLabels(layerData.labels);
|
|
16400
|
-
(_c = geojsonLayer.setTimeFrame) == null ? void 0 : _c.call(geojsonLayer, this.timeFrameStart, this.timeFrameEnd);
|
|
16401
|
-
geojsonLayer.setEnabled(false);
|
|
16402
|
-
this.content.add(geojsonLayer);
|
|
16403
|
-
break;
|
|
16404
|
-
}
|
|
16405
|
-
case "gaussian-splat": {
|
|
16406
|
-
const gaussianLayer = new GaussianSplatLayer(layerData, {
|
|
16407
|
-
ensureRenderer: () => this.ensureSparkRenderer(),
|
|
16408
|
-
onStart: (layer) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_LOAD_START, layerId: layer.contentLayerId }),
|
|
16409
|
-
onProgress: (layer, progress) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_LOAD_PROGRESS, layerId: layer.contentLayerId, progress }),
|
|
16410
|
-
onReady: (layer) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_READY, layerId: layer.contentLayerId }),
|
|
16411
|
-
onError: (layer, error) => this.dispatchEvent({ type: ViewerEvents.CONTENT_LAYER_ERROR, layerId: layer.contentLayerId, error })
|
|
16412
|
-
});
|
|
16413
|
-
this.content.add(gaussianLayer);
|
|
16414
|
-
break;
|
|
16415
|
-
}
|
|
16416
|
-
default:
|
|
16417
|
-
throw new Error(`Unsupported content layer type: ${String(layerData == null ? void 0 : layerData.type)}`);
|
|
16418
|
-
}
|
|
16419
|
-
this.content.children.at(-1).xrRenderLayer = layerData.type === "mesh" ? 6 : ((_d = layerData.options) == null ? void 0 : _d.renderOrder) ?? 0;
|
|
17104
|
+
definitions.push(this.prepareContentLayerDefinition(sourceLayerData));
|
|
16420
17105
|
} catch (error) {
|
|
16421
|
-
this.
|
|
16422
|
-
type: ViewerEvents.CONTENT_LAYER_ERROR,
|
|
16423
|
-
layerId: typeof (sourceLayerData == null ? void 0 : sourceLayerData.id) === "string" && sourceLayerData.id.length > 0 ? sourceLayerData.id : null,
|
|
16424
|
-
error: error instanceof Error ? error : new Error(String(error))
|
|
16425
|
-
});
|
|
17106
|
+
this.reportContentLayerError(sourceLayerData, error);
|
|
16426
17107
|
}
|
|
16427
17108
|
}
|
|
16428
|
-
this.
|
|
16429
|
-
this.
|
|
17109
|
+
this.contentLayerRegistry.setDefinitions(definitions);
|
|
17110
|
+
this.splatDestinationPrefetch.sync();
|
|
17111
|
+
this.refreshContentLayerDepth();
|
|
16430
17112
|
}
|
|
16431
|
-
|
|
16432
|
-
|
|
16433
|
-
|
|
16434
|
-
|
|
16435
|
-
|
|
16436
|
-
|
|
16437
|
-
|
|
16438
|
-
|
|
16439
|
-
|
|
16440
|
-
|
|
16441
|
-
|
|
17113
|
+
/** Replace, add, or remove one content layer without rebuilding its siblings. */
|
|
17114
|
+
/** @param {string} id @param {import('../main.js').ContentLayerDefinition | null} definition */
|
|
17115
|
+
replaceContentLayer(id, definition) {
|
|
17116
|
+
if (this.disposed) return;
|
|
17117
|
+
if (typeof id !== "string" || id.length === 0) throw new Error("Content layer id must be a non-empty string.");
|
|
17118
|
+
if (definition && definition.id !== id) throw new Error("Replacement layer id must match the requested id.");
|
|
17119
|
+
let prepared = null;
|
|
17120
|
+
if (definition) {
|
|
17121
|
+
try {
|
|
17122
|
+
prepared = this.prepareContentLayerDefinition(definition);
|
|
17123
|
+
} catch (error) {
|
|
17124
|
+
this.reportContentLayerError(definition, error);
|
|
17125
|
+
return;
|
|
16442
17126
|
}
|
|
16443
|
-
contentLayer.setEnabled(enabled);
|
|
16444
17127
|
}
|
|
17128
|
+
if (!this.contentLayerRegistry.replaceDefinition(id, prepared)) return;
|
|
17129
|
+
this.splatDestinationPrefetch.sync();
|
|
17130
|
+
this.refreshContentLayerDepth();
|
|
17131
|
+
}
|
|
17132
|
+
enableContentLayers(labels = []) {
|
|
17133
|
+
this.enabledLayers = labels;
|
|
17134
|
+
this.contentLayerRegistry.setEnabledLabels(labels);
|
|
17135
|
+
this.splatDestinationPrefetch.sync();
|
|
17136
|
+
this.refreshContentLayerDepth();
|
|
16445
17137
|
}
|
|
16446
17138
|
setTimeFrame(start, end) {
|
|
16447
|
-
var _a3;
|
|
16448
17139
|
this.timeFrameStart = start ? new Date(start) : null;
|
|
16449
17140
|
this.timeFrameEnd = end ? new Date(end) : null;
|
|
16450
|
-
|
|
16451
|
-
const contentLayer = this.content.children[i2];
|
|
16452
|
-
(_a3 = contentLayer.setTimeFrame) == null ? void 0 : _a3.call(contentLayer, this.timeFrameStart, this.timeFrameEnd);
|
|
16453
|
-
}
|
|
17141
|
+
this.contentLayerRegistry.setTimeFrame(this.timeFrameStart, this.timeFrameEnd);
|
|
16454
17142
|
}
|
|
16455
17143
|
/**
|
|
16456
17144
|
* @param {string} id
|
|
@@ -16510,7 +17198,16 @@ class Viewer extends EventDispatcher {
|
|
|
16510
17198
|
}
|
|
16511
17199
|
animate(time) {
|
|
16512
17200
|
var _a3, _b2, _c;
|
|
16513
|
-
if (this.
|
|
17201
|
+
if (this.loadingDiagnosticsEnabled) {
|
|
17202
|
+
if (this.diagnosticWindowStart === null) this.diagnosticWindowStart = time;
|
|
17203
|
+
this.diagnosticFrameCount++;
|
|
17204
|
+
const elapsed = time - this.diagnosticWindowStart;
|
|
17205
|
+
if (elapsed >= 1e3) {
|
|
17206
|
+
this.diagnosticFps = Math.round(this.diagnosticFrameCount * 1e3 / elapsed);
|
|
17207
|
+
this.diagnosticWindowStart = time;
|
|
17208
|
+
this.diagnosticFrameCount = 0;
|
|
17209
|
+
}
|
|
17210
|
+
}
|
|
16514
17211
|
this.transitionControls.update(time);
|
|
16515
17212
|
this.state.get("time").value = time;
|
|
16516
17213
|
const deltaTime = this.clock.getDelta();
|
|
@@ -16519,7 +17216,10 @@ class Viewer extends EventDispatcher {
|
|
|
16519
17216
|
this.updateCameraDirections();
|
|
16520
17217
|
this.cameraCoords = ecefToGeodeticRotation(this.camera.position.x, this.camera.position.y, this.camera.position.z, this.camera.quaternion);
|
|
16521
17218
|
this.sky.setSurfaceUp(geodeticToEcefUpVector(this.cameraCoords.lon, this.cameraCoords.lat));
|
|
16522
|
-
if (this.
|
|
17219
|
+
if (this.desktopNavigationController) {
|
|
17220
|
+
this._applyDesktopNavigationFrame(time, deltaTime);
|
|
17221
|
+
this.updateCameraDirections();
|
|
17222
|
+
} else if (this.keysEnabled) {
|
|
16523
17223
|
applyKeyboardMovement(this.camera.position, this.cameraForward, this.cameraRight, this.cameraUp, this.movementState, deltaTime, this.movementSpeed, this.boostMultiplier);
|
|
16524
17224
|
}
|
|
16525
17225
|
this.globeManager.update();
|
|
@@ -16566,9 +17266,9 @@ class Viewer extends EventDispatcher {
|
|
|
16566
17266
|
}
|
|
16567
17267
|
this.cameraCoords = ecefToGeodeticRotation(this.camera.position.x, this.camera.position.y, this.camera.position.z, this.camera.quaternion);
|
|
16568
17268
|
this.dispatchEvent({ type: ViewerEvents.ANIMATED, time, deltaTime });
|
|
16569
|
-
if (this.stats) this.stats.end();
|
|
16570
17269
|
}
|
|
16571
17270
|
render() {
|
|
17271
|
+
this.splatDestinationPrefetch.sync();
|
|
16572
17272
|
this.renderer.render(this.scene, this.camera);
|
|
16573
17273
|
this.css2DRenderer.render(this.scene, this.camera);
|
|
16574
17274
|
if (this.state.get("added") === true && this.state.get("ready") === false) {
|
|
@@ -16632,15 +17332,20 @@ class Viewer extends EventDispatcher {
|
|
|
16632
17332
|
* @param {number} [yaw]
|
|
16633
17333
|
* @param {number} [roll]
|
|
16634
17334
|
* @param {number} [duration]
|
|
17335
|
+
* @returns {Promise<boolean>} Whether the requested transition completed.
|
|
16635
17336
|
*/
|
|
16636
17337
|
async alignCamera(lon, lat, alt, pitch, yaw, roll, duration) {
|
|
17338
|
+
var _a3, _b2;
|
|
17339
|
+
(_b2 = (_a3 = this.desktopNavigationController) == null ? void 0 : _a3.interrupt) == null ? void 0 : _b2.call(_a3, "alignCamera");
|
|
16637
17340
|
const position = validateGeodeticPosition(lon, lat, alt, "Camera position");
|
|
16638
17341
|
const rotation = validateRotation(pitch ?? this.cameraCoords.pitch, yaw ?? this.cameraCoords.yaw, roll ?? this.cameraCoords.roll, "Camera rotation");
|
|
16639
17342
|
const resolvedDuration = requireFiniteNumber(duration ?? TweenSettings.DURATION, "Camera transition duration");
|
|
16640
17343
|
const targetPosition = new Vector3().fromArray(geodeticToEcefPosition(position.longitude, position.latitude, position.altitude));
|
|
16641
17344
|
const targetQuaternion = geodeticToEcefRotation(position.longitude, position.latitude, rotation.pitch, rotation.yaw, rotation.roll);
|
|
17345
|
+
if (this.globeControls) this.globeControls.adjustHeight = false;
|
|
16642
17346
|
return this.transitionControls.animateTo(targetPosition, targetQuaternion, resolvedDuration).then((completed) => {
|
|
16643
17347
|
if (completed) this.dispatchEvent({ type: ViewerEvents.TRANSITIONED, lon, lat, alt, ...rotation });
|
|
17348
|
+
return completed;
|
|
16644
17349
|
});
|
|
16645
17350
|
}
|
|
16646
17351
|
/**
|
|
@@ -16650,8 +17355,11 @@ class Viewer extends EventDispatcher {
|
|
|
16650
17355
|
* @param {number} [distance]
|
|
16651
17356
|
* @param {number} [pitch]
|
|
16652
17357
|
* @param {number} [duration]
|
|
17358
|
+
* @returns {Promise<boolean>} Whether the requested transition completed.
|
|
16653
17359
|
*/
|
|
16654
17360
|
async focusCamera(lon, lat, alt, distance, pitch, duration) {
|
|
17361
|
+
var _a3, _b2;
|
|
17362
|
+
(_b2 = (_a3 = this.desktopNavigationController) == null ? void 0 : _a3.interrupt) == null ? void 0 : _b2.call(_a3, "focusCamera");
|
|
16655
17363
|
const position = validateGeodeticPosition(lon, lat, alt, "Camera focus");
|
|
16656
17364
|
const resolvedDistance = requireFiniteNumber(distance ?? 2e3, "Camera focus distance");
|
|
16657
17365
|
const rotation = validateRotation(pitch ?? this.cameraCoords.pitch, 0, 0, "Camera rotation");
|
|
@@ -16660,25 +17368,72 @@ class Viewer extends EventDispatcher {
|
|
|
16660
17368
|
const targetQuaternion = geodeticToEcefRotation(position.longitude, position.latitude, rotation.pitch, rotation.yaw, rotation.roll);
|
|
16661
17369
|
const direction = new Vector3(0, 0, 1).applyQuaternion(targetQuaternion);
|
|
16662
17370
|
targetPosition.addScaledVector(direction, resolvedDistance);
|
|
17371
|
+
if (this.globeControls) this.globeControls.adjustHeight = true;
|
|
16663
17372
|
return this.transitionControls.animateTo(targetPosition, targetQuaternion, resolvedDuration).then((completed) => {
|
|
16664
17373
|
if (completed) this.dispatchEvent({ type: ViewerEvents.TRANSITIONED, lon, lat, alt });
|
|
17374
|
+
return completed;
|
|
16665
17375
|
});
|
|
16666
17376
|
}
|
|
16667
17377
|
/**
|
|
16668
17378
|
* Temporarily load Google 3D tiles around a WGS84 destination without changing the live view.
|
|
16669
17379
|
* Position and altitude use degrees and WGS84 ellipsoidal metres; rotation uses degrees.
|
|
16670
|
-
* @param {{longitude:number, latitude:number, altitude:number, pitch:number, yaw:number, roll:number, resolutionPixels:128|256} | null} target
|
|
17380
|
+
* @param {{longitude:number, latitude:number, altitude:number, pitch:number, yaw:number, roll:number, resolutionPixels:128|256, timeoutMs?:number} | null} target
|
|
16671
17381
|
*/
|
|
16672
17382
|
setDestinationTilePrefetch(target) {
|
|
16673
17383
|
if (this.disposed) return;
|
|
16674
17384
|
this.globeManager.setDestinationTilePrefetch(target);
|
|
16675
17385
|
}
|
|
17386
|
+
/**
|
|
17387
|
+
* Warm only active RAD layers at a WGS84 destination. This never changes the live camera.
|
|
17388
|
+
* @param {{longitude:number, latitude:number, altitude:number, pitch:number, yaw:number, roll:number, layerIds:string[], mode:'desktop'|'xr', timeoutMs:number} | null} target
|
|
17389
|
+
* @param {'cancel'|'arrival'} [clearReason]
|
|
17390
|
+
*/
|
|
17391
|
+
setDestinationSplatPrefetch(target, clearReason = "cancel") {
|
|
17392
|
+
if (this.disposed) return;
|
|
17393
|
+
if (!target) {
|
|
17394
|
+
this.splatDestinationPrefetch.clear(clearReason);
|
|
17395
|
+
return;
|
|
17396
|
+
}
|
|
17397
|
+
try {
|
|
17398
|
+
validateGeodeticPosition(target.longitude, target.latitude, target.altitude, "Destination splat prefetch");
|
|
17399
|
+
validateRotation(target.pitch, target.yaw, target.roll, "Destination splat prefetch rotation");
|
|
17400
|
+
} catch {
|
|
17401
|
+
return;
|
|
17402
|
+
}
|
|
17403
|
+
if (!Array.isArray(target.layerIds) || !target.layerIds.every((id) => typeof id === "string") || !["desktop", "xr"].includes(target.mode)) return;
|
|
17404
|
+
this.splatDestinationPrefetch.set(target);
|
|
17405
|
+
}
|
|
17406
|
+
/** Optional viewer-owned counters, sampled by the app only while its stats setting is on.
|
|
17407
|
+
* @param {boolean} enabled
|
|
17408
|
+
*/
|
|
17409
|
+
setLoadingDiagnosticsEnabled(enabled) {
|
|
17410
|
+
this.loadingDiagnosticsEnabled = Boolean(enabled);
|
|
17411
|
+
if (!enabled) {
|
|
17412
|
+
this.diagnosticFps = null;
|
|
17413
|
+
this.diagnosticWindowStart = null;
|
|
17414
|
+
this.diagnosticFrameCount = 0;
|
|
17415
|
+
}
|
|
17416
|
+
}
|
|
17417
|
+
getLoadingDiagnostics() {
|
|
17418
|
+
return readLoadingDiagnostics(this);
|
|
17419
|
+
}
|
|
17420
|
+
/** Short numeric rows in a small lower-right panel for both XR eyes.
|
|
17421
|
+
* @param {string[] | null} rows
|
|
17422
|
+
*/
|
|
17423
|
+
setXRDiagnosticsPanel(rows) {
|
|
17424
|
+
var _a3, _b2;
|
|
17425
|
+
this.xrDiagnosticsRows = Array.isArray(rows) && rows.length > 0 ? rows.slice(0, 5).map(String) : null;
|
|
17426
|
+
(_b2 = (_a3 = this.xrSession) == null ? void 0 : _a3.bridge) == null ? void 0 : _b2.setDiagnosticsRows(this.xrDiagnosticsRows);
|
|
17427
|
+
}
|
|
16676
17428
|
/**
|
|
16677
17429
|
* @param {number} [pitch]
|
|
16678
17430
|
* @param {number} [yaw]
|
|
16679
17431
|
* @param {number} [duration]
|
|
17432
|
+
* @returns {Promise<boolean>} Whether the requested transition completed.
|
|
16680
17433
|
*/
|
|
16681
17434
|
async angleCamera(pitch, yaw, duration) {
|
|
17435
|
+
var _a3, _b2;
|
|
17436
|
+
(_b2 = (_a3 = this.desktopNavigationController) == null ? void 0 : _a3.interrupt) == null ? void 0 : _b2.call(_a3, "angleCamera");
|
|
16682
17437
|
const rotation = validateRotation(pitch ?? this.cameraCoords.pitch, yaw ?? this.cameraCoords.yaw, 0, "Camera rotation");
|
|
16683
17438
|
const resolvedDuration = requireFiniteNumber(duration ?? TweenSettings.DURATION, "Camera transition duration");
|
|
16684
17439
|
const pivot = this.getCameraPivot();
|
|
@@ -16690,15 +17445,27 @@ class Viewer extends EventDispatcher {
|
|
|
16690
17445
|
targetPosition.addScaledVector(direction, distance);
|
|
16691
17446
|
return this.transitionControls.animateTo(targetPosition, targetQuaternion, resolvedDuration).then((completed) => {
|
|
16692
17447
|
if (completed) this.dispatchEvent({ type: ViewerEvents.TRANSITIONED, lon, lat, alt });
|
|
17448
|
+
return completed;
|
|
16693
17449
|
});
|
|
16694
17450
|
}
|
|
16695
|
-
|
|
16696
|
-
|
|
16697
|
-
|
|
16698
|
-
|
|
16699
|
-
|
|
16700
|
-
|
|
16701
|
-
|
|
17451
|
+
/** @param {'2d' | '3d'} [mode] @returns {Promise<boolean>} Whether the camera orientation transition completed. */
|
|
17452
|
+
async setViewMode(mode = "3d") {
|
|
17453
|
+
var _a3, _b2;
|
|
17454
|
+
(_b2 = (_a3 = this.desktopNavigationController) == null ? void 0 : _a3.interrupt) == null ? void 0 : _b2.call(_a3, "setViewMode");
|
|
17455
|
+
const request = this._viewModeState ?? (this._viewModeState = { version: 0, confirmedRotationSpeed: this.globeControls.rotationSpeed });
|
|
17456
|
+
const version = ++request.version;
|
|
17457
|
+
const targetRotationSpeed = mode === "3d" ? 1 : 0;
|
|
17458
|
+
this.globeControls.rotationSpeed = targetRotationSpeed;
|
|
17459
|
+
try {
|
|
17460
|
+
const completed = mode === "3d" ? await this.angleCamera(-60, void 0, 500) : await this.angleCamera(-90, 0, 500);
|
|
17461
|
+
if (request.version === version && !this.disposed) {
|
|
17462
|
+
if (completed) request.confirmedRotationSpeed = targetRotationSpeed;
|
|
17463
|
+
else this.globeControls.rotationSpeed = request.confirmedRotationSpeed;
|
|
17464
|
+
}
|
|
17465
|
+
return completed;
|
|
17466
|
+
} catch (error) {
|
|
17467
|
+
if (request.version === version && !this.disposed) this.globeControls.rotationSpeed = request.confirmedRotationSpeed;
|
|
17468
|
+
throw error;
|
|
16702
17469
|
}
|
|
16703
17470
|
}
|
|
16704
17471
|
exportScene() {
|
|
@@ -16723,9 +17490,12 @@ class Viewer extends EventDispatcher {
|
|
|
16723
17490
|
link.click();
|
|
16724
17491
|
}
|
|
16725
17492
|
dispose() {
|
|
16726
|
-
var _a3, _b2, _c, _d, _e, _f, _g, _h, _i2, _j, _k, _l, _m, _n2, _o;
|
|
17493
|
+
var _a3, _b2, _c, _d, _e, _f, _g, _h, _i2, _j, _k, _l, _m, _n2, _o, _p;
|
|
16727
17494
|
if (this.disposed) return;
|
|
16728
17495
|
this.disposed = true;
|
|
17496
|
+
(_a3 = this.splatDestinationPrefetch) == null ? void 0 : _a3.dispose();
|
|
17497
|
+
(_c = (_b2 = this.desktopNavigationController) == null ? void 0 : _b2.interrupt) == null ? void 0 : _c.call(_b2, "viewer disposed");
|
|
17498
|
+
if (this.desktopNavigationController || this.desktopLookControls) this.setDesktopNavigationController(null);
|
|
16729
17499
|
if (this.xrSession) {
|
|
16730
17500
|
void this.xrSession.dispose().catch((error) => console.error("WebXR session end failed during viewer disposal", error));
|
|
16731
17501
|
this.xrSession = null;
|
|
@@ -16736,6 +17506,8 @@ class Viewer extends EventDispatcher {
|
|
|
16736
17506
|
window.removeEventListener("keydown", this._onKeyDown);
|
|
16737
17507
|
window.removeEventListener("keyup", this._onKeyUp);
|
|
16738
17508
|
window.removeEventListener("resize", this._onResize);
|
|
17509
|
+
window.removeEventListener("blur", this._onWindowBlur);
|
|
17510
|
+
document.removeEventListener("visibilitychange", this._onVisibilityChange);
|
|
16739
17511
|
window.removeEventListener("pointermove", this._onPointerMove);
|
|
16740
17512
|
this.globeControls.removeEventListener("start", this._onGlobeControlsStart);
|
|
16741
17513
|
this.globeControls.dispose();
|
|
@@ -16758,17 +17530,16 @@ class Viewer extends EventDispatcher {
|
|
|
16758
17530
|
}
|
|
16759
17531
|
this.labels.clear();
|
|
16760
17532
|
this.features.clear();
|
|
16761
|
-
(
|
|
17533
|
+
(_e = (_d = this.scene.environment) == null ? void 0 : _d.dispose) == null ? void 0 : _e.call(_d);
|
|
16762
17534
|
this.scene.environment = null;
|
|
16763
|
-
(
|
|
16764
|
-
(
|
|
16765
|
-
(
|
|
16766
|
-
(_k = (_j = this.stats) == null ? void 0 : _j.dom) == null ? void 0 : _k.remove();
|
|
17535
|
+
(_h = (_g = (_f = this.sky) == null ? void 0 : _f.geometry) == null ? void 0 : _g.dispose) == null ? void 0 : _h.call(_g);
|
|
17536
|
+
(_k = (_j = (_i2 = this.sky) == null ? void 0 : _i2.material) == null ? void 0 : _j.dispose) == null ? void 0 : _k.call(_j);
|
|
17537
|
+
(_l = this.sky) == null ? void 0 : _l.removeFromParent();
|
|
16767
17538
|
this.css2DRenderer.domElement.remove();
|
|
16768
17539
|
this.renderer.domElement.remove();
|
|
16769
|
-
(
|
|
17540
|
+
(_n2 = (_m = this.renderer.renderLists) == null ? void 0 : _m.dispose) == null ? void 0 : _n2.call(_m);
|
|
16770
17541
|
this.renderer.dispose();
|
|
16771
|
-
(
|
|
17542
|
+
(_p = (_o = this.renderer).forceContextLoss) == null ? void 0 : _p.call(_o);
|
|
16772
17543
|
this.container = null;
|
|
16773
17544
|
this.listeners = {};
|
|
16774
17545
|
}
|