@ericchen1990/pano-view 3.8.0 → 3.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +675 -71
- package/README.zh-CN.md +558 -42
- package/dist/data.cjs +19 -0
- package/dist/data.cjs.map +1 -1
- package/dist/data.d.mts +17 -1
- package/dist/data.d.ts +17 -1
- package/dist/data.mjs +19 -0
- package/dist/data.mjs.map +1 -1
- package/dist/index.cjs +1262 -159
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.mts +144 -3
- package/dist/index.d.ts +144 -3
- package/dist/index.mjs +1281 -172
- package/dist/index.mjs.map +1 -1
- package/dist/styles.css +274 -1
- package/package.json +1 -1
package/dist/index.cjs
CHANGED
|
@@ -2254,6 +2254,7 @@ __export(index_exports, {
|
|
|
2254
2254
|
DEFAULT_HOTSPOT_TOOLTIP_APPEARANCE: () => DEFAULT_HOTSPOT_TOOLTIP_APPEARANCE,
|
|
2255
2255
|
DEFAULT_HOTSPOT_TOOLTIP_OFFSET: () => DEFAULT_HOTSPOT_TOOLTIP_OFFSET,
|
|
2256
2256
|
DEFAULT_PANO_CURSORS: () => DEFAULT_PANO_CURSORS,
|
|
2257
|
+
DEFAULT_PANO_SCENE_MENU_APPEARANCE: () => DEFAULT_PANO_SCENE_MENU_APPEARANCE,
|
|
2257
2258
|
DEFAULT_PANO_VIDEO_CAPTION_APPEARANCE: () => DEFAULT_PANO_VIDEO_CAPTION_APPEARANCE,
|
|
2258
2259
|
DEFAULT_PANO_VIDEO_CONTROLS_APPEARANCE: () => DEFAULT_PANO_VIDEO_CONTROLS_APPEARANCE,
|
|
2259
2260
|
DEFAULT_PANO_VIDEO_PLAYBACK_RATES: () => DEFAULT_PANO_VIDEO_PLAYBACK_RATES,
|
|
@@ -2274,6 +2275,7 @@ __export(index_exports, {
|
|
|
2274
2275
|
PanoMap: () => PanoMap,
|
|
2275
2276
|
PanoMapOverlay: () => PanoMapOverlay,
|
|
2276
2277
|
PanoOverlayPortalProvider: () => PanoOverlayPortalProvider,
|
|
2278
|
+
PanoSceneMenu: () => PanoSceneMenu,
|
|
2277
2279
|
PanoVideo: () => PanoVideo,
|
|
2278
2280
|
PanoVideoControls: () => PanoVideoControls,
|
|
2279
2281
|
PanoViewer: () => PanoViewer,
|
|
@@ -18240,8 +18242,908 @@ var WebVR = (0, import_react61.forwardRef)(function WebVR2({
|
|
|
18240
18242
|
] });
|
|
18241
18243
|
});
|
|
18242
18244
|
|
|
18243
|
-
// src/
|
|
18245
|
+
// src/pano-scene-menu.tsx
|
|
18244
18246
|
var import_react62 = require("react");
|
|
18247
|
+
|
|
18248
|
+
// src/drag-motion.ts
|
|
18249
|
+
var DRAG_INERTIA_DAMPING = 8;
|
|
18250
|
+
var DRAG_FRICTION_STOP = 24;
|
|
18251
|
+
var DRAG_SPRING_STRENGTH = 28;
|
|
18252
|
+
var DRAG_RUBBER_CONSTANT = 0.55;
|
|
18253
|
+
var DRAG_SPRING_SETTLE_DISTANCE = 0.5;
|
|
18254
|
+
var DRAG_SPRING_SETTLE_VELOCITY = 12;
|
|
18255
|
+
function resolveDragMotion(motion) {
|
|
18256
|
+
if (motion === false) {
|
|
18257
|
+
return { inertia: false, bounce: false };
|
|
18258
|
+
}
|
|
18259
|
+
return {
|
|
18260
|
+
inertia: motion?.inertia !== false,
|
|
18261
|
+
bounce: motion?.bounce !== false
|
|
18262
|
+
};
|
|
18263
|
+
}
|
|
18264
|
+
function clampAxis(value, min, max) {
|
|
18265
|
+
if (max < min) return min;
|
|
18266
|
+
return Math.min(max, Math.max(min, value));
|
|
18267
|
+
}
|
|
18268
|
+
function constrainDragPosition(raw, min, max, dimension, bounce) {
|
|
18269
|
+
if (!(Number.isFinite(raw) && Number.isFinite(min) && Number.isFinite(max))) {
|
|
18270
|
+
return 0;
|
|
18271
|
+
}
|
|
18272
|
+
if (raw >= min && raw <= max) {
|
|
18273
|
+
return raw;
|
|
18274
|
+
}
|
|
18275
|
+
if (!bounce) {
|
|
18276
|
+
return clampAxis(raw, min, max);
|
|
18277
|
+
}
|
|
18278
|
+
const size = Math.max(1, Math.abs(dimension) || 1);
|
|
18279
|
+
if (raw < min) {
|
|
18280
|
+
const overshoot2 = min - raw;
|
|
18281
|
+
return min - rubberBandDistance(overshoot2, size);
|
|
18282
|
+
}
|
|
18283
|
+
const overshoot = raw - max;
|
|
18284
|
+
return max + rubberBandDistance(overshoot, size);
|
|
18285
|
+
}
|
|
18286
|
+
function rubberBandDistance(overshoot, dimension, constant = DRAG_RUBBER_CONSTANT) {
|
|
18287
|
+
if (!(overshoot > 0)) return 0;
|
|
18288
|
+
const size = Math.max(1, Math.abs(dimension) || 1);
|
|
18289
|
+
return size * overshoot / (size + overshoot * constant);
|
|
18290
|
+
}
|
|
18291
|
+
function velocityFromSamples(samples, now) {
|
|
18292
|
+
if (samples.length < 2) return 0;
|
|
18293
|
+
const windowMs = 100;
|
|
18294
|
+
let oldest = samples[0];
|
|
18295
|
+
const newest = samples[samples.length - 1];
|
|
18296
|
+
const referenceTime = now ?? newest.t;
|
|
18297
|
+
for (let i = samples.length - 2; i >= 0; i -= 1) {
|
|
18298
|
+
const sample = samples[i];
|
|
18299
|
+
if (referenceTime - sample.t > windowMs) break;
|
|
18300
|
+
oldest = sample;
|
|
18301
|
+
}
|
|
18302
|
+
const dt = (newest.t - oldest.t) / 1e3;
|
|
18303
|
+
if (!(dt >= 1e-3)) return 0;
|
|
18304
|
+
return (newest.position - oldest.position) / dt;
|
|
18305
|
+
}
|
|
18306
|
+
function integrateAxis(state, deltaSeconds, options) {
|
|
18307
|
+
const dt = Math.max(0, deltaSeconds);
|
|
18308
|
+
if (!(dt > 0)) {
|
|
18309
|
+
return { ...state, settled: isAxisSettled(state, options) };
|
|
18310
|
+
}
|
|
18311
|
+
const damping = options.damping ?? DRAG_INERTIA_DAMPING;
|
|
18312
|
+
const frictionStop = options.frictionStop ?? DRAG_FRICTION_STOP;
|
|
18313
|
+
const spring = options.spring ?? DRAG_SPRING_STRENGTH;
|
|
18314
|
+
const { min, max } = options;
|
|
18315
|
+
let { position, velocity } = state;
|
|
18316
|
+
const pastMin = position < min;
|
|
18317
|
+
const pastMax = position > max;
|
|
18318
|
+
if (pastMin || pastMax) {
|
|
18319
|
+
if (!options.bounce) {
|
|
18320
|
+
position = clampAxis(position, min, max);
|
|
18321
|
+
return { position, velocity: 0, settled: true };
|
|
18322
|
+
}
|
|
18323
|
+
const edge = pastMin ? min : max;
|
|
18324
|
+
if (pastMin && velocity < 0) velocity = 0;
|
|
18325
|
+
if (pastMax && velocity > 0) velocity = 0;
|
|
18326
|
+
const displacement = edge - position;
|
|
18327
|
+
velocity += displacement * spring * dt;
|
|
18328
|
+
const decay = Math.exp(-damping * dt);
|
|
18329
|
+
velocity *= decay;
|
|
18330
|
+
position += velocity * dt;
|
|
18331
|
+
if (pastMin && position > min) {
|
|
18332
|
+
position = min;
|
|
18333
|
+
velocity = 0;
|
|
18334
|
+
}
|
|
18335
|
+
if (pastMax && position < max) {
|
|
18336
|
+
position = max;
|
|
18337
|
+
velocity = 0;
|
|
18338
|
+
}
|
|
18339
|
+
const settled = isAxisSettled({ position, velocity }, options);
|
|
18340
|
+
if (settled) {
|
|
18341
|
+
return { position: clampAxis(position, min, max), velocity: 0, settled: true };
|
|
18342
|
+
}
|
|
18343
|
+
return { position, velocity, settled: false };
|
|
18344
|
+
}
|
|
18345
|
+
if (!options.inertia || Math.abs(velocity) < frictionStop) {
|
|
18346
|
+
return { position, velocity: 0, settled: true };
|
|
18347
|
+
}
|
|
18348
|
+
position += velocity * dt;
|
|
18349
|
+
velocity *= Math.exp(-damping * dt);
|
|
18350
|
+
if (position < min || position > max) {
|
|
18351
|
+
if (!options.bounce) {
|
|
18352
|
+
position = clampAxis(position, min, max);
|
|
18353
|
+
return { position, velocity: 0, settled: true };
|
|
18354
|
+
}
|
|
18355
|
+
if (Math.abs(velocity) < frictionStop) {
|
|
18356
|
+
velocity = 0;
|
|
18357
|
+
}
|
|
18358
|
+
return { position, velocity, settled: false };
|
|
18359
|
+
}
|
|
18360
|
+
if (Math.abs(velocity) < frictionStop) {
|
|
18361
|
+
return { position, velocity: 0, settled: true };
|
|
18362
|
+
}
|
|
18363
|
+
return { position, velocity, settled: false };
|
|
18364
|
+
}
|
|
18365
|
+
function isAxisSettled(state, options) {
|
|
18366
|
+
const frictionStop = options.frictionStop ?? DRAG_FRICTION_STOP;
|
|
18367
|
+
const inside = state.position >= options.min - DRAG_SPRING_SETTLE_DISTANCE && state.position <= options.max + DRAG_SPRING_SETTLE_DISTANCE;
|
|
18368
|
+
const slow = Math.abs(state.velocity) < (options.frictionStop ?? DRAG_SPRING_SETTLE_VELOCITY);
|
|
18369
|
+
if (!inside) return false;
|
|
18370
|
+
return slow || Math.abs(state.velocity) < frictionStop;
|
|
18371
|
+
}
|
|
18372
|
+
function pushSample(samples, sample, maxCount = 8) {
|
|
18373
|
+
const next = samples.length >= maxCount ? samples.slice(samples.length - maxCount + 1) : samples.slice();
|
|
18374
|
+
next.push(sample);
|
|
18375
|
+
return next;
|
|
18376
|
+
}
|
|
18377
|
+
|
|
18378
|
+
// src/pano-scene-menu.tsx
|
|
18379
|
+
var import_jsx_runtime41 = require("react/jsx-runtime");
|
|
18380
|
+
var SCENE_MENU_DRAG_THRESHOLD_PX = 6;
|
|
18381
|
+
var DEFAULT_PANO_SCENE_MENU_APPEARANCE = {
|
|
18382
|
+
background: "rgba(16, 16, 16, 0.72)",
|
|
18383
|
+
padding: "8px 10px",
|
|
18384
|
+
itemWidth: 128,
|
|
18385
|
+
itemHeight: 80,
|
|
18386
|
+
gap: 8,
|
|
18387
|
+
borderRadius: 8,
|
|
18388
|
+
selectionColor: "#ffffff",
|
|
18389
|
+
selectionWidth: 2,
|
|
18390
|
+
labelBackground: "rgba(0, 0, 0, 0.55)",
|
|
18391
|
+
labelColor: "#ffffff",
|
|
18392
|
+
labelAlign: "start",
|
|
18393
|
+
fontSize: 12,
|
|
18394
|
+
controlColor: "#ffffff",
|
|
18395
|
+
controlBackground: "rgba(255, 255, 255, 0.12)"
|
|
18396
|
+
};
|
|
18397
|
+
var DEFAULT_INSET = 12;
|
|
18398
|
+
function cssLength(value) {
|
|
18399
|
+
return typeof value === "number" ? `${value}px` : value;
|
|
18400
|
+
}
|
|
18401
|
+
function resolveAppearance2(appearance) {
|
|
18402
|
+
return {
|
|
18403
|
+
...DEFAULT_PANO_SCENE_MENU_APPEARANCE,
|
|
18404
|
+
...appearance
|
|
18405
|
+
};
|
|
18406
|
+
}
|
|
18407
|
+
function resolveInset(inset) {
|
|
18408
|
+
if (inset === void 0) {
|
|
18409
|
+
const value = cssLength(DEFAULT_INSET);
|
|
18410
|
+
return { top: value, right: value, bottom: value, left: value };
|
|
18411
|
+
}
|
|
18412
|
+
if (typeof inset === "number" || typeof inset === "string") {
|
|
18413
|
+
const value = cssLength(inset);
|
|
18414
|
+
return { top: value, right: value, bottom: value, left: value };
|
|
18415
|
+
}
|
|
18416
|
+
return {
|
|
18417
|
+
top: cssLength(inset.top ?? DEFAULT_INSET),
|
|
18418
|
+
right: cssLength(inset.right ?? DEFAULT_INSET),
|
|
18419
|
+
bottom: cssLength(inset.bottom ?? DEFAULT_INSET),
|
|
18420
|
+
left: cssLength(inset.left ?? DEFAULT_INSET)
|
|
18421
|
+
};
|
|
18422
|
+
}
|
|
18423
|
+
function itemLabel(item) {
|
|
18424
|
+
return item.title?.trim() || item.id;
|
|
18425
|
+
}
|
|
18426
|
+
function isHorizontal(placement) {
|
|
18427
|
+
return placement === "top" || placement === "bottom";
|
|
18428
|
+
}
|
|
18429
|
+
var CHEVRON_PATHS = {
|
|
18430
|
+
// Keep glyphs optically centered in the 16×16 viewBox.
|
|
18431
|
+
up: "M3 11l5-6 5 6",
|
|
18432
|
+
down: "M3 5l5 6 5-6",
|
|
18433
|
+
left: "M11 3 5 8l6 5",
|
|
18434
|
+
right: "M5 3l6 5-6 5"
|
|
18435
|
+
};
|
|
18436
|
+
function arrowChevron(direction, orientation2) {
|
|
18437
|
+
if (direction === "prev") {
|
|
18438
|
+
return orientation2 === "horizontal" ? "left" : "up";
|
|
18439
|
+
}
|
|
18440
|
+
return orientation2 === "horizontal" ? "right" : "down";
|
|
18441
|
+
}
|
|
18442
|
+
function toggleChevron(placement, expanded) {
|
|
18443
|
+
switch (placement) {
|
|
18444
|
+
case "bottom":
|
|
18445
|
+
return expanded ? "down" : "up";
|
|
18446
|
+
case "top":
|
|
18447
|
+
return expanded ? "up" : "down";
|
|
18448
|
+
case "left":
|
|
18449
|
+
return expanded ? "left" : "right";
|
|
18450
|
+
case "right":
|
|
18451
|
+
return expanded ? "right" : "left";
|
|
18452
|
+
default: {
|
|
18453
|
+
const exhaustive = placement;
|
|
18454
|
+
void exhaustive;
|
|
18455
|
+
return "down";
|
|
18456
|
+
}
|
|
18457
|
+
}
|
|
18458
|
+
}
|
|
18459
|
+
function dockInset(placement, inset) {
|
|
18460
|
+
switch (placement) {
|
|
18461
|
+
case "top":
|
|
18462
|
+
return inset.top;
|
|
18463
|
+
case "bottom":
|
|
18464
|
+
return inset.bottom;
|
|
18465
|
+
case "left":
|
|
18466
|
+
return inset.left;
|
|
18467
|
+
case "right":
|
|
18468
|
+
return inset.right;
|
|
18469
|
+
default: {
|
|
18470
|
+
const exhaustive = placement;
|
|
18471
|
+
void exhaustive;
|
|
18472
|
+
return inset.bottom;
|
|
18473
|
+
}
|
|
18474
|
+
}
|
|
18475
|
+
}
|
|
18476
|
+
function Chevron({ arrow }) {
|
|
18477
|
+
return /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
18478
|
+
"svg",
|
|
18479
|
+
{
|
|
18480
|
+
"aria-hidden": true,
|
|
18481
|
+
fill: "none",
|
|
18482
|
+
height: "16",
|
|
18483
|
+
stroke: "currentColor",
|
|
18484
|
+
strokeLinecap: "round",
|
|
18485
|
+
strokeLinejoin: "round",
|
|
18486
|
+
strokeWidth: "1.75",
|
|
18487
|
+
viewBox: "0 0 16 16",
|
|
18488
|
+
width: "16",
|
|
18489
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsx)("path", { d: CHEVRON_PATHS[arrow] })
|
|
18490
|
+
}
|
|
18491
|
+
);
|
|
18492
|
+
}
|
|
18493
|
+
function ControlButton({
|
|
18494
|
+
className,
|
|
18495
|
+
disabled,
|
|
18496
|
+
label,
|
|
18497
|
+
onClick,
|
|
18498
|
+
children
|
|
18499
|
+
}) {
|
|
18500
|
+
return /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
18501
|
+
"button",
|
|
18502
|
+
{
|
|
18503
|
+
"aria-label": label,
|
|
18504
|
+
className: cn("pano-scene-menu-control", className),
|
|
18505
|
+
disabled,
|
|
18506
|
+
onClick,
|
|
18507
|
+
onPointerDown: (event) => {
|
|
18508
|
+
event.stopPropagation();
|
|
18509
|
+
},
|
|
18510
|
+
title: label,
|
|
18511
|
+
type: "button",
|
|
18512
|
+
children
|
|
18513
|
+
}
|
|
18514
|
+
);
|
|
18515
|
+
}
|
|
18516
|
+
function horizontalAlignStyle(align, inset, widthValue) {
|
|
18517
|
+
const left = `calc(${inset.left} + var(--pano-safe-left))`;
|
|
18518
|
+
const right = `calc(${inset.right} + var(--pano-safe-right))`;
|
|
18519
|
+
if (!widthValue) {
|
|
18520
|
+
return { left, right, width: void 0, marginInline: void 0 };
|
|
18521
|
+
}
|
|
18522
|
+
switch (align) {
|
|
18523
|
+
case "start":
|
|
18524
|
+
return { left, right: "auto", width: widthValue, marginInline: void 0 };
|
|
18525
|
+
case "end":
|
|
18526
|
+
return { left: "auto", right, width: widthValue, marginInline: void 0 };
|
|
18527
|
+
case "center":
|
|
18528
|
+
return { left, right, width: widthValue, marginInline: "auto" };
|
|
18529
|
+
default: {
|
|
18530
|
+
const exhaustive = align;
|
|
18531
|
+
void exhaustive;
|
|
18532
|
+
return { left, right, width: widthValue, marginInline: "auto" };
|
|
18533
|
+
}
|
|
18534
|
+
}
|
|
18535
|
+
}
|
|
18536
|
+
function verticalAlignStyle(align, inset, heightValue) {
|
|
18537
|
+
const top = `calc(${inset.top} + var(--pano-safe-top))`;
|
|
18538
|
+
const bottom = `calc(${inset.bottom} + var(--pano-safe-bottom))`;
|
|
18539
|
+
if (!heightValue) {
|
|
18540
|
+
return { top, bottom, height: void 0, marginBlock: void 0 };
|
|
18541
|
+
}
|
|
18542
|
+
switch (align) {
|
|
18543
|
+
case "start":
|
|
18544
|
+
return { top, bottom: "auto", height: heightValue, marginBlock: void 0 };
|
|
18545
|
+
case "end":
|
|
18546
|
+
return { top: "auto", bottom, height: heightValue, marginBlock: void 0 };
|
|
18547
|
+
case "center":
|
|
18548
|
+
return { top, bottom, height: heightValue, marginBlock: "auto" };
|
|
18549
|
+
default: {
|
|
18550
|
+
const exhaustive = align;
|
|
18551
|
+
void exhaustive;
|
|
18552
|
+
return { top, bottom, height: heightValue, marginBlock: "auto" };
|
|
18553
|
+
}
|
|
18554
|
+
}
|
|
18555
|
+
}
|
|
18556
|
+
function placementBoxStyle(placement, inset, width, height, align) {
|
|
18557
|
+
const widthValue = width === void 0 ? void 0 : cssLength(width);
|
|
18558
|
+
const heightValue = height === void 0 ? void 0 : cssLength(height);
|
|
18559
|
+
const maxWidth = `calc(100% - ${inset.left} - ${inset.right} - var(--pano-safe-left) - var(--pano-safe-right))`;
|
|
18560
|
+
const maxHeight = `calc(100% - ${inset.top} - ${inset.bottom} - var(--pano-safe-top) - var(--pano-safe-bottom))`;
|
|
18561
|
+
switch (placement) {
|
|
18562
|
+
case "top":
|
|
18563
|
+
return {
|
|
18564
|
+
...horizontalAlignStyle(align, inset, widthValue),
|
|
18565
|
+
top: `calc(${inset.top} + var(--pano-safe-top))`,
|
|
18566
|
+
bottom: "auto",
|
|
18567
|
+
maxWidth,
|
|
18568
|
+
height: heightValue,
|
|
18569
|
+
maxHeight
|
|
18570
|
+
};
|
|
18571
|
+
case "bottom":
|
|
18572
|
+
return {
|
|
18573
|
+
...horizontalAlignStyle(align, inset, widthValue),
|
|
18574
|
+
top: "auto",
|
|
18575
|
+
bottom: `calc(${inset.bottom} + var(--pano-safe-bottom))`,
|
|
18576
|
+
maxWidth,
|
|
18577
|
+
height: heightValue,
|
|
18578
|
+
maxHeight
|
|
18579
|
+
};
|
|
18580
|
+
case "left":
|
|
18581
|
+
return {
|
|
18582
|
+
...verticalAlignStyle(align, inset, heightValue),
|
|
18583
|
+
right: "auto",
|
|
18584
|
+
left: `calc(${inset.left} + var(--pano-safe-left))`,
|
|
18585
|
+
width: widthValue,
|
|
18586
|
+
maxWidth,
|
|
18587
|
+
maxHeight
|
|
18588
|
+
};
|
|
18589
|
+
case "right":
|
|
18590
|
+
return {
|
|
18591
|
+
...verticalAlignStyle(align, inset, heightValue),
|
|
18592
|
+
right: `calc(${inset.right} + var(--pano-safe-right))`,
|
|
18593
|
+
left: "auto",
|
|
18594
|
+
width: widthValue,
|
|
18595
|
+
maxWidth,
|
|
18596
|
+
maxHeight
|
|
18597
|
+
};
|
|
18598
|
+
default: {
|
|
18599
|
+
const exhaustive = placement;
|
|
18600
|
+
void exhaustive;
|
|
18601
|
+
return {};
|
|
18602
|
+
}
|
|
18603
|
+
}
|
|
18604
|
+
}
|
|
18605
|
+
function PanoSceneMenu({
|
|
18606
|
+
items,
|
|
18607
|
+
activeId = null,
|
|
18608
|
+
onSelect,
|
|
18609
|
+
placement = "bottom",
|
|
18610
|
+
align = "center",
|
|
18611
|
+
inset,
|
|
18612
|
+
width,
|
|
18613
|
+
height,
|
|
18614
|
+
collapsible = false,
|
|
18615
|
+
defaultExpanded = true,
|
|
18616
|
+
expanded: expandedProp,
|
|
18617
|
+
onExpandedChange,
|
|
18618
|
+
showArrows = false,
|
|
18619
|
+
loop = false,
|
|
18620
|
+
dragMotion: dragMotionProp,
|
|
18621
|
+
appearance,
|
|
18622
|
+
className,
|
|
18623
|
+
style,
|
|
18624
|
+
label = "Scenes",
|
|
18625
|
+
previousLabel = "Previous scene",
|
|
18626
|
+
nextLabel = "Next scene",
|
|
18627
|
+
expandLabel = "Show scenes",
|
|
18628
|
+
collapseLabel = "Hide scenes"
|
|
18629
|
+
}) {
|
|
18630
|
+
const listId = (0, import_react62.useId)();
|
|
18631
|
+
const listRef = (0, import_react62.useRef)(null);
|
|
18632
|
+
const trackRef = (0, import_react62.useRef)(null);
|
|
18633
|
+
const itemRefs = (0, import_react62.useRef)(/* @__PURE__ */ new Map());
|
|
18634
|
+
const resolved = resolveAppearance2(appearance);
|
|
18635
|
+
const resolvedInset = resolveInset(inset);
|
|
18636
|
+
const horizontal = isHorizontal(placement);
|
|
18637
|
+
const customDrag = dragMotionProp !== false;
|
|
18638
|
+
const dragMotion = resolveDragMotion(
|
|
18639
|
+
dragMotionProp === false ? false : dragMotionProp
|
|
18640
|
+
);
|
|
18641
|
+
const isExpandedControlled = expandedProp !== void 0;
|
|
18642
|
+
const [internalExpanded, setInternalExpanded] = (0, import_react62.useState)(defaultExpanded);
|
|
18643
|
+
const expanded = collapsible ? isExpandedControlled ? expandedProp : internalExpanded : true;
|
|
18644
|
+
const [offset, setOffset] = (0, import_react62.useState)(0);
|
|
18645
|
+
const [viewportSize, setViewportSize] = (0, import_react62.useState)(0);
|
|
18646
|
+
const [contentSize, setContentSize] = (0, import_react62.useState)(0);
|
|
18647
|
+
const offsetRef = (0, import_react62.useRef)(0);
|
|
18648
|
+
const dragRef = (0, import_react62.useRef)(null);
|
|
18649
|
+
const animRef = (0, import_react62.useRef)(null);
|
|
18650
|
+
const maxOffset = Math.max(0, contentSize - viewportSize);
|
|
18651
|
+
offsetRef.current = offset;
|
|
18652
|
+
const activeIndex = (0, import_react62.useMemo)(() => {
|
|
18653
|
+
if (activeId == null) {
|
|
18654
|
+
return -1;
|
|
18655
|
+
}
|
|
18656
|
+
return items.findIndex((item) => item.id === activeId);
|
|
18657
|
+
}, [activeId, items]);
|
|
18658
|
+
const cancelScrollAnimation = (0, import_react62.useCallback)(() => {
|
|
18659
|
+
const anim = animRef.current;
|
|
18660
|
+
if (anim?.raf != null) {
|
|
18661
|
+
cancelAnimationFrame(anim.raf);
|
|
18662
|
+
}
|
|
18663
|
+
animRef.current = null;
|
|
18664
|
+
}, []);
|
|
18665
|
+
const clampOffset = (0, import_react62.useCallback)(
|
|
18666
|
+
(value) => Math.min(maxOffset, Math.max(0, value)),
|
|
18667
|
+
[maxOffset]
|
|
18668
|
+
);
|
|
18669
|
+
const startScrollAnimation = (0, import_react62.useCallback)(
|
|
18670
|
+
(velocity) => {
|
|
18671
|
+
cancelScrollAnimation();
|
|
18672
|
+
const current = offsetRef.current;
|
|
18673
|
+
const needsSpring = dragMotion.bounce && (current < 0 || current > maxOffset);
|
|
18674
|
+
const nextVelocity = dragMotion.inertia ? velocity : 0;
|
|
18675
|
+
if (!needsSpring && Math.abs(nextVelocity) < 1) {
|
|
18676
|
+
setOffset(clampOffset(current));
|
|
18677
|
+
return;
|
|
18678
|
+
}
|
|
18679
|
+
if (!dragMotion.inertia && !dragMotion.bounce) {
|
|
18680
|
+
setOffset(clampOffset(current));
|
|
18681
|
+
return;
|
|
18682
|
+
}
|
|
18683
|
+
const anim = {
|
|
18684
|
+
raf: null,
|
|
18685
|
+
lastTime: performance.now(),
|
|
18686
|
+
position: current,
|
|
18687
|
+
velocity: nextVelocity
|
|
18688
|
+
};
|
|
18689
|
+
animRef.current = anim;
|
|
18690
|
+
const tick = (now) => {
|
|
18691
|
+
if (animRef.current !== anim) return;
|
|
18692
|
+
const dt = Math.min(0.064, Math.max(0, (now - anim.lastTime) / 1e3));
|
|
18693
|
+
anim.lastTime = now;
|
|
18694
|
+
const next = integrateAxis(
|
|
18695
|
+
{ position: anim.position, velocity: anim.velocity },
|
|
18696
|
+
dt,
|
|
18697
|
+
{
|
|
18698
|
+
min: 0,
|
|
18699
|
+
max: maxOffset,
|
|
18700
|
+
inertia: dragMotion.inertia,
|
|
18701
|
+
bounce: dragMotion.bounce
|
|
18702
|
+
}
|
|
18703
|
+
);
|
|
18704
|
+
anim.position = next.position;
|
|
18705
|
+
anim.velocity = next.velocity;
|
|
18706
|
+
setOffset(next.position);
|
|
18707
|
+
if (next.settled) {
|
|
18708
|
+
setOffset(clampOffset(next.position));
|
|
18709
|
+
animRef.current = null;
|
|
18710
|
+
return;
|
|
18711
|
+
}
|
|
18712
|
+
anim.raf = requestAnimationFrame(tick);
|
|
18713
|
+
};
|
|
18714
|
+
anim.raf = requestAnimationFrame(tick);
|
|
18715
|
+
},
|
|
18716
|
+
[
|
|
18717
|
+
cancelScrollAnimation,
|
|
18718
|
+
clampOffset,
|
|
18719
|
+
dragMotion.bounce,
|
|
18720
|
+
dragMotion.inertia,
|
|
18721
|
+
maxOffset
|
|
18722
|
+
]
|
|
18723
|
+
);
|
|
18724
|
+
(0, import_react62.useEffect)(() => () => cancelScrollAnimation(), [cancelScrollAnimation]);
|
|
18725
|
+
(0, import_react62.useLayoutEffect)(() => {
|
|
18726
|
+
if (!customDrag || !expanded) return;
|
|
18727
|
+
const list = listRef.current;
|
|
18728
|
+
const track = trackRef.current;
|
|
18729
|
+
if (!list || !track) return;
|
|
18730
|
+
const measure = () => {
|
|
18731
|
+
const nextViewport = horizontal ? list.clientWidth : list.clientHeight;
|
|
18732
|
+
const nextContent = horizontal ? track.scrollWidth : track.scrollHeight;
|
|
18733
|
+
setViewportSize(
|
|
18734
|
+
(previous) => previous === nextViewport ? previous : nextViewport
|
|
18735
|
+
);
|
|
18736
|
+
setContentSize(
|
|
18737
|
+
(previous) => previous === nextContent ? previous : nextContent
|
|
18738
|
+
);
|
|
18739
|
+
};
|
|
18740
|
+
measure();
|
|
18741
|
+
const observer = new ResizeObserver(measure);
|
|
18742
|
+
observer.observe(list);
|
|
18743
|
+
observer.observe(track);
|
|
18744
|
+
return () => observer.disconnect();
|
|
18745
|
+
}, [customDrag, expanded, horizontal, items]);
|
|
18746
|
+
(0, import_react62.useEffect)(() => {
|
|
18747
|
+
if (!customDrag) return;
|
|
18748
|
+
if (dragRef.current || animRef.current) return;
|
|
18749
|
+
setOffset((previous) => Math.min(maxOffset, Math.max(0, previous)));
|
|
18750
|
+
}, [customDrag, maxOffset]);
|
|
18751
|
+
(0, import_react62.useEffect)(() => {
|
|
18752
|
+
if (!expanded || activeId == null) {
|
|
18753
|
+
return;
|
|
18754
|
+
}
|
|
18755
|
+
const node = itemRefs.current.get(activeId);
|
|
18756
|
+
if (!node) return;
|
|
18757
|
+
if (!customDrag) {
|
|
18758
|
+
node.scrollIntoView({
|
|
18759
|
+
behavior: "smooth",
|
|
18760
|
+
block: "nearest",
|
|
18761
|
+
inline: "nearest"
|
|
18762
|
+
});
|
|
18763
|
+
return;
|
|
18764
|
+
}
|
|
18765
|
+
const list = listRef.current;
|
|
18766
|
+
if (!list) return;
|
|
18767
|
+
const listRect = list.getBoundingClientRect();
|
|
18768
|
+
const itemRect = node.getBoundingClientRect();
|
|
18769
|
+
if (horizontal) {
|
|
18770
|
+
const itemStart2 = itemRect.left - listRect.left + offsetRef.current;
|
|
18771
|
+
const itemEnd2 = itemStart2 + itemRect.width;
|
|
18772
|
+
let next2 = offsetRef.current;
|
|
18773
|
+
if (itemStart2 < next2) next2 = itemStart2;
|
|
18774
|
+
else if (itemEnd2 > next2 + listRect.width) next2 = itemEnd2 - listRect.width;
|
|
18775
|
+
cancelScrollAnimation();
|
|
18776
|
+
setOffset(clampOffset(next2));
|
|
18777
|
+
return;
|
|
18778
|
+
}
|
|
18779
|
+
const itemStart = itemRect.top - listRect.top + offsetRef.current;
|
|
18780
|
+
const itemEnd = itemStart + itemRect.height;
|
|
18781
|
+
let next = offsetRef.current;
|
|
18782
|
+
if (itemStart < next) next = itemStart;
|
|
18783
|
+
else if (itemEnd > next + listRect.height) next = itemEnd - listRect.height;
|
|
18784
|
+
cancelScrollAnimation();
|
|
18785
|
+
setOffset(clampOffset(next));
|
|
18786
|
+
}, [
|
|
18787
|
+
activeId,
|
|
18788
|
+
cancelScrollAnimation,
|
|
18789
|
+
clampOffset,
|
|
18790
|
+
customDrag,
|
|
18791
|
+
expanded,
|
|
18792
|
+
horizontal
|
|
18793
|
+
]);
|
|
18794
|
+
const rootStyle = (0, import_react62.useMemo)(() => {
|
|
18795
|
+
const vars = {
|
|
18796
|
+
"--pano-scene-menu-background": resolved.background,
|
|
18797
|
+
"--pano-scene-menu-padding": cssLength(resolved.padding),
|
|
18798
|
+
"--pano-scene-menu-item-width": cssLength(resolved.itemWidth),
|
|
18799
|
+
"--pano-scene-menu-item-height": cssLength(resolved.itemHeight),
|
|
18800
|
+
"--pano-scene-menu-gap": cssLength(resolved.gap),
|
|
18801
|
+
"--pano-scene-menu-radius": cssLength(resolved.borderRadius),
|
|
18802
|
+
"--pano-scene-menu-selection-color": resolved.selectionColor,
|
|
18803
|
+
"--pano-scene-menu-selection-width": cssLength(resolved.selectionWidth),
|
|
18804
|
+
"--pano-scene-menu-label-background": resolved.labelBackground,
|
|
18805
|
+
"--pano-scene-menu-label-color": resolved.labelColor,
|
|
18806
|
+
"--pano-scene-menu-label-align": resolved.labelAlign,
|
|
18807
|
+
"--pano-scene-menu-font-size": cssLength(resolved.fontSize),
|
|
18808
|
+
"--pano-scene-menu-control-color": resolved.controlColor,
|
|
18809
|
+
"--pano-scene-menu-control-background": resolved.controlBackground,
|
|
18810
|
+
"--pano-scene-menu-dock-inset": dockInset(placement, resolvedInset)
|
|
18811
|
+
};
|
|
18812
|
+
return {
|
|
18813
|
+
...vars,
|
|
18814
|
+
...placementBoxStyle(placement, resolvedInset, width, height, align),
|
|
18815
|
+
...style
|
|
18816
|
+
};
|
|
18817
|
+
}, [align, height, placement, resolved, resolvedInset, style, width]);
|
|
18818
|
+
const setExpanded = (next) => {
|
|
18819
|
+
if (!collapsible) {
|
|
18820
|
+
return;
|
|
18821
|
+
}
|
|
18822
|
+
if (!isExpandedControlled) {
|
|
18823
|
+
setInternalExpanded(next);
|
|
18824
|
+
}
|
|
18825
|
+
onExpandedChange?.(next);
|
|
18826
|
+
};
|
|
18827
|
+
const selectAt = (index) => {
|
|
18828
|
+
const item = items[index];
|
|
18829
|
+
if (!item) {
|
|
18830
|
+
return;
|
|
18831
|
+
}
|
|
18832
|
+
onSelect?.(item.id);
|
|
18833
|
+
itemRefs.current.get(item.id)?.focus({ preventScroll: true });
|
|
18834
|
+
};
|
|
18835
|
+
const selectRelative = (delta) => {
|
|
18836
|
+
if (items.length === 0) {
|
|
18837
|
+
return;
|
|
18838
|
+
}
|
|
18839
|
+
const current = activeIndex >= 0 ? activeIndex : 0;
|
|
18840
|
+
if (loop) {
|
|
18841
|
+
const next = ((current + delta) % items.length + items.length) % items.length;
|
|
18842
|
+
selectAt(next);
|
|
18843
|
+
return;
|
|
18844
|
+
}
|
|
18845
|
+
selectAt(Math.max(0, Math.min(items.length - 1, current + delta)));
|
|
18846
|
+
};
|
|
18847
|
+
const onKeyDown = (event) => {
|
|
18848
|
+
if (items.length === 0 || !expanded) {
|
|
18849
|
+
return;
|
|
18850
|
+
}
|
|
18851
|
+
const current = activeIndex >= 0 ? activeIndex : Math.max(
|
|
18852
|
+
0,
|
|
18853
|
+
items.findIndex(
|
|
18854
|
+
(item) => itemRefs.current.get(item.id) === event.target
|
|
18855
|
+
)
|
|
18856
|
+
);
|
|
18857
|
+
const backward = horizontal ? event.key === "ArrowLeft" : event.key === "ArrowUp";
|
|
18858
|
+
const forward = horizontal ? event.key === "ArrowRight" : event.key === "ArrowDown";
|
|
18859
|
+
if (backward) {
|
|
18860
|
+
event.preventDefault();
|
|
18861
|
+
if (loop) {
|
|
18862
|
+
selectAt((current - 1 + items.length) % items.length);
|
|
18863
|
+
} else {
|
|
18864
|
+
selectAt(Math.max(0, current - 1));
|
|
18865
|
+
}
|
|
18866
|
+
return;
|
|
18867
|
+
}
|
|
18868
|
+
if (forward) {
|
|
18869
|
+
event.preventDefault();
|
|
18870
|
+
if (loop) {
|
|
18871
|
+
selectAt((current + 1) % items.length);
|
|
18872
|
+
} else {
|
|
18873
|
+
selectAt(Math.min(items.length - 1, current + 1));
|
|
18874
|
+
}
|
|
18875
|
+
return;
|
|
18876
|
+
}
|
|
18877
|
+
switch (event.key) {
|
|
18878
|
+
case "Home": {
|
|
18879
|
+
event.preventDefault();
|
|
18880
|
+
selectAt(0);
|
|
18881
|
+
break;
|
|
18882
|
+
}
|
|
18883
|
+
case "End": {
|
|
18884
|
+
event.preventDefault();
|
|
18885
|
+
selectAt(items.length - 1);
|
|
18886
|
+
break;
|
|
18887
|
+
}
|
|
18888
|
+
default:
|
|
18889
|
+
break;
|
|
18890
|
+
}
|
|
18891
|
+
};
|
|
18892
|
+
const onWheel = (event) => {
|
|
18893
|
+
const list = listRef.current;
|
|
18894
|
+
if (!list) {
|
|
18895
|
+
return;
|
|
18896
|
+
}
|
|
18897
|
+
if (!customDrag) {
|
|
18898
|
+
if (horizontal) {
|
|
18899
|
+
const canScroll2 = list.scrollWidth > list.clientWidth + 1;
|
|
18900
|
+
if (!canScroll2 || Math.abs(event.deltaY) <= Math.abs(event.deltaX)) {
|
|
18901
|
+
return;
|
|
18902
|
+
}
|
|
18903
|
+
event.preventDefault();
|
|
18904
|
+
event.stopPropagation();
|
|
18905
|
+
list.scrollLeft += event.deltaY;
|
|
18906
|
+
return;
|
|
18907
|
+
}
|
|
18908
|
+
const canScroll = list.scrollHeight > list.clientHeight + 1;
|
|
18909
|
+
if (!canScroll || Math.abs(event.deltaX) <= Math.abs(event.deltaY)) {
|
|
18910
|
+
return;
|
|
18911
|
+
}
|
|
18912
|
+
event.preventDefault();
|
|
18913
|
+
event.stopPropagation();
|
|
18914
|
+
list.scrollTop += event.deltaX;
|
|
18915
|
+
return;
|
|
18916
|
+
}
|
|
18917
|
+
if (horizontal) {
|
|
18918
|
+
if (maxOffset <= 0 || Math.abs(event.deltaY) <= Math.abs(event.deltaX)) {
|
|
18919
|
+
return;
|
|
18920
|
+
}
|
|
18921
|
+
event.preventDefault();
|
|
18922
|
+
event.stopPropagation();
|
|
18923
|
+
cancelScrollAnimation();
|
|
18924
|
+
setOffset((previous) => clampOffset(previous + event.deltaY));
|
|
18925
|
+
return;
|
|
18926
|
+
}
|
|
18927
|
+
if (maxOffset <= 0 || Math.abs(event.deltaX) <= Math.abs(event.deltaY)) {
|
|
18928
|
+
return;
|
|
18929
|
+
}
|
|
18930
|
+
event.preventDefault();
|
|
18931
|
+
event.stopPropagation();
|
|
18932
|
+
cancelScrollAnimation();
|
|
18933
|
+
setOffset((previous) => clampOffset(previous + event.deltaX));
|
|
18934
|
+
};
|
|
18935
|
+
const axisPoint = (event) => horizontal ? event.clientX : event.clientY;
|
|
18936
|
+
const endSuppressClickRef = (0, import_react62.useRef)(false);
|
|
18937
|
+
const beginListDrag = (event, captureTarget) => {
|
|
18938
|
+
if (!customDrag || event.button !== 0) return;
|
|
18939
|
+
cancelScrollAnimation();
|
|
18940
|
+
const now = performance.now();
|
|
18941
|
+
const origin = axisPoint(event);
|
|
18942
|
+
dragRef.current = {
|
|
18943
|
+
pointerId: event.pointerId,
|
|
18944
|
+
origin,
|
|
18945
|
+
startOffset: offsetRef.current,
|
|
18946
|
+
samples: [{ t: now, position: offsetRef.current }],
|
|
18947
|
+
moved: false,
|
|
18948
|
+
suppressClick: false
|
|
18949
|
+
};
|
|
18950
|
+
try {
|
|
18951
|
+
captureTarget.setPointerCapture(event.pointerId);
|
|
18952
|
+
} catch {
|
|
18953
|
+
}
|
|
18954
|
+
};
|
|
18955
|
+
const onListPointerMove = (event) => {
|
|
18956
|
+
const drag = dragRef.current;
|
|
18957
|
+
if (!drag || drag.pointerId !== event.pointerId) return;
|
|
18958
|
+
const point = axisPoint(event);
|
|
18959
|
+
const delta = point - drag.origin;
|
|
18960
|
+
if (!drag.moved && Math.abs(delta) >= SCENE_MENU_DRAG_THRESHOLD_PX) {
|
|
18961
|
+
drag.moved = true;
|
|
18962
|
+
drag.suppressClick = true;
|
|
18963
|
+
}
|
|
18964
|
+
if (!drag.moved) return;
|
|
18965
|
+
const raw = drag.startOffset - delta;
|
|
18966
|
+
const now = performance.now();
|
|
18967
|
+
drag.samples = pushSample(drag.samples, { t: now, position: raw });
|
|
18968
|
+
setOffset(
|
|
18969
|
+
constrainDragPosition(
|
|
18970
|
+
raw,
|
|
18971
|
+
0,
|
|
18972
|
+
maxOffset,
|
|
18973
|
+
Math.max(1, viewportSize),
|
|
18974
|
+
dragMotion.bounce
|
|
18975
|
+
)
|
|
18976
|
+
);
|
|
18977
|
+
event.preventDefault();
|
|
18978
|
+
};
|
|
18979
|
+
const finishPointerWithClickGuard = (event) => {
|
|
18980
|
+
const drag = dragRef.current;
|
|
18981
|
+
if (!drag || drag.pointerId !== event.pointerId) return;
|
|
18982
|
+
const suppress = drag.suppressClick;
|
|
18983
|
+
dragRef.current = null;
|
|
18984
|
+
try {
|
|
18985
|
+
if (event.currentTarget.hasPointerCapture(event.pointerId)) {
|
|
18986
|
+
event.currentTarget.releasePointerCapture(event.pointerId);
|
|
18987
|
+
}
|
|
18988
|
+
} catch {
|
|
18989
|
+
}
|
|
18990
|
+
if (suppress) {
|
|
18991
|
+
endSuppressClickRef.current = true;
|
|
18992
|
+
queueMicrotask(() => {
|
|
18993
|
+
endSuppressClickRef.current = false;
|
|
18994
|
+
});
|
|
18995
|
+
}
|
|
18996
|
+
if (!drag.moved) return;
|
|
18997
|
+
if (event.type === "pointercancel") {
|
|
18998
|
+
setOffset(clampOffset(offsetRef.current));
|
|
18999
|
+
return;
|
|
19000
|
+
}
|
|
19001
|
+
startScrollAnimation(velocityFromSamples(drag.samples));
|
|
19002
|
+
};
|
|
19003
|
+
const onItemClick = (event, id) => {
|
|
19004
|
+
if (endSuppressClickRef.current) {
|
|
19005
|
+
event.preventDefault();
|
|
19006
|
+
event.stopPropagation();
|
|
19007
|
+
return;
|
|
19008
|
+
}
|
|
19009
|
+
onSelect?.(id);
|
|
19010
|
+
};
|
|
19011
|
+
const canStep = items.length > 1;
|
|
19012
|
+
const canGoPrevious = canStep && (loop || activeIndex !== 0);
|
|
19013
|
+
const canGoNext = canStep && (loop || activeIndex !== items.length - 1);
|
|
19014
|
+
const orientation2 = horizontal ? "horizontal" : "vertical";
|
|
19015
|
+
const trackStyle = customDrag ? {
|
|
19016
|
+
transform: horizontal ? `translate3d(${-offset}px, 0, 0)` : `translate3d(0, ${-offset}px, 0)`,
|
|
19017
|
+
willChange: "transform"
|
|
19018
|
+
} : void 0;
|
|
19019
|
+
return /* @__PURE__ */ (0, import_jsx_runtime41.jsxs)(
|
|
19020
|
+
"div",
|
|
19021
|
+
{
|
|
19022
|
+
"aria-label": label,
|
|
19023
|
+
className: cn("pano-scene-menu", className),
|
|
19024
|
+
"data-align": align,
|
|
19025
|
+
"data-collapsible": collapsible ? "true" : void 0,
|
|
19026
|
+
"data-drag-motion": customDrag ? "custom" : "native",
|
|
19027
|
+
"data-expanded": expanded ? "true" : "false",
|
|
19028
|
+
"data-orientation": orientation2,
|
|
19029
|
+
"data-placement": placement,
|
|
19030
|
+
role: "group",
|
|
19031
|
+
style: rootStyle,
|
|
19032
|
+
children: [
|
|
19033
|
+
/* @__PURE__ */ (0, import_jsx_runtime41.jsxs)(
|
|
19034
|
+
"div",
|
|
19035
|
+
{
|
|
19036
|
+
"aria-hidden": expanded ? void 0 : true,
|
|
19037
|
+
className: "pano-scene-menu-body",
|
|
19038
|
+
...!expanded ? { inert: true } : null,
|
|
19039
|
+
children: [
|
|
19040
|
+
showArrows ? /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19041
|
+
ControlButton,
|
|
19042
|
+
{
|
|
19043
|
+
className: "pano-scene-menu-arrow",
|
|
19044
|
+
disabled: !canGoPrevious || !expanded,
|
|
19045
|
+
label: previousLabel,
|
|
19046
|
+
onClick: () => selectRelative(-1),
|
|
19047
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(Chevron, { arrow: arrowChevron("prev", orientation2) })
|
|
19048
|
+
}
|
|
19049
|
+
) : null,
|
|
19050
|
+
/* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19051
|
+
"div",
|
|
19052
|
+
{
|
|
19053
|
+
"aria-label": label,
|
|
19054
|
+
className: "pano-scene-menu-list",
|
|
19055
|
+
id: listId,
|
|
19056
|
+
onKeyDown,
|
|
19057
|
+
onPointerCancel: customDrag ? finishPointerWithClickGuard : void 0,
|
|
19058
|
+
onPointerDown: customDrag ? (event) => beginListDrag(event, event.currentTarget) : void 0,
|
|
19059
|
+
onPointerMove: customDrag ? onListPointerMove : void 0,
|
|
19060
|
+
onPointerUp: customDrag ? finishPointerWithClickGuard : void 0,
|
|
19061
|
+
onWheel,
|
|
19062
|
+
ref: listRef,
|
|
19063
|
+
role: "radiogroup",
|
|
19064
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19065
|
+
"div",
|
|
19066
|
+
{
|
|
19067
|
+
className: "pano-scene-menu-track",
|
|
19068
|
+
ref: trackRef,
|
|
19069
|
+
style: trackStyle,
|
|
19070
|
+
children: items.map((item) => {
|
|
19071
|
+
const name = itemLabel(item);
|
|
19072
|
+
const selected = item.id === activeId;
|
|
19073
|
+
return /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19074
|
+
"button",
|
|
19075
|
+
{
|
|
19076
|
+
"aria-checked": selected,
|
|
19077
|
+
className: "pano-scene-menu-item",
|
|
19078
|
+
"data-active": selected ? "true" : void 0,
|
|
19079
|
+
onClick: (event) => onItemClick(event, item.id),
|
|
19080
|
+
onPointerDown: (event) => {
|
|
19081
|
+
event.stopPropagation();
|
|
19082
|
+
const list = listRef.current;
|
|
19083
|
+
if (customDrag && list) {
|
|
19084
|
+
beginListDrag(event, list);
|
|
19085
|
+
}
|
|
19086
|
+
},
|
|
19087
|
+
ref: (node) => {
|
|
19088
|
+
if (node) {
|
|
19089
|
+
itemRefs.current.set(item.id, node);
|
|
19090
|
+
} else {
|
|
19091
|
+
itemRefs.current.delete(item.id);
|
|
19092
|
+
}
|
|
19093
|
+
},
|
|
19094
|
+
role: "radio",
|
|
19095
|
+
tabIndex: selected || activeId == null && item === items[0] ? 0 : -1,
|
|
19096
|
+
title: name,
|
|
19097
|
+
type: "button",
|
|
19098
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsxs)("span", { className: "pano-scene-menu-thumb", children: [
|
|
19099
|
+
/* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19100
|
+
"img",
|
|
19101
|
+
{
|
|
19102
|
+
alt: "",
|
|
19103
|
+
decoding: "async",
|
|
19104
|
+
draggable: false,
|
|
19105
|
+
src: item.thumbnailUrl
|
|
19106
|
+
}
|
|
19107
|
+
),
|
|
19108
|
+
/* @__PURE__ */ (0, import_jsx_runtime41.jsx)("span", { className: "pano-scene-menu-label", children: name })
|
|
19109
|
+
] })
|
|
19110
|
+
},
|
|
19111
|
+
item.id
|
|
19112
|
+
);
|
|
19113
|
+
})
|
|
19114
|
+
}
|
|
19115
|
+
)
|
|
19116
|
+
}
|
|
19117
|
+
),
|
|
19118
|
+
showArrows ? /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19119
|
+
ControlButton,
|
|
19120
|
+
{
|
|
19121
|
+
className: "pano-scene-menu-arrow",
|
|
19122
|
+
disabled: !canGoNext || !expanded,
|
|
19123
|
+
label: nextLabel,
|
|
19124
|
+
onClick: () => selectRelative(1),
|
|
19125
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(Chevron, { arrow: arrowChevron("next", orientation2) })
|
|
19126
|
+
}
|
|
19127
|
+
) : null
|
|
19128
|
+
]
|
|
19129
|
+
}
|
|
19130
|
+
),
|
|
19131
|
+
collapsible ? /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(
|
|
19132
|
+
ControlButton,
|
|
19133
|
+
{
|
|
19134
|
+
className: "pano-scene-menu-toggle",
|
|
19135
|
+
label: expanded ? collapseLabel : expandLabel,
|
|
19136
|
+
onClick: () => setExpanded(!expanded),
|
|
19137
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime41.jsx)(Chevron, { arrow: toggleChevron(placement, expanded) })
|
|
19138
|
+
}
|
|
19139
|
+
) : null
|
|
19140
|
+
]
|
|
19141
|
+
}
|
|
19142
|
+
);
|
|
19143
|
+
}
|
|
19144
|
+
|
|
19145
|
+
// src/use-pano-viewer.ts
|
|
19146
|
+
var import_react63 = require("react");
|
|
18245
19147
|
function createPanoViewerHandle(ref) {
|
|
18246
19148
|
return {
|
|
18247
19149
|
getView: () => ref.current?.getView() ?? { yaw: 0, pitch: 0, fov: 75 },
|
|
@@ -18323,16 +19225,16 @@ function createPanoViewerHandle(ref) {
|
|
|
18323
19225
|
};
|
|
18324
19226
|
}
|
|
18325
19227
|
function usePanoViewer() {
|
|
18326
|
-
const ref = (0,
|
|
18327
|
-
const handle = (0,
|
|
18328
|
-
return (0,
|
|
19228
|
+
const ref = (0, import_react63.useRef)(null);
|
|
19229
|
+
const handle = (0, import_react63.useMemo)(() => createPanoViewerHandle(ref), []);
|
|
19230
|
+
return (0, import_react63.useMemo)(() => ({ ref, ...handle }), [handle]);
|
|
18329
19231
|
}
|
|
18330
19232
|
|
|
18331
19233
|
// src/video/pano-video.tsx
|
|
18332
19234
|
var import_fiber31 = require("@react-three/fiber");
|
|
18333
|
-
var
|
|
19235
|
+
var import_react64 = require("react");
|
|
18334
19236
|
var import_three40 = require("three");
|
|
18335
|
-
var
|
|
19237
|
+
var import_jsx_runtime42 = require("react/jsx-runtime");
|
|
18336
19238
|
var EMPTY_TRACKS = [];
|
|
18337
19239
|
var EMPTY_RATES = DEFAULT_PANO_VIDEO_PLAYBACK_RATES;
|
|
18338
19240
|
function createEmptySnapshot() {
|
|
@@ -18417,10 +19319,10 @@ function applyEquirectangularLayout(texture, anisotropy) {
|
|
|
18417
19319
|
}
|
|
18418
19320
|
function usePosterTexture2(poster, onError) {
|
|
18419
19321
|
const gl = (0, import_fiber31.useThree)((state) => state.gl);
|
|
18420
|
-
const [texture, setTexture] = (0,
|
|
18421
|
-
const onErrorRef = (0,
|
|
19322
|
+
const [texture, setTexture] = (0, import_react64.useState)(null);
|
|
19323
|
+
const onErrorRef = (0, import_react64.useRef)(onError);
|
|
18422
19324
|
onErrorRef.current = onError;
|
|
18423
|
-
(0,
|
|
19325
|
+
(0, import_react64.useEffect)(() => {
|
|
18424
19326
|
let active = true;
|
|
18425
19327
|
setTexture(null);
|
|
18426
19328
|
if (!poster) {
|
|
@@ -18457,7 +19359,7 @@ function usePosterTexture2(poster, onError) {
|
|
|
18457
19359
|
active = false;
|
|
18458
19360
|
};
|
|
18459
19361
|
}, [gl, poster]);
|
|
18460
|
-
(0,
|
|
19362
|
+
(0, import_react64.useEffect)(
|
|
18461
19363
|
() => () => {
|
|
18462
19364
|
texture?.dispose();
|
|
18463
19365
|
},
|
|
@@ -18516,37 +19418,37 @@ function PanoVideo({
|
|
|
18516
19418
|
}) {
|
|
18517
19419
|
usePanoMediaActivationIntent(autoPlay);
|
|
18518
19420
|
const gl = (0, import_fiber31.useThree)((state) => state.gl);
|
|
18519
|
-
const host = (0,
|
|
18520
|
-
const variants = (0,
|
|
19421
|
+
const host = (0, import_react64.useContext)(PanoVideoHostContext);
|
|
19422
|
+
const variants = (0, import_react64.useMemo)(
|
|
18521
19423
|
() => resolvePanoVideoVariants({ poster, src, variants: variantsProp }),
|
|
18522
19424
|
[poster, src, variantsProp]
|
|
18523
19425
|
);
|
|
18524
19426
|
const tracks = tracksProp ?? EMPTY_TRACKS;
|
|
18525
19427
|
const captionsEnabled = captions !== false;
|
|
18526
|
-
const captionAppearance = (0,
|
|
19428
|
+
const captionAppearance = (0, import_react64.useMemo)(
|
|
18527
19429
|
() => resolvePanoVideoCaptionAppearance(
|
|
18528
19430
|
typeof captions === "object" ? captions : void 0
|
|
18529
19431
|
),
|
|
18530
19432
|
[captions]
|
|
18531
19433
|
);
|
|
18532
|
-
const [variantId, setVariantId] = (0,
|
|
19434
|
+
const [variantId, setVariantId] = (0, import_react64.useState)(
|
|
18533
19435
|
() => resolvePanoVideoVariantId(variants, defaultVariantId)
|
|
18534
19436
|
);
|
|
18535
|
-
const [trackId, setTrackId] = (0,
|
|
19437
|
+
const [trackId, setTrackId] = (0, import_react64.useState)(
|
|
18536
19438
|
() => captionsEnabled ? defaultPanoVideoTrackId(tracks) : null
|
|
18537
19439
|
);
|
|
18538
|
-
const [ready, setReady] = (0,
|
|
18539
|
-
const autoPlayRef = (0,
|
|
19440
|
+
const [ready, setReady] = (0, import_react64.useState)(false);
|
|
19441
|
+
const autoPlayRef = (0, import_react64.useRef)(autoPlay);
|
|
18540
19442
|
autoPlayRef.current = autoPlay;
|
|
18541
|
-
const blockedRef = (0,
|
|
18542
|
-
const captionAppearanceOverrideRef = (0,
|
|
19443
|
+
const blockedRef = (0, import_react64.useRef)(false);
|
|
19444
|
+
const captionAppearanceOverrideRef = (0, import_react64.useRef)(
|
|
18543
19445
|
{}
|
|
18544
19446
|
);
|
|
18545
|
-
const mediaCapabilitiesRef = (0,
|
|
19447
|
+
const mediaCapabilitiesRef = (0, import_react64.useRef)({
|
|
18546
19448
|
volumeAdjustable: true,
|
|
18547
19449
|
playbackRates: [...DEFAULT_PANO_VIDEO_PLAYBACK_RATES]
|
|
18548
19450
|
});
|
|
18549
|
-
const storeRef = (0,
|
|
19451
|
+
const storeRef = (0, import_react64.useRef)(null);
|
|
18550
19452
|
if (!storeRef.current) {
|
|
18551
19453
|
storeRef.current = {
|
|
18552
19454
|
snapshot: {
|
|
@@ -18556,7 +19458,7 @@ function PanoVideo({
|
|
|
18556
19458
|
listeners: /* @__PURE__ */ new Set()
|
|
18557
19459
|
};
|
|
18558
19460
|
}
|
|
18559
|
-
const actionsRef = (0,
|
|
19461
|
+
const actionsRef = (0, import_react64.useRef)({
|
|
18560
19462
|
play: async () => {
|
|
18561
19463
|
},
|
|
18562
19464
|
pause: () => {
|
|
@@ -18576,19 +19478,19 @@ function PanoVideo({
|
|
|
18576
19478
|
setCaptionAppearance: (_appearance) => {
|
|
18577
19479
|
}
|
|
18578
19480
|
});
|
|
18579
|
-
const onLoadRef = (0,
|
|
18580
|
-
const onErrorRef = (0,
|
|
18581
|
-
const onPlaybackStateChangeRef = (0,
|
|
18582
|
-
const onEndedRef = (0,
|
|
18583
|
-
const onVariantChangeRef = (0,
|
|
18584
|
-
const onTrackChangeRef = (0,
|
|
19481
|
+
const onLoadRef = (0, import_react64.useRef)(onLoad);
|
|
19482
|
+
const onErrorRef = (0, import_react64.useRef)(onError);
|
|
19483
|
+
const onPlaybackStateChangeRef = (0, import_react64.useRef)(onPlaybackStateChange);
|
|
19484
|
+
const onEndedRef = (0, import_react64.useRef)(onEnded);
|
|
19485
|
+
const onVariantChangeRef = (0, import_react64.useRef)(onVariantChange);
|
|
19486
|
+
const onTrackChangeRef = (0, import_react64.useRef)(onTrackChange);
|
|
18585
19487
|
onLoadRef.current = onLoad;
|
|
18586
19488
|
onErrorRef.current = onError;
|
|
18587
19489
|
onPlaybackStateChangeRef.current = onPlaybackStateChange;
|
|
18588
19490
|
onEndedRef.current = onEnded;
|
|
18589
19491
|
onVariantChangeRef.current = onVariantChange;
|
|
18590
19492
|
onTrackChangeRef.current = onTrackChange;
|
|
18591
|
-
const resource = (0,
|
|
19493
|
+
const resource = (0, import_react64.useMemo)(() => {
|
|
18592
19494
|
if (typeof document === "undefined") {
|
|
18593
19495
|
return null;
|
|
18594
19496
|
}
|
|
@@ -18603,7 +19505,7 @@ function PanoVideo({
|
|
|
18603
19505
|
texture.generateMipmaps = false;
|
|
18604
19506
|
return { video, texture };
|
|
18605
19507
|
}, []);
|
|
18606
|
-
(0,
|
|
19508
|
+
(0, import_react64.useEffect)(
|
|
18607
19509
|
() => () => {
|
|
18608
19510
|
if (!resource) {
|
|
18609
19511
|
return;
|
|
@@ -18618,13 +19520,13 @@ function PanoVideo({
|
|
|
18618
19520
|
},
|
|
18619
19521
|
[resource]
|
|
18620
19522
|
);
|
|
18621
|
-
(0,
|
|
19523
|
+
(0, import_react64.useEffect)(() => {
|
|
18622
19524
|
if (!resource) {
|
|
18623
19525
|
return;
|
|
18624
19526
|
}
|
|
18625
19527
|
resource.texture.anisotropy = gl.capabilities.getMaxAnisotropy();
|
|
18626
19528
|
}, [gl, resource]);
|
|
18627
|
-
(0,
|
|
19529
|
+
(0, import_react64.useLayoutEffect)(() => {
|
|
18628
19530
|
if (!resource) {
|
|
18629
19531
|
return;
|
|
18630
19532
|
}
|
|
@@ -18640,7 +19542,7 @@ function PanoVideo({
|
|
|
18640
19542
|
activeVariant?.poster ?? poster,
|
|
18641
19543
|
onError
|
|
18642
19544
|
);
|
|
18643
|
-
const emitSnapshot = (0,
|
|
19545
|
+
const emitSnapshot = (0, import_react64.useCallback)(
|
|
18644
19546
|
(patch) => {
|
|
18645
19547
|
const store = storeRef.current;
|
|
18646
19548
|
const video = resource?.video;
|
|
@@ -18692,7 +19594,7 @@ function PanoVideo({
|
|
|
18692
19594
|
captionAppearance
|
|
18693
19595
|
]
|
|
18694
19596
|
);
|
|
18695
|
-
const controller = (0,
|
|
19597
|
+
const controller = (0, import_react64.useMemo)(
|
|
18696
19598
|
() => ({
|
|
18697
19599
|
subscribe: (onStoreChange) => {
|
|
18698
19600
|
const store = storeRef.current;
|
|
@@ -18744,7 +19646,7 @@ function PanoVideo({
|
|
|
18744
19646
|
}),
|
|
18745
19647
|
[]
|
|
18746
19648
|
);
|
|
18747
|
-
(0,
|
|
19649
|
+
(0, import_react64.useLayoutEffect)(() => {
|
|
18748
19650
|
if (!host || variants.length === 0) {
|
|
18749
19651
|
return;
|
|
18750
19652
|
}
|
|
@@ -18757,7 +19659,7 @@ function PanoVideo({
|
|
|
18757
19659
|
notifyPanoVideoHost(host);
|
|
18758
19660
|
};
|
|
18759
19661
|
}, [captionsEnabled, controller, controls, host, variants.length]);
|
|
18760
|
-
(0,
|
|
19662
|
+
(0, import_react64.useLayoutEffect)(() => {
|
|
18761
19663
|
if (!resource) {
|
|
18762
19664
|
return;
|
|
18763
19665
|
}
|
|
@@ -18770,10 +19672,10 @@ function PanoVideo({
|
|
|
18770
19672
|
};
|
|
18771
19673
|
emitSnapshot();
|
|
18772
19674
|
}, [emitSnapshot, playbackRates, resource]);
|
|
18773
|
-
(0,
|
|
19675
|
+
(0, import_react64.useEffect)(() => {
|
|
18774
19676
|
emitSnapshot();
|
|
18775
19677
|
}, [emitSnapshot]);
|
|
18776
|
-
(0,
|
|
19678
|
+
(0, import_react64.useEffect)(() => {
|
|
18777
19679
|
if (!resource || !activeVariant || !mediaKey) {
|
|
18778
19680
|
return;
|
|
18779
19681
|
}
|
|
@@ -18830,7 +19732,7 @@ function PanoVideo({
|
|
|
18830
19732
|
video.removeEventListener("error", handleError);
|
|
18831
19733
|
};
|
|
18832
19734
|
}, [mediaKey, resource]);
|
|
18833
|
-
(0,
|
|
19735
|
+
(0, import_react64.useEffect)(() => {
|
|
18834
19736
|
if (!resource) {
|
|
18835
19737
|
return;
|
|
18836
19738
|
}
|
|
@@ -18922,7 +19824,7 @@ function PanoVideo({
|
|
|
18922
19824
|
}
|
|
18923
19825
|
};
|
|
18924
19826
|
}, [emitSnapshot, resource]);
|
|
18925
|
-
(0,
|
|
19827
|
+
(0, import_react64.useLayoutEffect)(() => {
|
|
18926
19828
|
if (!resource) {
|
|
18927
19829
|
return;
|
|
18928
19830
|
}
|
|
@@ -18935,7 +19837,7 @@ function PanoVideo({
|
|
|
18935
19837
|
applyInlineVideoPlayback(video, playsInline);
|
|
18936
19838
|
video.preload = preload;
|
|
18937
19839
|
}, [loop, muted, playsInline, preload, resource, volume]);
|
|
18938
|
-
(0,
|
|
19840
|
+
(0, import_react64.useEffect)(() => {
|
|
18939
19841
|
if (!resource) {
|
|
18940
19842
|
return;
|
|
18941
19843
|
}
|
|
@@ -18985,7 +19887,7 @@ function PanoVideo({
|
|
|
18985
19887
|
video.removeEventListener("ratechange", handleVolume);
|
|
18986
19888
|
};
|
|
18987
19889
|
}, [emitSnapshot, resource]);
|
|
18988
|
-
(0,
|
|
19890
|
+
(0, import_react64.useEffect)(() => {
|
|
18989
19891
|
if (!resource) {
|
|
18990
19892
|
return;
|
|
18991
19893
|
}
|
|
@@ -19020,7 +19922,7 @@ function PanoVideo({
|
|
|
19020
19922
|
video.textTracks.removeEventListener("change", applyModes);
|
|
19021
19923
|
};
|
|
19022
19924
|
}, [emitSnapshot, resource, trackId, tracks]);
|
|
19023
|
-
(0,
|
|
19925
|
+
(0, import_react64.useEffect)(() => {
|
|
19024
19926
|
if (!captionsEnabled) {
|
|
19025
19927
|
setTrackId(null);
|
|
19026
19928
|
return;
|
|
@@ -19031,15 +19933,15 @@ function PanoVideo({
|
|
|
19031
19933
|
if (variants.length === 0) {
|
|
19032
19934
|
return null;
|
|
19033
19935
|
}
|
|
19034
|
-
return /* @__PURE__ */ (0,
|
|
19035
|
-
activeTexture ? /* @__PURE__ */ (0,
|
|
19936
|
+
return /* @__PURE__ */ (0, import_jsx_runtime42.jsxs)(import_jsx_runtime42.Fragment, { children: [
|
|
19937
|
+
activeTexture ? /* @__PURE__ */ (0, import_jsx_runtime42.jsxs)(
|
|
19036
19938
|
"mesh",
|
|
19037
19939
|
{
|
|
19038
19940
|
rotation: [0, import_three40.MathUtils.degToRad(90 + yawOffset2), 0],
|
|
19039
19941
|
visible,
|
|
19040
19942
|
children: [
|
|
19041
|
-
/* @__PURE__ */ (0,
|
|
19042
|
-
/* @__PURE__ */ (0,
|
|
19943
|
+
/* @__PURE__ */ (0, import_jsx_runtime42.jsx)("sphereGeometry", { args: [DEFAULT_PANORAMA_RADIUS, 128, 64] }),
|
|
19944
|
+
/* @__PURE__ */ (0, import_jsx_runtime42.jsx)(
|
|
19043
19945
|
PanoBasicMaterial,
|
|
19044
19946
|
{
|
|
19045
19947
|
map: activeTexture,
|
|
@@ -19050,12 +19952,12 @@ function PanoVideo({
|
|
|
19050
19952
|
]
|
|
19051
19953
|
}
|
|
19052
19954
|
) : null,
|
|
19053
|
-
captionsEnabled ? /* @__PURE__ */ (0,
|
|
19955
|
+
captionsEnabled ? /* @__PURE__ */ (0, import_jsx_runtime42.jsx)(PanoVideoCaptions, { appearance: typeof captions === "object" ? captions : void 0 }) : null
|
|
19054
19956
|
] });
|
|
19055
19957
|
}
|
|
19056
19958
|
|
|
19057
19959
|
// src/map/pano-map.tsx
|
|
19058
|
-
var
|
|
19960
|
+
var import_react66 = require("react");
|
|
19059
19961
|
|
|
19060
19962
|
// src/map/geometry.ts
|
|
19061
19963
|
function sectorRotation(heading, yaw) {
|
|
@@ -19115,14 +20017,14 @@ function normalizeDegrees(value) {
|
|
|
19115
20017
|
}
|
|
19116
20018
|
|
|
19117
20019
|
// src/map/use-map-view.ts
|
|
19118
|
-
var
|
|
20020
|
+
var import_react65 = require("react");
|
|
19119
20021
|
var DEFAULT_VIEW2 = { yaw: 0, pitch: 0, fov: 75 };
|
|
19120
20022
|
function useMapView(controlled) {
|
|
19121
|
-
const eventBus = (0,
|
|
19122
|
-
const [view, setView] = (0,
|
|
19123
|
-
const controlledRef = (0,
|
|
20023
|
+
const eventBus = (0, import_react65.useContext)(PanoEventBusContext);
|
|
20024
|
+
const [view, setView] = (0, import_react65.useState)(controlled ?? DEFAULT_VIEW2);
|
|
20025
|
+
const controlledRef = (0, import_react65.useRef)(controlled);
|
|
19124
20026
|
controlledRef.current = controlled;
|
|
19125
|
-
(0,
|
|
20027
|
+
(0, import_react65.useEffect)(() => {
|
|
19126
20028
|
if (controlled !== void 0) {
|
|
19127
20029
|
setView(controlled);
|
|
19128
20030
|
return;
|
|
@@ -19137,7 +20039,7 @@ function useMapView(controlled) {
|
|
|
19137
20039
|
}
|
|
19138
20040
|
|
|
19139
20041
|
// src/map/pano-map.tsx
|
|
19140
|
-
var
|
|
20042
|
+
var import_jsx_runtime43 = require("react/jsx-runtime");
|
|
19141
20043
|
var DEFAULT_ICON_SIZE2 = 28;
|
|
19142
20044
|
var DEFAULT_SECTOR_COLOR = "#ffffff";
|
|
19143
20045
|
var DEFAULT_SECTOR_OPACITY = 0.55;
|
|
@@ -19176,8 +20078,8 @@ function SectorShape({
|
|
|
19176
20078
|
...gradient.stops.map((stop) => stop.opacity ?? 1),
|
|
19177
20079
|
Number.EPSILON
|
|
19178
20080
|
) : 1;
|
|
19179
|
-
return /* @__PURE__ */ (0,
|
|
19180
|
-
gradient ? /* @__PURE__ */ (0,
|
|
20081
|
+
return /* @__PURE__ */ (0, import_jsx_runtime43.jsxs)("g", { ref: transformRef, transform: `rotate(${rotation})`, style: { pointerEvents: "none" }, children: [
|
|
20082
|
+
gradient ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)("defs", { children: gradient.type === "radial" ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)("radialGradient", { id: gradientId, cx: "0", cy: "0", r: radius, gradientUnits: "userSpaceOnUse", children: gradient.stops.map((stop, index) => /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19181
20083
|
"stop",
|
|
19182
20084
|
{
|
|
19183
20085
|
offset: `${stop.offset * 100}%`,
|
|
@@ -19185,7 +20087,7 @@ function SectorShape({
|
|
|
19185
20087
|
stopOpacity: (stop.opacity ?? 1) / gradientStrength
|
|
19186
20088
|
},
|
|
19187
20089
|
`${stop.offset}:${index}`
|
|
19188
|
-
)) }) : /* @__PURE__ */ (0,
|
|
20090
|
+
)) }) : /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19189
20091
|
"linearGradient",
|
|
19190
20092
|
{
|
|
19191
20093
|
id: gradientId,
|
|
@@ -19194,7 +20096,7 @@ function SectorShape({
|
|
|
19194
20096
|
x2: "0",
|
|
19195
20097
|
y2: -radius,
|
|
19196
20098
|
gradientUnits: "userSpaceOnUse",
|
|
19197
|
-
children: gradient.stops.map((stop, index) => /* @__PURE__ */ (0,
|
|
20099
|
+
children: gradient.stops.map((stop, index) => /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19198
20100
|
"stop",
|
|
19199
20101
|
{
|
|
19200
20102
|
offset: `${stop.offset * 100}%`,
|
|
@@ -19205,7 +20107,7 @@ function SectorShape({
|
|
|
19205
20107
|
))
|
|
19206
20108
|
}
|
|
19207
20109
|
) }) : null,
|
|
19208
|
-
/* @__PURE__ */ (0,
|
|
20110
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19209
20111
|
"path",
|
|
19210
20112
|
{
|
|
19211
20113
|
d: path,
|
|
@@ -19225,7 +20127,7 @@ function SectorShape({
|
|
|
19225
20127
|
] });
|
|
19226
20128
|
}
|
|
19227
20129
|
function DefaultSpotIcon({ active, size }) {
|
|
19228
|
-
return /* @__PURE__ */ (0,
|
|
20130
|
+
return /* @__PURE__ */ (0, import_jsx_runtime43.jsxs)(
|
|
19229
20131
|
"svg",
|
|
19230
20132
|
{
|
|
19231
20133
|
width: size,
|
|
@@ -19234,7 +20136,7 @@ function DefaultSpotIcon({ active, size }) {
|
|
|
19234
20136
|
"aria-hidden": "true",
|
|
19235
20137
|
style: { display: "block" },
|
|
19236
20138
|
children: [
|
|
19237
|
-
/* @__PURE__ */ (0,
|
|
20139
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19238
20140
|
"rect",
|
|
19239
20141
|
{
|
|
19240
20142
|
x: "3",
|
|
@@ -19247,8 +20149,8 @@ function DefaultSpotIcon({ active, size }) {
|
|
|
19247
20149
|
strokeWidth: "2"
|
|
19248
20150
|
}
|
|
19249
20151
|
),
|
|
19250
|
-
/* @__PURE__ */ (0,
|
|
19251
|
-
/* @__PURE__ */ (0,
|
|
20152
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)("circle", { cx: "16", cy: "16", r: "5", fill: "none", stroke: "rgba(255,255,255,0.92)", strokeWidth: "2" }),
|
|
20153
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)("circle", { cx: "16", cy: "16", r: "2", fill: active ? "#ef4444" : "rgba(255,255,255,0.85)" })
|
|
19252
20154
|
]
|
|
19253
20155
|
}
|
|
19254
20156
|
);
|
|
@@ -19269,38 +20171,51 @@ function PanoMap({
|
|
|
19269
20171
|
showCollapseControl,
|
|
19270
20172
|
collapsed: controlledCollapsed,
|
|
19271
20173
|
onCollapsedChange,
|
|
19272
|
-
renderChrome
|
|
20174
|
+
renderChrome,
|
|
20175
|
+
initialScale
|
|
19273
20176
|
}) {
|
|
19274
|
-
const reactId = (0,
|
|
20177
|
+
const reactId = (0, import_react66.useId)().replace(/:/g, "");
|
|
19275
20178
|
const view = useMapView(controlledView);
|
|
19276
|
-
const rootRef = (0,
|
|
19277
|
-
const containerRef = (0,
|
|
19278
|
-
const sectorNodeRef = (0,
|
|
19279
|
-
const yawRef = (0,
|
|
19280
|
-
const [size, setSize] = (0,
|
|
19281
|
-
const [imageSize2, setImageSize] = (0,
|
|
19282
|
-
const [scale, setScale] = (0,
|
|
19283
|
-
const [pan, setPan] = (0,
|
|
19284
|
-
const [uncontrolledCollapsed, setUncontrolledCollapsed] = (0,
|
|
19285
|
-
const dragRef = (0,
|
|
20179
|
+
const rootRef = (0, import_react66.useRef)(null);
|
|
20180
|
+
const containerRef = (0, import_react66.useRef)(null);
|
|
20181
|
+
const sectorNodeRef = (0, import_react66.useRef)(null);
|
|
20182
|
+
const yawRef = (0, import_react66.useRef)(view.yaw);
|
|
20183
|
+
const [size, setSize] = (0, import_react66.useState)({ width: 0, height: 0 });
|
|
20184
|
+
const [imageSize2, setImageSize] = (0, import_react66.useState)({ width: 0, height: 0 });
|
|
20185
|
+
const [scale, setScale] = (0, import_react66.useState)(1);
|
|
20186
|
+
const [pan, setPan] = (0, import_react66.useState)({ x: 0, y: 0 });
|
|
20187
|
+
const [uncontrolledCollapsed, setUncontrolledCollapsed] = (0, import_react66.useState)(false);
|
|
20188
|
+
const dragRef = (0, import_react66.useRef)(null);
|
|
20189
|
+
const panAnimRef = (0, import_react66.useRef)(null);
|
|
20190
|
+
const panRef = (0, import_react66.useRef)(pan);
|
|
20191
|
+
const scaleRef = (0, import_react66.useRef)(scale);
|
|
20192
|
+
const initialViewKeyRef = (0, import_react66.useRef)(null);
|
|
19286
20193
|
const spots = map.spots;
|
|
19287
20194
|
const iconSize = map.iconSize ?? DEFAULT_ICON_SIZE2;
|
|
19288
20195
|
const interaction = map.interaction ?? "fixed";
|
|
19289
20196
|
const gestureZoom = interaction === "zoom";
|
|
20197
|
+
const dragMotion = resolveDragMotion(map.dragMotion);
|
|
19290
20198
|
const maxScale = Math.max(MIN_SCALE, map.maxScale ?? DEFAULT_MAX_SCALE);
|
|
20199
|
+
const resolvedInitialScale = Math.min(
|
|
20200
|
+
maxScale,
|
|
20201
|
+
Math.max(
|
|
20202
|
+
MIN_SCALE,
|
|
20203
|
+
Number.isFinite(initialScale) ? initialScale : MIN_SCALE
|
|
20204
|
+
)
|
|
20205
|
+
);
|
|
19291
20206
|
const zoomControls = gestureZoom && (showZoomControls ?? map.controls?.zoom === true);
|
|
19292
20207
|
const collapseControl = showCollapseControl ?? map.controls?.collapse === true;
|
|
19293
20208
|
const collapsed = controlledCollapsed ?? uncontrolledCollapsed;
|
|
19294
20209
|
const editing = mode === "edit";
|
|
19295
|
-
const fit = (0,
|
|
20210
|
+
const fit = (0, import_react66.useMemo)(
|
|
19296
20211
|
() => containRect(size.width, size.height, imageSize2.width, imageSize2.height),
|
|
19297
20212
|
[size, imageSize2]
|
|
19298
20213
|
);
|
|
19299
|
-
const viewport = (0,
|
|
20214
|
+
const viewport = (0, import_react66.useMemo)(
|
|
19300
20215
|
() => ({ fit, scale, panX: pan.x, panY: pan.y }),
|
|
19301
20216
|
[fit, scale, pan]
|
|
19302
20217
|
);
|
|
19303
|
-
(0,
|
|
20218
|
+
(0, import_react66.useLayoutEffect)(() => {
|
|
19304
20219
|
if (collapsed) return;
|
|
19305
20220
|
const node = containerRef.current;
|
|
19306
20221
|
if (!node) return;
|
|
@@ -19317,7 +20232,7 @@ function PanoMap({
|
|
|
19317
20232
|
observer.observe(node);
|
|
19318
20233
|
return () => observer.disconnect();
|
|
19319
20234
|
}, [collapsed]);
|
|
19320
|
-
(0,
|
|
20235
|
+
(0, import_react66.useEffect)(() => {
|
|
19321
20236
|
yawRef.current = view.yaw;
|
|
19322
20237
|
const node = sectorNodeRef.current;
|
|
19323
20238
|
if (!node) return;
|
|
@@ -19332,24 +20247,108 @@ function PanoMap({
|
|
|
19332
20247
|
onCollapsedChange?.(next);
|
|
19333
20248
|
if (controlledCollapsed === void 0) setUncontrolledCollapsed(next);
|
|
19334
20249
|
};
|
|
19335
|
-
|
|
19336
|
-
|
|
20250
|
+
panRef.current = pan;
|
|
20251
|
+
scaleRef.current = scale;
|
|
20252
|
+
const panBoundsFor = (0, import_react66.useCallback)(
|
|
20253
|
+
(nextScale) => {
|
|
19337
20254
|
const width = fit.width * nextScale;
|
|
19338
20255
|
const height = fit.height * nextScale;
|
|
19339
|
-
if (!(fit.width > 0) || !(fit.height > 0))
|
|
19340
|
-
|
|
19341
|
-
|
|
19342
|
-
const minY = Math.min(0, size.height - (fit.top + height));
|
|
19343
|
-
const maxY = Math.max(0, -fit.top);
|
|
20256
|
+
if (!(fit.width > 0) || !(fit.height > 0)) {
|
|
20257
|
+
return { minX: 0, maxX: 0, minY: 0, maxY: 0 };
|
|
20258
|
+
}
|
|
19344
20259
|
return {
|
|
19345
|
-
|
|
19346
|
-
|
|
20260
|
+
minX: Math.min(0, size.width - (fit.left + width)),
|
|
20261
|
+
maxX: Math.max(0, -fit.left),
|
|
20262
|
+
minY: Math.min(0, size.height - (fit.top + height)),
|
|
20263
|
+
maxY: Math.max(0, -fit.top)
|
|
19347
20264
|
};
|
|
19348
20265
|
},
|
|
19349
20266
|
[fit, size]
|
|
19350
20267
|
);
|
|
19351
|
-
(0,
|
|
20268
|
+
const clampPan = (0, import_react66.useCallback)(
|
|
20269
|
+
(nextScale, nextPan) => {
|
|
20270
|
+
const bounds = panBoundsFor(nextScale);
|
|
20271
|
+
return {
|
|
20272
|
+
x: Math.min(bounds.maxX, Math.max(bounds.minX, nextPan.x)),
|
|
20273
|
+
y: Math.min(bounds.maxY, Math.max(bounds.minY, nextPan.y))
|
|
20274
|
+
};
|
|
20275
|
+
},
|
|
20276
|
+
[panBoundsFor]
|
|
20277
|
+
);
|
|
20278
|
+
const cancelPanAnimation = (0, import_react66.useCallback)(() => {
|
|
20279
|
+
const anim = panAnimRef.current;
|
|
20280
|
+
if (anim?.raf != null) {
|
|
20281
|
+
cancelAnimationFrame(anim.raf);
|
|
20282
|
+
}
|
|
20283
|
+
panAnimRef.current = null;
|
|
20284
|
+
}, []);
|
|
20285
|
+
const startPanAnimation = (0, import_react66.useCallback)(
|
|
20286
|
+
(velocity) => {
|
|
20287
|
+
cancelPanAnimation();
|
|
20288
|
+
const current = panRef.current;
|
|
20289
|
+
const currentScale = scaleRef.current;
|
|
20290
|
+
const bounds = panBoundsFor(currentScale);
|
|
20291
|
+
const needsSpring = dragMotion.bounce && (current.x < bounds.minX || current.x > bounds.maxX || current.y < bounds.minY || current.y > bounds.maxY);
|
|
20292
|
+
const vx = dragMotion.inertia ? velocity.x : 0;
|
|
20293
|
+
const vy = dragMotion.inertia ? velocity.y : 0;
|
|
20294
|
+
if (!needsSpring && Math.abs(vx) < 1 && Math.abs(vy) < 1) {
|
|
20295
|
+
setPan(clampPan(currentScale, current));
|
|
20296
|
+
return;
|
|
20297
|
+
}
|
|
20298
|
+
if (!dragMotion.inertia && !dragMotion.bounce) {
|
|
20299
|
+
setPan(clampPan(currentScale, current));
|
|
20300
|
+
return;
|
|
20301
|
+
}
|
|
20302
|
+
const anim = {
|
|
20303
|
+
raf: null,
|
|
20304
|
+
lastTime: performance.now(),
|
|
20305
|
+
x: { position: current.x, velocity: vx },
|
|
20306
|
+
y: { position: current.y, velocity: vy }
|
|
20307
|
+
};
|
|
20308
|
+
panAnimRef.current = anim;
|
|
20309
|
+
const tick = (now) => {
|
|
20310
|
+
if (panAnimRef.current !== anim) return;
|
|
20311
|
+
const dt = Math.min(0.064, Math.max(0, (now - anim.lastTime) / 1e3));
|
|
20312
|
+
anim.lastTime = now;
|
|
20313
|
+
const liveBounds = panBoundsFor(scaleRef.current);
|
|
20314
|
+
const nextX = integrateAxis(anim.x, dt, {
|
|
20315
|
+
min: liveBounds.minX,
|
|
20316
|
+
max: liveBounds.maxX,
|
|
20317
|
+
inertia: dragMotion.inertia,
|
|
20318
|
+
bounce: dragMotion.bounce
|
|
20319
|
+
});
|
|
20320
|
+
const nextY = integrateAxis(anim.y, dt, {
|
|
20321
|
+
min: liveBounds.minY,
|
|
20322
|
+
max: liveBounds.maxY,
|
|
20323
|
+
inertia: dragMotion.inertia,
|
|
20324
|
+
bounce: dragMotion.bounce
|
|
20325
|
+
});
|
|
20326
|
+
anim.x = { position: nextX.position, velocity: nextX.velocity };
|
|
20327
|
+
anim.y = { position: nextY.position, velocity: nextY.velocity };
|
|
20328
|
+
setPan({ x: nextX.position, y: nextY.position });
|
|
20329
|
+
if (nextX.settled && nextY.settled) {
|
|
20330
|
+
setPan(
|
|
20331
|
+
clampPan(scaleRef.current, {
|
|
20332
|
+
x: nextX.position,
|
|
20333
|
+
y: nextY.position
|
|
20334
|
+
})
|
|
20335
|
+
);
|
|
20336
|
+
panAnimRef.current = null;
|
|
20337
|
+
return;
|
|
20338
|
+
}
|
|
20339
|
+
anim.raf = requestAnimationFrame(tick);
|
|
20340
|
+
};
|
|
20341
|
+
anim.raf = requestAnimationFrame(tick);
|
|
20342
|
+
},
|
|
20343
|
+
[cancelPanAnimation, clampPan, dragMotion.bounce, dragMotion.inertia, panBoundsFor]
|
|
20344
|
+
);
|
|
20345
|
+
(0, import_react66.useEffect)(() => () => cancelPanAnimation(), [cancelPanAnimation]);
|
|
20346
|
+
(0, import_react66.useEffect)(() => {
|
|
20347
|
+
if (collapsed) cancelPanAnimation();
|
|
20348
|
+
}, [cancelPanAnimation, collapsed]);
|
|
20349
|
+
(0, import_react66.useEffect)(() => {
|
|
19352
20350
|
if (!gestureZoom) {
|
|
20351
|
+
initialViewKeyRef.current = null;
|
|
19353
20352
|
setScale(1);
|
|
19354
20353
|
setPan({ x: 0, y: 0 });
|
|
19355
20354
|
return;
|
|
@@ -19362,9 +20361,37 @@ function PanoMap({
|
|
|
19362
20361
|
return next;
|
|
19363
20362
|
});
|
|
19364
20363
|
}, [clampPan, gestureZoom, maxScale]);
|
|
19365
|
-
|
|
20364
|
+
(0, import_react66.useEffect)(() => {
|
|
20365
|
+
if (!gestureZoom) return;
|
|
20366
|
+
if (!(fit.width > 0) || !(fit.height > 0)) return;
|
|
20367
|
+
if (!(size.width > 0) || !(size.height > 0)) return;
|
|
20368
|
+
const key = `${interaction}:${initialScale ?? MIN_SCALE}`;
|
|
20369
|
+
if (initialViewKeyRef.current === key) return;
|
|
20370
|
+
initialViewKeyRef.current = key;
|
|
20371
|
+
const pivot = { x: size.width / 2, y: size.height / 2 };
|
|
20372
|
+
const nextPan = {
|
|
20373
|
+
x: pivot.x - (pivot.x - fit.left) * resolvedInitialScale - fit.left,
|
|
20374
|
+
y: pivot.y - (pivot.y - fit.top) * resolvedInitialScale - fit.top
|
|
20375
|
+
};
|
|
20376
|
+
setScale(resolvedInitialScale);
|
|
20377
|
+
setPan(clampPan(resolvedInitialScale, nextPan));
|
|
20378
|
+
}, [
|
|
20379
|
+
clampPan,
|
|
20380
|
+
fit.height,
|
|
20381
|
+
fit.left,
|
|
20382
|
+
fit.top,
|
|
20383
|
+
fit.width,
|
|
20384
|
+
gestureZoom,
|
|
20385
|
+
initialScale,
|
|
20386
|
+
interaction,
|
|
20387
|
+
resolvedInitialScale,
|
|
20388
|
+
size.height,
|
|
20389
|
+
size.width
|
|
20390
|
+
]);
|
|
20391
|
+
const applyZoom = (0, import_react66.useCallback)(
|
|
19366
20392
|
(nextScale, origin) => {
|
|
19367
20393
|
if (!gestureZoom) return;
|
|
20394
|
+
cancelPanAnimation();
|
|
19368
20395
|
const clamped = Math.min(maxScale, Math.max(MIN_SCALE, nextScale));
|
|
19369
20396
|
const pivot = origin ?? { x: size.width / 2, y: size.height / 2 };
|
|
19370
20397
|
const ratio = clamped / scale;
|
|
@@ -19376,6 +20403,7 @@ function PanoMap({
|
|
|
19376
20403
|
setPan(clampPan(clamped, nextPan));
|
|
19377
20404
|
},
|
|
19378
20405
|
[
|
|
20406
|
+
cancelPanAnimation,
|
|
19379
20407
|
clampPan,
|
|
19380
20408
|
fit.left,
|
|
19381
20409
|
fit.top,
|
|
@@ -19388,7 +20416,7 @@ function PanoMap({
|
|
|
19388
20416
|
size.width
|
|
19389
20417
|
]
|
|
19390
20418
|
);
|
|
19391
|
-
(0,
|
|
20419
|
+
(0, import_react66.useEffect)(() => {
|
|
19392
20420
|
const root = rootRef.current;
|
|
19393
20421
|
if (!root) return;
|
|
19394
20422
|
const onWheel = (event) => {
|
|
@@ -19440,15 +20468,22 @@ function PanoMap({
|
|
|
19440
20468
|
return;
|
|
19441
20469
|
}
|
|
19442
20470
|
if (gestureZoom && scale > 1) {
|
|
20471
|
+
cancelPanAnimation();
|
|
20472
|
+
const now = performance.now();
|
|
19443
20473
|
dragRef.current = {
|
|
19444
20474
|
kind: "pan",
|
|
19445
20475
|
pointerId: event.pointerId,
|
|
19446
20476
|
originX: point.x,
|
|
19447
20477
|
originY: point.y,
|
|
19448
20478
|
panX: pan.x,
|
|
19449
|
-
panY: pan.y
|
|
20479
|
+
panY: pan.y,
|
|
20480
|
+
samplesX: [{ t: now, position: pan.x }],
|
|
20481
|
+
samplesY: [{ t: now, position: pan.y }]
|
|
19450
20482
|
};
|
|
19451
|
-
|
|
20483
|
+
try {
|
|
20484
|
+
event.currentTarget.setPointerCapture(event.pointerId);
|
|
20485
|
+
} catch {
|
|
20486
|
+
}
|
|
19452
20487
|
event.preventDefault();
|
|
19453
20488
|
event.stopPropagation();
|
|
19454
20489
|
}
|
|
@@ -19459,12 +20494,28 @@ function PanoMap({
|
|
|
19459
20494
|
const point = localPoint(event);
|
|
19460
20495
|
if (!point) return;
|
|
19461
20496
|
if (drag.kind === "pan") {
|
|
19462
|
-
|
|
19463
|
-
|
|
19464
|
-
|
|
19465
|
-
|
|
19466
|
-
|
|
19467
|
-
);
|
|
20497
|
+
const rawX = drag.panX + (point.x - drag.originX);
|
|
20498
|
+
const rawY = drag.panY + (point.y - drag.originY);
|
|
20499
|
+
const bounds = panBoundsFor(scale);
|
|
20500
|
+
const now = performance.now();
|
|
20501
|
+
drag.samplesX = pushSample(drag.samplesX, { t: now, position: rawX });
|
|
20502
|
+
drag.samplesY = pushSample(drag.samplesY, { t: now, position: rawY });
|
|
20503
|
+
setPan({
|
|
20504
|
+
x: constrainDragPosition(
|
|
20505
|
+
rawX,
|
|
20506
|
+
bounds.minX,
|
|
20507
|
+
bounds.maxX,
|
|
20508
|
+
size.width,
|
|
20509
|
+
dragMotion.bounce
|
|
20510
|
+
),
|
|
20511
|
+
y: constrainDragPosition(
|
|
20512
|
+
rawY,
|
|
20513
|
+
bounds.minY,
|
|
20514
|
+
bounds.maxY,
|
|
20515
|
+
size.height,
|
|
20516
|
+
dragMotion.bounce
|
|
20517
|
+
)
|
|
20518
|
+
});
|
|
19468
20519
|
event.preventDefault();
|
|
19469
20520
|
event.stopPropagation();
|
|
19470
20521
|
return;
|
|
@@ -19505,11 +20556,24 @@ function PanoMap({
|
|
|
19505
20556
|
event.stopPropagation();
|
|
19506
20557
|
};
|
|
19507
20558
|
const endDrag = (event) => {
|
|
19508
|
-
|
|
20559
|
+
const drag = dragRef.current;
|
|
20560
|
+
if (drag?.pointerId !== event.pointerId) return;
|
|
19509
20561
|
dragRef.current = null;
|
|
19510
|
-
|
|
19511
|
-
event.currentTarget.
|
|
20562
|
+
try {
|
|
20563
|
+
if (event.currentTarget.hasPointerCapture(event.pointerId)) {
|
|
20564
|
+
event.currentTarget.releasePointerCapture(event.pointerId);
|
|
20565
|
+
}
|
|
20566
|
+
} catch {
|
|
20567
|
+
}
|
|
20568
|
+
if (drag.kind !== "pan") return;
|
|
20569
|
+
if (event.type === "pointercancel") {
|
|
20570
|
+
setPan(clampPan(scale, panRef.current));
|
|
20571
|
+
return;
|
|
19512
20572
|
}
|
|
20573
|
+
startPanAnimation({
|
|
20574
|
+
x: velocityFromSamples(drag.samplesX),
|
|
20575
|
+
y: velocityFromSamples(drag.samplesY)
|
|
20576
|
+
});
|
|
19513
20577
|
};
|
|
19514
20578
|
const sectorAngle = (() => {
|
|
19515
20579
|
if (!map.sector) return 0;
|
|
@@ -19519,8 +20583,8 @@ function PanoMap({
|
|
|
19519
20583
|
})();
|
|
19520
20584
|
const activeSpot = spots.find((spot) => spot.sceneId === activeSceneId);
|
|
19521
20585
|
const selectedSpot = spots.find((spot) => spot.id === selectedSpotId);
|
|
19522
|
-
const controls = /* @__PURE__ */ (0,
|
|
19523
|
-
collapseControl ? /* @__PURE__ */ (0,
|
|
20586
|
+
const controls = /* @__PURE__ */ (0, import_jsx_runtime43.jsxs)("div", { className: "pano-map-controls", style: { pointerEvents: "auto" }, children: [
|
|
20587
|
+
collapseControl ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19524
20588
|
"button",
|
|
19525
20589
|
{
|
|
19526
20590
|
type: "button",
|
|
@@ -19536,8 +20600,8 @@ function PanoMap({
|
|
|
19536
20600
|
children: collapsed ? "\u25A3" : "\u25A2"
|
|
19537
20601
|
}
|
|
19538
20602
|
) : null,
|
|
19539
|
-
zoomControls && !collapsed ? /* @__PURE__ */ (0,
|
|
19540
|
-
/* @__PURE__ */ (0,
|
|
20603
|
+
zoomControls && !collapsed ? /* @__PURE__ */ (0, import_jsx_runtime43.jsxs)(import_jsx_runtime43.Fragment, { children: [
|
|
20604
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19541
20605
|
"button",
|
|
19542
20606
|
{
|
|
19543
20607
|
type: "button",
|
|
@@ -19552,7 +20616,7 @@ function PanoMap({
|
|
|
19552
20616
|
children: "+"
|
|
19553
20617
|
}
|
|
19554
20618
|
),
|
|
19555
|
-
/* @__PURE__ */ (0,
|
|
20619
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19556
20620
|
"button",
|
|
19557
20621
|
{
|
|
19558
20622
|
type: "button",
|
|
@@ -19575,7 +20639,7 @@ function PanoMap({
|
|
|
19575
20639
|
(previous) => previous.width === image.naturalWidth && previous.height === image.naturalHeight ? previous : { width: image.naturalWidth, height: image.naturalHeight }
|
|
19576
20640
|
);
|
|
19577
20641
|
};
|
|
19578
|
-
return /* @__PURE__ */ (0,
|
|
20642
|
+
return /* @__PURE__ */ (0, import_jsx_runtime43.jsxs)(
|
|
19579
20643
|
"div",
|
|
19580
20644
|
{
|
|
19581
20645
|
ref: rootRef,
|
|
@@ -19593,8 +20657,8 @@ function PanoMap({
|
|
|
19593
20657
|
"data-mode": mode,
|
|
19594
20658
|
"data-collapsed": collapsed ? "true" : void 0,
|
|
19595
20659
|
children: [
|
|
19596
|
-
renderChrome ? renderChrome(controls) : /* @__PURE__ */ (0,
|
|
19597
|
-
/* @__PURE__ */ (0,
|
|
20660
|
+
renderChrome ? renderChrome(controls) : /* @__PURE__ */ (0, import_jsx_runtime43.jsx)("div", { className: "pano-map-chrome", children: controls }),
|
|
20661
|
+
/* @__PURE__ */ (0, import_jsx_runtime43.jsxs)(
|
|
19598
20662
|
"div",
|
|
19599
20663
|
{
|
|
19600
20664
|
ref: containerRef,
|
|
@@ -19611,7 +20675,7 @@ function PanoMap({
|
|
|
19611
20675
|
onPointerUp: endDrag,
|
|
19612
20676
|
onPointerCancel: endDrag,
|
|
19613
20677
|
children: [
|
|
19614
|
-
fit.width > 0 && fit.height > 0 ? /* @__PURE__ */ (0,
|
|
20678
|
+
fit.width > 0 && fit.height > 0 ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19615
20679
|
"div",
|
|
19616
20680
|
{
|
|
19617
20681
|
className: "pano-map-image-layer",
|
|
@@ -19623,7 +20687,7 @@ function PanoMap({
|
|
|
19623
20687
|
height: fit.height * scale,
|
|
19624
20688
|
transformOrigin: "0 0"
|
|
19625
20689
|
},
|
|
19626
|
-
children: /* @__PURE__ */ (0,
|
|
20690
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19627
20691
|
"img",
|
|
19628
20692
|
{
|
|
19629
20693
|
src: map.image,
|
|
@@ -19645,7 +20709,7 @@ function PanoMap({
|
|
|
19645
20709
|
}
|
|
19646
20710
|
)
|
|
19647
20711
|
}
|
|
19648
|
-
) : /* @__PURE__ */ (0,
|
|
20712
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19649
20713
|
"img",
|
|
19650
20714
|
{
|
|
19651
20715
|
src: map.image,
|
|
@@ -19659,7 +20723,7 @@ function PanoMap({
|
|
|
19659
20723
|
}
|
|
19660
20724
|
}
|
|
19661
20725
|
),
|
|
19662
|
-
activeSpot && map.sector ? /* @__PURE__ */ (0,
|
|
20726
|
+
activeSpot && map.sector ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19663
20727
|
"svg",
|
|
19664
20728
|
{
|
|
19665
20729
|
className: "pano-map-sector-layer",
|
|
@@ -19671,11 +20735,11 @@ function PanoMap({
|
|
|
19671
20735
|
overflow: "visible",
|
|
19672
20736
|
pointerEvents: "none"
|
|
19673
20737
|
},
|
|
19674
|
-
children: /* @__PURE__ */ (0,
|
|
20738
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19675
20739
|
"g",
|
|
19676
20740
|
{
|
|
19677
20741
|
transform: `translate(${imagePointToContainer(activeSpot, viewport).x} ${imagePointToContainer(activeSpot, viewport).y})`,
|
|
19678
|
-
children: /* @__PURE__ */ (0,
|
|
20742
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19679
20743
|
SectorShape,
|
|
19680
20744
|
{
|
|
19681
20745
|
sector: map.sector,
|
|
@@ -19707,7 +20771,7 @@ function PanoMap({
|
|
|
19707
20771
|
const point = imagePointToContainer(spot, viewport);
|
|
19708
20772
|
const active = spot.sceneId === activeSceneId;
|
|
19709
20773
|
const selected = spot.id === selectedSpotId;
|
|
19710
|
-
return /* @__PURE__ */ (0,
|
|
20774
|
+
return /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19711
20775
|
"button",
|
|
19712
20776
|
{
|
|
19713
20777
|
type: "button",
|
|
@@ -19752,7 +20816,7 @@ function PanoMap({
|
|
|
19752
20816
|
if (editing) return;
|
|
19753
20817
|
onSelectScene?.(spot.sceneId, spot);
|
|
19754
20818
|
},
|
|
19755
|
-
children: spot.icon ? /* @__PURE__ */ (0,
|
|
20819
|
+
children: spot.icon ? /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(
|
|
19756
20820
|
"img",
|
|
19757
20821
|
{
|
|
19758
20822
|
src: spot.icon,
|
|
@@ -19760,7 +20824,7 @@ function PanoMap({
|
|
|
19760
20824
|
draggable: false,
|
|
19761
20825
|
style: { width: "100%", height: "100%", display: "block", pointerEvents: "none" }
|
|
19762
20826
|
}
|
|
19763
|
-
) : /* @__PURE__ */ (0,
|
|
20827
|
+
) : /* @__PURE__ */ (0, import_jsx_runtime43.jsx)(DefaultSpotIcon, { active, size: iconSize })
|
|
19764
20828
|
},
|
|
19765
20829
|
spot.id
|
|
19766
20830
|
);
|
|
@@ -19774,8 +20838,10 @@ function PanoMap({
|
|
|
19774
20838
|
}
|
|
19775
20839
|
|
|
19776
20840
|
// src/map/pano-map-overlay.tsx
|
|
19777
|
-
var
|
|
19778
|
-
var
|
|
20841
|
+
var import_react67 = require("react");
|
|
20842
|
+
var import_jsx_runtime44 = require("react/jsx-runtime");
|
|
20843
|
+
var DEFAULT_DIALOG_WIDTH = 720;
|
|
20844
|
+
var DEFAULT_DIALOG_HEIGHT = 520;
|
|
19779
20845
|
function dockedBox(corner, offsetX, offsetY, width, height) {
|
|
19780
20846
|
const horizontal = corner === "top-right" || corner === "bottom-right" ? { left: "auto", right: offsetX } : { left: offsetX, right: "auto" };
|
|
19781
20847
|
const vertical = corner === "bottom-left" || corner === "bottom-right" ? { top: "auto", bottom: offsetY } : { top: offsetY, bottom: "auto" };
|
|
@@ -19786,14 +20852,16 @@ function PanoMapDialogShell({
|
|
|
19786
20852
|
onOpenChange,
|
|
19787
20853
|
title,
|
|
19788
20854
|
closeLabel,
|
|
20855
|
+
dialogWidth,
|
|
20856
|
+
dialogHeight,
|
|
19789
20857
|
children
|
|
19790
20858
|
}) {
|
|
19791
20859
|
usePanoModal(open);
|
|
19792
20860
|
const { size } = usePanoOverlay();
|
|
19793
|
-
const titleId = (0,
|
|
19794
|
-
const panelRef = (0,
|
|
19795
|
-
const previouslyFocused = (0,
|
|
19796
|
-
(0,
|
|
20861
|
+
const titleId = (0, import_react67.useId)();
|
|
20862
|
+
const panelRef = (0, import_react67.useRef)(null);
|
|
20863
|
+
const previouslyFocused = (0, import_react67.useRef)(null);
|
|
20864
|
+
(0, import_react67.useEffect)(() => {
|
|
19797
20865
|
if (!open) return;
|
|
19798
20866
|
const active = panelRef.current?.ownerDocument.activeElement;
|
|
19799
20867
|
previouslyFocused.current = active instanceof HTMLElement ? active : null;
|
|
@@ -19815,12 +20883,14 @@ function PanoMapDialogShell({
|
|
|
19815
20883
|
};
|
|
19816
20884
|
}, [open, onOpenChange]);
|
|
19817
20885
|
if (!open) return null;
|
|
19818
|
-
const
|
|
19819
|
-
const
|
|
20886
|
+
const preferredWidth = Number.isFinite(dialogWidth) && dialogWidth > 0 ? dialogWidth : DEFAULT_DIALOG_WIDTH;
|
|
20887
|
+
const preferredHeight = Number.isFinite(dialogHeight) && dialogHeight > 0 ? dialogHeight : DEFAULT_DIALOG_HEIGHT;
|
|
20888
|
+
const width = Math.min(preferredWidth, Math.max(0, size.width - 32));
|
|
20889
|
+
const height = Math.min(preferredHeight, Math.max(0, size.height - 32));
|
|
19820
20890
|
const left = Math.max(0, (size.width - width) / 2);
|
|
19821
20891
|
const top = Math.max(0, (size.height - height) / 2);
|
|
19822
|
-
return /* @__PURE__ */ (0,
|
|
19823
|
-
/* @__PURE__ */ (0,
|
|
20892
|
+
return /* @__PURE__ */ (0, import_jsx_runtime44.jsxs)(import_jsx_runtime44.Fragment, { children: [
|
|
20893
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19824
20894
|
"div",
|
|
19825
20895
|
{
|
|
19826
20896
|
className: "pano-map-dialog-backdrop",
|
|
@@ -19833,7 +20903,7 @@ function PanoMapDialogShell({
|
|
|
19833
20903
|
onClick: () => onOpenChange(false)
|
|
19834
20904
|
}
|
|
19835
20905
|
),
|
|
19836
|
-
/* @__PURE__ */ (0,
|
|
20906
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsxs)(
|
|
19837
20907
|
"div",
|
|
19838
20908
|
{
|
|
19839
20909
|
ref: panelRef,
|
|
@@ -19856,9 +20926,9 @@ function PanoMapDialogShell({
|
|
|
19856
20926
|
zIndex: 1
|
|
19857
20927
|
},
|
|
19858
20928
|
children: [
|
|
19859
|
-
/* @__PURE__ */ (0,
|
|
19860
|
-
/* @__PURE__ */ (0,
|
|
19861
|
-
/* @__PURE__ */ (0,
|
|
20929
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsxs)("header", { className: "pano-map-dialog-header", style: { flexShrink: 0 }, children: [
|
|
20930
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)("h2", { id: titleId, className: "pano-map-dialog-title", children: title }),
|
|
20931
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19862
20932
|
"button",
|
|
19863
20933
|
{
|
|
19864
20934
|
type: "button",
|
|
@@ -19866,11 +20936,11 @@ function PanoMapDialogShell({
|
|
|
19866
20936
|
"data-pano-map-dialog-close": "",
|
|
19867
20937
|
"aria-label": closeLabel,
|
|
19868
20938
|
onClick: () => onOpenChange(false),
|
|
19869
|
-
children: /* @__PURE__ */ (0,
|
|
20939
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)("svg", { "aria-hidden": "true", width: "16", height: "16", viewBox: "0 0 16 16", fill: "none", stroke: "currentColor", strokeWidth: "2", strokeLinecap: "round", children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)("path", { d: "m4 4 8 8M12 4l-8 8" }) })
|
|
19870
20940
|
}
|
|
19871
20941
|
)
|
|
19872
20942
|
] }),
|
|
19873
|
-
/* @__PURE__ */ (0,
|
|
20943
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)("div", { className: "pano-map-dialog-body", style: { minHeight: 0, flex: 1 }, children })
|
|
19874
20944
|
]
|
|
19875
20945
|
}
|
|
19876
20946
|
)
|
|
@@ -19887,6 +20957,20 @@ function PanoMapOverlay({
|
|
|
19887
20957
|
onEditChange,
|
|
19888
20958
|
placementSceneId,
|
|
19889
20959
|
presentationOverride,
|
|
20960
|
+
presentation: presentationModeProp,
|
|
20961
|
+
corner: cornerProp,
|
|
20962
|
+
width: widthProp,
|
|
20963
|
+
height: heightProp,
|
|
20964
|
+
offsetX: offsetXProp,
|
|
20965
|
+
offsetY: offsetYProp,
|
|
20966
|
+
dialogWidth = DEFAULT_DIALOG_WIDTH,
|
|
20967
|
+
dialogHeight = DEFAULT_DIALOG_HEIGHT,
|
|
20968
|
+
interaction,
|
|
20969
|
+
maxScale,
|
|
20970
|
+
initialScale,
|
|
20971
|
+
showZoomControls,
|
|
20972
|
+
showCollapseControl,
|
|
20973
|
+
iconSize,
|
|
19890
20974
|
openLabel = "Map",
|
|
19891
20975
|
closeLabel = "Close",
|
|
19892
20976
|
title = "Map",
|
|
@@ -19895,9 +20979,9 @@ function PanoMapOverlay({
|
|
|
19895
20979
|
editorSurface = false
|
|
19896
20980
|
}) {
|
|
19897
20981
|
const { size } = usePanoOverlay();
|
|
19898
|
-
const [open, setOpen] = (0,
|
|
19899
|
-
const [collapsed, setCollapsed] = (0,
|
|
19900
|
-
const
|
|
20982
|
+
const [open, setOpen] = (0, import_react67.useState)(false);
|
|
20983
|
+
const [collapsed, setCollapsed] = (0, import_react67.useState)(false);
|
|
20984
|
+
const basePresentation = presentationOverride ?? map.presentation ?? {
|
|
19901
20985
|
mode: "docked",
|
|
19902
20986
|
corner: "bottom-left",
|
|
19903
20987
|
width: 220,
|
|
@@ -19905,13 +20989,25 @@ function PanoMapOverlay({
|
|
|
19905
20989
|
offsetX: 16,
|
|
19906
20990
|
offsetY: 16
|
|
19907
20991
|
};
|
|
19908
|
-
const
|
|
19909
|
-
const
|
|
19910
|
-
const
|
|
19911
|
-
const
|
|
19912
|
-
const
|
|
20992
|
+
const presentationMode = presentationModeProp ?? basePresentation.mode;
|
|
20993
|
+
const corner = cornerProp ?? basePresentation.corner ?? "bottom-left";
|
|
20994
|
+
const offsetX = offsetXProp ?? basePresentation.offsetX ?? 16;
|
|
20995
|
+
const offsetY = offsetYProp ?? basePresentation.offsetY ?? 16;
|
|
20996
|
+
const width = widthProp ?? basePresentation.width ?? (presentationMode === "dialog" ? 48 : 220);
|
|
20997
|
+
const height = heightProp ?? basePresentation.height ?? (presentationMode === "dialog" ? 48 : 160);
|
|
20998
|
+
const resolvedMap = (0, import_react67.useMemo)(() => {
|
|
20999
|
+
if (interaction === void 0 && maxScale === void 0 && iconSize === void 0) {
|
|
21000
|
+
return map;
|
|
21001
|
+
}
|
|
21002
|
+
return {
|
|
21003
|
+
...map,
|
|
21004
|
+
...interaction === void 0 ? {} : { interaction },
|
|
21005
|
+
...maxScale === void 0 ? {} : { maxScale },
|
|
21006
|
+
...iconSize === void 0 ? {} : { iconSize }
|
|
21007
|
+
};
|
|
21008
|
+
}, [iconSize, interaction, map, maxScale]);
|
|
19913
21009
|
const mapProps = {
|
|
19914
|
-
map,
|
|
21010
|
+
map: resolvedMap,
|
|
19915
21011
|
activeSceneId,
|
|
19916
21012
|
view,
|
|
19917
21013
|
mode,
|
|
@@ -19919,14 +21015,17 @@ function PanoMapOverlay({
|
|
|
19919
21015
|
onSelectedSpotIdChange,
|
|
19920
21016
|
onEditChange,
|
|
19921
21017
|
placementSceneId,
|
|
21018
|
+
initialScale,
|
|
21019
|
+
showZoomControls,
|
|
21020
|
+
showCollapseControl,
|
|
19922
21021
|
onSelectScene: (sceneId, spot) => {
|
|
19923
21022
|
onSelectScene?.(sceneId, spot);
|
|
19924
|
-
if (
|
|
21023
|
+
if (presentationMode === "dialog") setOpen(false);
|
|
19925
21024
|
}
|
|
19926
21025
|
};
|
|
19927
|
-
const editorBox = (0,
|
|
19928
|
-
const panelWidth2 = Math.min(420, Math.max(240, size.width * 0.45));
|
|
19929
|
-
const panelHeight2 = Math.min(320, Math.max(180, size.height * 0.45));
|
|
21026
|
+
const editorBox = (0, import_react67.useMemo)(() => {
|
|
21027
|
+
const panelWidth2 = widthProp !== void 0 && Number.isFinite(widthProp) && widthProp > 0 ? widthProp : Math.min(420, Math.max(240, size.width * 0.45));
|
|
21028
|
+
const panelHeight2 = heightProp !== void 0 && Number.isFinite(heightProp) && heightProp > 0 ? heightProp : Math.min(320, Math.max(180, size.height * 0.45));
|
|
19930
21029
|
return {
|
|
19931
21030
|
left: 16,
|
|
19932
21031
|
right: "auto",
|
|
@@ -19935,9 +21034,9 @@ function PanoMapOverlay({
|
|
|
19935
21034
|
width: panelWidth2,
|
|
19936
21035
|
height: panelHeight2
|
|
19937
21036
|
};
|
|
19938
|
-
}, [size.height, size.width]);
|
|
21037
|
+
}, [heightProp, size.height, size.width, widthProp]);
|
|
19939
21038
|
if (editorSurface) {
|
|
19940
|
-
return /* @__PURE__ */ (0,
|
|
21039
|
+
return /* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19941
21040
|
"div",
|
|
19942
21041
|
{
|
|
19943
21042
|
className: ["pano-map-overlay", "pano-map-overlay-editor", className].filter(Boolean).join(" "),
|
|
@@ -19948,14 +21047,14 @@ function PanoMapOverlay({
|
|
|
19948
21047
|
...style
|
|
19949
21048
|
},
|
|
19950
21049
|
"data-pano-map-overlay": "",
|
|
19951
|
-
children: /* @__PURE__ */ (0,
|
|
21050
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)(PanoMap, { ...mapProps, showCollapseControl: false })
|
|
19952
21051
|
}
|
|
19953
21052
|
);
|
|
19954
21053
|
}
|
|
19955
|
-
if (
|
|
21054
|
+
if (presentationMode === "dialog") {
|
|
19956
21055
|
const launcherBox = dockedBox(corner, offsetX, offsetY, width, height);
|
|
19957
|
-
return /* @__PURE__ */ (0,
|
|
19958
|
-
/* @__PURE__ */ (0,
|
|
21056
|
+
return /* @__PURE__ */ (0, import_jsx_runtime44.jsxs)("div", { className: ["pano-map-overlay", className].filter(Boolean).join(" "), "data-pano-map-overlay": "", children: [
|
|
21057
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19959
21058
|
"button",
|
|
19960
21059
|
{
|
|
19961
21060
|
type: "button",
|
|
@@ -19971,14 +21070,16 @@ function PanoMapOverlay({
|
|
|
19971
21070
|
children: openLabel
|
|
19972
21071
|
}
|
|
19973
21072
|
),
|
|
19974
|
-
/* @__PURE__ */ (0,
|
|
21073
|
+
/* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19975
21074
|
PanoMapDialogShell,
|
|
19976
21075
|
{
|
|
19977
21076
|
open,
|
|
19978
21077
|
onOpenChange: setOpen,
|
|
19979
21078
|
title,
|
|
19980
21079
|
closeLabel,
|
|
19981
|
-
|
|
21080
|
+
dialogWidth,
|
|
21081
|
+
dialogHeight,
|
|
21082
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)("div", { style: { height: "100%" }, children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)(PanoMap, { ...mapProps, showCollapseControl: false }) })
|
|
19982
21083
|
}
|
|
19983
21084
|
)
|
|
19984
21085
|
] });
|
|
@@ -19986,7 +21087,7 @@ function PanoMapOverlay({
|
|
|
19986
21087
|
const panelWidth = collapsed ? Math.max(44, Math.min(width, 56)) : width;
|
|
19987
21088
|
const panelHeight = collapsed ? Math.max(44, Math.min(height, 56)) : height;
|
|
19988
21089
|
const box = dockedBox(corner, offsetX, offsetY, panelWidth, panelHeight);
|
|
19989
|
-
return /* @__PURE__ */ (0,
|
|
21090
|
+
return /* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
19990
21091
|
"div",
|
|
19991
21092
|
{
|
|
19992
21093
|
className: ["pano-map-overlay", className].filter(Boolean).join(" "),
|
|
@@ -19998,7 +21099,7 @@ function PanoMapOverlay({
|
|
|
19998
21099
|
},
|
|
19999
21100
|
"data-pano-map-overlay": "",
|
|
20000
21101
|
"data-presentation": "docked",
|
|
20001
|
-
children: /* @__PURE__ */ (0,
|
|
21102
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime44.jsx)(
|
|
20002
21103
|
PanoMap,
|
|
20003
21104
|
{
|
|
20004
21105
|
...mapProps,
|
|
@@ -20017,6 +21118,7 @@ function PanoMapOverlay({
|
|
|
20017
21118
|
DEFAULT_HOTSPOT_TOOLTIP_APPEARANCE,
|
|
20018
21119
|
DEFAULT_HOTSPOT_TOOLTIP_OFFSET,
|
|
20019
21120
|
DEFAULT_PANO_CURSORS,
|
|
21121
|
+
DEFAULT_PANO_SCENE_MENU_APPEARANCE,
|
|
20020
21122
|
DEFAULT_PANO_VIDEO_CAPTION_APPEARANCE,
|
|
20021
21123
|
DEFAULT_PANO_VIDEO_CONTROLS_APPEARANCE,
|
|
20022
21124
|
DEFAULT_PANO_VIDEO_PLAYBACK_RATES,
|
|
@@ -20037,6 +21139,7 @@ function PanoMapOverlay({
|
|
|
20037
21139
|
PanoMap,
|
|
20038
21140
|
PanoMapOverlay,
|
|
20039
21141
|
PanoOverlayPortalProvider,
|
|
21142
|
+
PanoSceneMenu,
|
|
20040
21143
|
PanoVideo,
|
|
20041
21144
|
PanoVideoControls,
|
|
20042
21145
|
PanoViewer,
|