@almadar/ui 5.152.0 → 5.154.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{EntityBindingContext-CD9ZoXb4.d.cts → EntityBindingContext-BfZGeDfX.d.cts} +4 -2
- package/dist/{EntityBindingContext-CD9ZoXb4.d.ts → EntityBindingContext-BfZGeDfX.d.ts} +4 -2
- package/dist/NavStackContext-BoVV9nWb.d.cts +83 -0
- package/dist/NavStackContext-BoVV9nWb.d.ts +83 -0
- package/dist/avl/index.cjs +571 -76
- package/dist/avl/index.js +572 -77
- package/dist/{avl-schema-parser-Cx_4SVg9.d.ts → avl-schema-parser-CLIm28Wa.d.ts} +1 -1
- package/dist/{avl-schema-parser-CVzkNzg7.d.cts → avl-schema-parser-Do_LPV1o.d.cts} +1 -1
- package/dist/{cn-DJTUjk1M.d.ts → cn-CFurBb2q.d.ts} +1 -1
- package/dist/{cn-BnAJZcNb.d.cts → cn-TH-RHihd.d.cts} +1 -1
- package/dist/components/index.cjs +502 -52
- package/dist/components/index.d.cts +58 -9
- package/dist/components/index.d.ts +58 -9
- package/dist/components/index.js +501 -55
- package/dist/hooks/index.cjs +4 -0
- package/dist/hooks/index.d.cts +1 -0
- package/dist/hooks/index.d.ts +1 -0
- package/dist/hooks/index.js +1 -0
- package/dist/lib/drawable/three/index.cjs +212 -0
- package/dist/lib/drawable/three/index.d.cts +3 -3
- package/dist/lib/drawable/three/index.d.ts +3 -3
- package/dist/lib/drawable/three/index.js +212 -0
- package/dist/lib/index.d.cts +2 -2
- package/dist/lib/index.d.ts +2 -2
- package/dist/{paintDispatch-CxdLjHQq.d.ts → paintDispatch-B5n2DTB-.d.ts} +178 -2
- package/dist/{paintDispatch-BjZjUbcb.d.cts → paintDispatch-DgBctxIq.d.cts} +178 -2
- package/dist/providers/index.cjs +677 -59
- package/dist/providers/index.d.cts +2 -1
- package/dist/providers/index.d.ts +2 -1
- package/dist/providers/index.js +677 -62
- package/dist/runtime/index.cjs +570 -75
- package/dist/runtime/index.d.cts +12 -5
- package/dist/runtime/index.d.ts +12 -5
- package/dist/runtime/index.js +571 -76
- package/package.json +4 -4
package/dist/runtime/index.cjs
CHANGED
|
@@ -6245,27 +6245,61 @@ var init_InfiniteScrollSentinel = __esm({
|
|
|
6245
6245
|
InfiniteScrollSentinel.displayName = "InfiniteScrollSentinel";
|
|
6246
6246
|
}
|
|
6247
6247
|
});
|
|
6248
|
-
|
|
6249
|
-
|
|
6250
|
-
|
|
6251
|
-
|
|
6252
|
-
|
|
6253
|
-
|
|
6254
|
-
|
|
6255
|
-
|
|
6256
|
-
|
|
6257
|
-
|
|
6258
|
-
|
|
6259
|
-
|
|
6260
|
-
|
|
6261
|
-
|
|
6248
|
+
|
|
6249
|
+
// components/core/atoms/fx.ts
|
|
6250
|
+
function resolveFxView(item, presets) {
|
|
6251
|
+
const row = presets?.find((p) => p.type === item.type);
|
|
6252
|
+
if (!row) return item;
|
|
6253
|
+
return {
|
|
6254
|
+
...item,
|
|
6255
|
+
space: item.space ?? row.space,
|
|
6256
|
+
effect: item.effect ?? row.effect,
|
|
6257
|
+
color: item.color ?? row.color,
|
|
6258
|
+
size: item.size ?? row.size,
|
|
6259
|
+
vx: item.vx ?? row.vx,
|
|
6260
|
+
vy: item.vy ?? row.vy,
|
|
6261
|
+
vz: item.vz ?? row.vz,
|
|
6262
|
+
particleCount: item.particleCount ?? row.particleCount,
|
|
6263
|
+
shape: row.shape,
|
|
6264
|
+
count: row.count,
|
|
6265
|
+
glow: row.glow,
|
|
6266
|
+
gravity: row.gravity,
|
|
6267
|
+
color2: row.color2
|
|
6268
|
+
};
|
|
6262
6269
|
}
|
|
6263
|
-
|
|
6264
|
-
|
|
6265
|
-
|
|
6266
|
-
|
|
6267
|
-
|
|
6268
|
-
|
|
6270
|
+
function fxLifecycle(item, epochNowMs, tickMs) {
|
|
6271
|
+
const maxTtl = Math.max(item.maxTtl ?? item.ttl, item.ttl, 1);
|
|
6272
|
+
const lifeMs = maxTtl * tickMs;
|
|
6273
|
+
const ageMs = item.bornAt !== void 0 && epochNowMs > 0 ? Math.max(0, epochNowMs - item.bornAt) : (1 - item.ttl / maxTtl) * lifeMs;
|
|
6274
|
+
const progress = Math.min(1, Math.max(0, ageMs / lifeMs));
|
|
6275
|
+
return { lifeMs, ageMs, progress, fade: 1 - progress };
|
|
6276
|
+
}
|
|
6277
|
+
function fxHash01(seed, salt) {
|
|
6278
|
+
let h = 2166136261 ^ salt;
|
|
6279
|
+
for (let i = 0; i < seed.length; i++) {
|
|
6280
|
+
h ^= seed.charCodeAt(i);
|
|
6281
|
+
h = Math.imul(h, 16777619);
|
|
6282
|
+
}
|
|
6283
|
+
h ^= h >>> 13;
|
|
6284
|
+
h = Math.imul(h, 1274126177);
|
|
6285
|
+
h ^= h >>> 16;
|
|
6286
|
+
return (h >>> 0) / 4294967296;
|
|
6287
|
+
}
|
|
6288
|
+
function createConfettiParticles(count, seed) {
|
|
6289
|
+
return Array.from({ length: count }, (_, i) => ({
|
|
6290
|
+
id: i,
|
|
6291
|
+
color: CONFETTI_COLORS[Math.floor(fxHash01(seed, i * 7 + 1) * CONFETTI_COLORS.length)],
|
|
6292
|
+
left: 30 + fxHash01(seed, i * 7 + 2) * 40,
|
|
6293
|
+
delay: fxHash01(seed, i * 7 + 3) * 300,
|
|
6294
|
+
angle: fxHash01(seed, i * 7 + 4) * 360,
|
|
6295
|
+
distance: 40 + fxHash01(seed, i * 7 + 5) * 80,
|
|
6296
|
+
rotation: fxHash01(seed, i * 7 + 6) * 720 - 360,
|
|
6297
|
+
size: 4 + fxHash01(seed, i * 7 + 7) * 6
|
|
6298
|
+
}));
|
|
6299
|
+
}
|
|
6300
|
+
var CONFETTI_COLORS, CONFETTI_BURST_KEYFRAMES;
|
|
6301
|
+
var init_fx = __esm({
|
|
6302
|
+
"components/core/atoms/fx.ts"() {
|
|
6269
6303
|
CONFETTI_COLORS = [
|
|
6270
6304
|
"var(--color-primary)",
|
|
6271
6305
|
"var(--color-success)",
|
|
@@ -6274,7 +6308,30 @@ var init_ConfettiEffect = __esm({
|
|
|
6274
6308
|
"gold",
|
|
6275
6309
|
"dodgerblue"
|
|
6276
6310
|
];
|
|
6277
|
-
|
|
6311
|
+
CONFETTI_BURST_KEYFRAMES = `
|
|
6312
|
+
@keyframes confetti-burst {
|
|
6313
|
+
0% {
|
|
6314
|
+
opacity: 1;
|
|
6315
|
+
transform: translate(0, 0) rotate(0deg) scale(1);
|
|
6316
|
+
}
|
|
6317
|
+
70% {
|
|
6318
|
+
opacity: 1;
|
|
6319
|
+
}
|
|
6320
|
+
100% {
|
|
6321
|
+
opacity: 0;
|
|
6322
|
+
transform: translate(var(--confetti-tx), var(--confetti-ty)) rotate(var(--confetti-rotate)) scale(0.5);
|
|
6323
|
+
}
|
|
6324
|
+
}
|
|
6325
|
+
`;
|
|
6326
|
+
}
|
|
6327
|
+
});
|
|
6328
|
+
var ConfettiEffect;
|
|
6329
|
+
var init_ConfettiEffect = __esm({
|
|
6330
|
+
"components/core/atoms/ConfettiEffect.tsx"() {
|
|
6331
|
+
"use client";
|
|
6332
|
+
init_cn();
|
|
6333
|
+
init_Box();
|
|
6334
|
+
init_fx();
|
|
6278
6335
|
ConfettiEffect = ({
|
|
6279
6336
|
trigger,
|
|
6280
6337
|
duration = 2e3,
|
|
@@ -6283,11 +6340,13 @@ var init_ConfettiEffect = __esm({
|
|
|
6283
6340
|
}) => {
|
|
6284
6341
|
const [particles, setParticles] = React85.useState([]);
|
|
6285
6342
|
const previousTriggerRef = React85.useRef(false);
|
|
6343
|
+
const burstRef = React85.useRef(0);
|
|
6286
6344
|
React85.useEffect(() => {
|
|
6287
6345
|
const wasFalse = !previousTriggerRef.current;
|
|
6288
6346
|
previousTriggerRef.current = trigger;
|
|
6289
6347
|
if (trigger && wasFalse) {
|
|
6290
|
-
|
|
6348
|
+
burstRef.current += 1;
|
|
6349
|
+
const newParticles = createConfettiParticles(particleCount, `confetti-${burstRef.current}`);
|
|
6291
6350
|
setParticles(newParticles);
|
|
6292
6351
|
const timer = window.setTimeout(() => {
|
|
6293
6352
|
setParticles([]);
|
|
@@ -6335,21 +6394,7 @@ var init_ConfettiEffect = __esm({
|
|
|
6335
6394
|
p.id
|
|
6336
6395
|
);
|
|
6337
6396
|
}),
|
|
6338
|
-
/* @__PURE__ */ jsxRuntime.jsx("style", { children:
|
|
6339
|
-
@keyframes confetti-burst {
|
|
6340
|
-
0% {
|
|
6341
|
-
opacity: 1;
|
|
6342
|
-
transform: translate(0, 0) rotate(0deg) scale(1);
|
|
6343
|
-
}
|
|
6344
|
-
70% {
|
|
6345
|
-
opacity: 1;
|
|
6346
|
-
}
|
|
6347
|
-
100% {
|
|
6348
|
-
opacity: 0;
|
|
6349
|
-
transform: translate(var(--confetti-tx), var(--confetti-ty)) rotate(var(--confetti-rotate)) scale(0.5);
|
|
6350
|
-
}
|
|
6351
|
-
}
|
|
6352
|
-
` })
|
|
6397
|
+
/* @__PURE__ */ jsxRuntime.jsx("style", { children: CONFETTI_BURST_KEYFRAMES })
|
|
6353
6398
|
]
|
|
6354
6399
|
}
|
|
6355
6400
|
);
|
|
@@ -9798,7 +9843,7 @@ var init_DrawShape = __esm({
|
|
|
9798
9843
|
const cx = p.x + (node.offsetX ?? 0) * tw;
|
|
9799
9844
|
const cy = p.y + (node.offsetY ?? 0) * tw;
|
|
9800
9845
|
const rx = (node.radiusX ?? 0) * tw;
|
|
9801
|
-
const ry = (node.radiusY ??
|
|
9846
|
+
const ry = (node.radiusY ?? node.radiusX ?? 0) * tw;
|
|
9802
9847
|
if (pxFill) painter.fillEllipse(cx, cy, rx, ry, pxFill);
|
|
9803
9848
|
if (patFill) painter.fillEllipse(cx, cy, rx, ry, patFill);
|
|
9804
9849
|
if (pxStroke) painter.strokeEllipse(cx, cy, rx, ry, pxStroke, strokePx);
|
|
@@ -9988,6 +10033,172 @@ var init_DrawTextLayer = __esm({
|
|
|
9988
10033
|
};
|
|
9989
10034
|
}
|
|
9990
10035
|
});
|
|
10036
|
+
|
|
10037
|
+
// components/game/molecules/DrawFxLayer.tsx
|
|
10038
|
+
function fxPosition(view, dim, ageSec) {
|
|
10039
|
+
const g = view.gravity ?? 0;
|
|
10040
|
+
const fall = 0.5 * g * ageSec * ageSec;
|
|
10041
|
+
{
|
|
10042
|
+
const base2 = view.position ?? { x: view.x, y: view.z ?? view.y ?? 0 };
|
|
10043
|
+
if (!Number.isFinite(base2.x) || !Number.isFinite(base2.y)) return void 0;
|
|
10044
|
+
return {
|
|
10045
|
+
x: base2.x + (view.vx ?? 0) * ageSec,
|
|
10046
|
+
y: base2.y + (view.vz ?? 0) * ageSec + fall
|
|
10047
|
+
};
|
|
10048
|
+
}
|
|
10049
|
+
}
|
|
10050
|
+
function sparkShape(view, pos, i, fade, progress) {
|
|
10051
|
+
const size = view.size ?? 0.5;
|
|
10052
|
+
const angle = fxHash01(view.id, i * 3) * Math.PI * 2;
|
|
10053
|
+
const dist = size * (0.4 + 0.6 * fxHash01(view.id, i * 3 + 1)) * easeOut2(progress);
|
|
10054
|
+
const r = size * (0.06 + 0.06 * fxHash01(view.id, i * 3 + 2));
|
|
10055
|
+
const color = view.color ?? DEFAULT_SPARK_COLOR;
|
|
10056
|
+
return {
|
|
10057
|
+
type: "draw-shape",
|
|
10058
|
+
shape: "ellipse",
|
|
10059
|
+
position: { ...pos, x: pos.x + Math.cos(angle) * dist, y: pos.y + Math.sin(angle) * dist },
|
|
10060
|
+
anchor: "center",
|
|
10061
|
+
radiusX: r,
|
|
10062
|
+
fill: color,
|
|
10063
|
+
blendMode: "lighter",
|
|
10064
|
+
opacity: fade,
|
|
10065
|
+
...view.glow ? { shadow: { color, blur: view.glow } } : {}
|
|
10066
|
+
};
|
|
10067
|
+
}
|
|
10068
|
+
function proceduralShapes(view, pos, fade, progress) {
|
|
10069
|
+
const size = view.size ?? 0.5;
|
|
10070
|
+
const color = view.color ?? DEFAULT_SPARK_COLOR;
|
|
10071
|
+
switch (view.shape ?? "spark") {
|
|
10072
|
+
case "ring": {
|
|
10073
|
+
return [
|
|
10074
|
+
{
|
|
10075
|
+
type: "draw-shape",
|
|
10076
|
+
shape: "ellipse",
|
|
10077
|
+
position: pos,
|
|
10078
|
+
anchor: "center",
|
|
10079
|
+
radiusX: size * easeOut2(progress),
|
|
10080
|
+
stroke: view.color2 ?? color,
|
|
10081
|
+
strokeWidth: 2,
|
|
10082
|
+
blendMode: "lighter",
|
|
10083
|
+
opacity: fade,
|
|
10084
|
+
...view.glow ? { shadow: { color, blur: view.glow } } : {}
|
|
10085
|
+
}
|
|
10086
|
+
];
|
|
10087
|
+
}
|
|
10088
|
+
case "puff": {
|
|
10089
|
+
const count = view.count ?? 3;
|
|
10090
|
+
return Array.from({ length: count }, (_, i) => {
|
|
10091
|
+
const angle = fxHash01(view.id, i * 5) * Math.PI * 2;
|
|
10092
|
+
const drift = size * 0.3 * fxHash01(view.id, i * 5 + 1) * easeOut2(progress);
|
|
10093
|
+
return {
|
|
10094
|
+
type: "draw-shape",
|
|
10095
|
+
shape: "ellipse",
|
|
10096
|
+
position: { ...pos, x: pos.x + Math.cos(angle) * drift, y: pos.y + Math.sin(angle) * drift },
|
|
10097
|
+
anchor: "center",
|
|
10098
|
+
radiusX: size * (0.15 + 0.35 * progress) * (0.7 + 0.6 * fxHash01(view.id, i * 5 + 2)),
|
|
10099
|
+
fill: i === 0 && view.color2 ? view.color2 : color,
|
|
10100
|
+
opacity: fade * 0.6,
|
|
10101
|
+
...view.glow ? { shadow: { color, blur: view.glow } } : {}
|
|
10102
|
+
};
|
|
10103
|
+
});
|
|
10104
|
+
}
|
|
10105
|
+
case "streak": {
|
|
10106
|
+
const count = view.count ?? 5;
|
|
10107
|
+
return Array.from({ length: count }, (_, i) => {
|
|
10108
|
+
const angle = fxHash01(view.id, i * 3) * Math.PI * 2;
|
|
10109
|
+
const inner = size * (0.2 + 0.8 * easeOut2(progress)) * (0.6 + 0.4 * fxHash01(view.id, i * 3 + 1));
|
|
10110
|
+
const len = size * 0.35;
|
|
10111
|
+
return {
|
|
10112
|
+
type: "draw-shape",
|
|
10113
|
+
shape: "ellipse",
|
|
10114
|
+
position: pos,
|
|
10115
|
+
anchor: "center",
|
|
10116
|
+
offsetX: inner + len / 2,
|
|
10117
|
+
offsetY: 0,
|
|
10118
|
+
radiusX: len / 2,
|
|
10119
|
+
radiusY: size * 0.04,
|
|
10120
|
+
rotate: angle,
|
|
10121
|
+
fill: color,
|
|
10122
|
+
blendMode: "lighter",
|
|
10123
|
+
opacity: fade,
|
|
10124
|
+
...view.glow ? { shadow: { color, blur: view.glow } } : {}
|
|
10125
|
+
};
|
|
10126
|
+
});
|
|
10127
|
+
}
|
|
10128
|
+
default: {
|
|
10129
|
+
const count = view.count ?? 6;
|
|
10130
|
+
return Array.from({ length: count }, (_, i) => sparkShape(view, pos, i, fade, progress));
|
|
10131
|
+
}
|
|
10132
|
+
}
|
|
10133
|
+
}
|
|
10134
|
+
function expandFxItem(view, node, epochNowMs, dim) {
|
|
10135
|
+
if (view.space === "screen") return [];
|
|
10136
|
+
const tickMs = node.tickMs ?? DEFAULT_TICK_MS;
|
|
10137
|
+
const { ageMs, progress, fade } = fxLifecycle(view, epochNowMs, tickMs);
|
|
10138
|
+
if (progress >= 1) return [];
|
|
10139
|
+
const pos = fxPosition(view, dim, ageMs / 1e3);
|
|
10140
|
+
if (!pos) return [];
|
|
10141
|
+
const out = [];
|
|
10142
|
+
const artItems = node.art?.[view.type]?.["idle"];
|
|
10143
|
+
const sprite = node.sprites?.[view.type];
|
|
10144
|
+
if (Array.isArray(artItems)) {
|
|
10145
|
+
out.push({
|
|
10146
|
+
type: "draw-group",
|
|
10147
|
+
position: pos,
|
|
10148
|
+
opacity: fade,
|
|
10149
|
+
...view.size !== void 0 ? { scale: view.size } : {},
|
|
10150
|
+
items: artItems
|
|
10151
|
+
});
|
|
10152
|
+
} else if (sprite?.url) {
|
|
10153
|
+
const spriteSize = view.size ?? 0.6;
|
|
10154
|
+
out.push({
|
|
10155
|
+
type: "draw-sprite",
|
|
10156
|
+
position: pos,
|
|
10157
|
+
asset: sprite,
|
|
10158
|
+
anchor: "center",
|
|
10159
|
+
width: spriteSize,
|
|
10160
|
+
height: spriteSize,
|
|
10161
|
+
opacity: fade
|
|
10162
|
+
});
|
|
10163
|
+
} else {
|
|
10164
|
+
out.push(...proceduralShapes(view, pos, fade, progress));
|
|
10165
|
+
}
|
|
10166
|
+
if (view.message) {
|
|
10167
|
+
const text = {
|
|
10168
|
+
type: "draw-text",
|
|
10169
|
+
text: view.message,
|
|
10170
|
+
position: pos,
|
|
10171
|
+
offsetY: -(0.15 + 0.55 * progress),
|
|
10172
|
+
color: view.color ?? node.textColor ?? DEFAULT_TEXT_COLOR,
|
|
10173
|
+
opacity: fade
|
|
10174
|
+
};
|
|
10175
|
+
out.push(text);
|
|
10176
|
+
}
|
|
10177
|
+
return out;
|
|
10178
|
+
}
|
|
10179
|
+
function expandFxLayer(node, epochNowMs, dim) {
|
|
10180
|
+
if (!Array.isArray(node.items)) return [];
|
|
10181
|
+
const out = [];
|
|
10182
|
+
for (const item of node.items) {
|
|
10183
|
+
if (!item || typeof item.id !== "string") continue;
|
|
10184
|
+
out.push(...expandFxItem(resolveFxView(item, node.presets), node, epochNowMs, dim));
|
|
10185
|
+
}
|
|
10186
|
+
return out;
|
|
10187
|
+
}
|
|
10188
|
+
function DrawFxLayer(_props) {
|
|
10189
|
+
return null;
|
|
10190
|
+
}
|
|
10191
|
+
var DEFAULT_TICK_MS, DEFAULT_TEXT_COLOR, DEFAULT_SPARK_COLOR, easeOut2;
|
|
10192
|
+
var init_DrawFxLayer = __esm({
|
|
10193
|
+
"components/game/molecules/DrawFxLayer.tsx"() {
|
|
10194
|
+
"use client";
|
|
10195
|
+
init_fx();
|
|
10196
|
+
DEFAULT_TICK_MS = 500;
|
|
10197
|
+
DEFAULT_TEXT_COLOR = "#ffe066";
|
|
10198
|
+
DEFAULT_SPARK_COLOR = "#ffffff";
|
|
10199
|
+
easeOut2 = (t) => 1 - (1 - t) * (1 - t);
|
|
10200
|
+
}
|
|
10201
|
+
});
|
|
9991
10202
|
function paintDrawable(painter, node, dctx) {
|
|
9992
10203
|
switch (node.type) {
|
|
9993
10204
|
case "draw-sprite":
|
|
@@ -10035,6 +10246,11 @@ function paintDrawable(painter, node, dctx) {
|
|
|
10035
10246
|
case "draw-text-layer":
|
|
10036
10247
|
paintTextLayer(painter, node, dctx);
|
|
10037
10248
|
break;
|
|
10249
|
+
case "draw-fx-layer": {
|
|
10250
|
+
const epochNow = dctx.time > 0 && typeof performance !== "undefined" ? performance.timeOrigin + dctx.time : 0;
|
|
10251
|
+
for (const child of expandFxLayer(node, epochNow, "2d")) paintDrawable(painter, child, dctx);
|
|
10252
|
+
break;
|
|
10253
|
+
}
|
|
10038
10254
|
}
|
|
10039
10255
|
}
|
|
10040
10256
|
var paint2dLog, warnedUnsupported2d, warnUnsupported2d;
|
|
@@ -10049,6 +10265,7 @@ var init_paintDispatch = __esm({
|
|
|
10049
10265
|
init_DrawSpriteLayer();
|
|
10050
10266
|
init_DrawShapeLayer();
|
|
10051
10267
|
init_DrawTextLayer();
|
|
10268
|
+
init_DrawFxLayer();
|
|
10052
10269
|
paint2dLog = logger.createLogger("almadar:ui:drawable-2d");
|
|
10053
10270
|
warnedUnsupported2d = /* @__PURE__ */ new Set();
|
|
10054
10271
|
warnUnsupported2d = (kind) => {
|
|
@@ -10297,6 +10514,7 @@ function Canvas2D({
|
|
|
10297
10514
|
return isAnimatedGroup(node) || Array.isArray(node.items) && node.items.some(drawableIsAnimated);
|
|
10298
10515
|
if (node.type === "draw-shape-layer") return Array.isArray(node.items) && node.items.some(isAnimatedShape);
|
|
10299
10516
|
if (node.type === "draw-sprite-layer") return Array.isArray(node.items) && node.items.some(isAnimatedSprite);
|
|
10517
|
+
if (node.type === "draw-fx-layer") return Array.isArray(node.items) && node.items.length > 0;
|
|
10300
10518
|
return false;
|
|
10301
10519
|
};
|
|
10302
10520
|
const animRafRef = React85.useRef(0);
|
|
@@ -20816,17 +21034,27 @@ var init_Breadcrumb = __esm({
|
|
|
20816
21034
|
init_useEventBus();
|
|
20817
21035
|
Breadcrumb = ({
|
|
20818
21036
|
items,
|
|
21037
|
+
fromNavStack = false,
|
|
21038
|
+
itemEvent,
|
|
20819
21039
|
separator = "chevron-right",
|
|
20820
21040
|
maxItems,
|
|
20821
21041
|
className
|
|
20822
21042
|
}) => {
|
|
20823
21043
|
const eventBus = useEventBus();
|
|
20824
21044
|
const { t } = hooks.useTranslate();
|
|
20825
|
-
const
|
|
20826
|
-
|
|
21045
|
+
const navStack = providers.useNavStack();
|
|
21046
|
+
const sourceItems = fromNavStack ? navStack.entries.map((entry, i) => ({
|
|
21047
|
+
label: entry.label,
|
|
21048
|
+
path: entry.href,
|
|
21049
|
+
isCurrent: i === navStack.entries.length - 1,
|
|
21050
|
+
event: itemEvent
|
|
21051
|
+
})) : items ?? [];
|
|
21052
|
+
if (fromNavStack && sourceItems.length === 0) return null;
|
|
21053
|
+
const displayItems = maxItems && sourceItems.length > maxItems ? [
|
|
21054
|
+
...sourceItems.slice(0, 1),
|
|
20827
21055
|
{ label: "...", isCurrent: false },
|
|
20828
|
-
...
|
|
20829
|
-
] :
|
|
21056
|
+
...sourceItems.slice(-maxItems + 1)
|
|
21057
|
+
] : sourceItems;
|
|
20830
21058
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
20831
21059
|
"nav",
|
|
20832
21060
|
{
|
|
@@ -20836,7 +21064,7 @@ var init_Breadcrumb = __esm({
|
|
|
20836
21064
|
const isLast = index === displayItems.length - 1;
|
|
20837
21065
|
const isEllipsis = item.label === "...";
|
|
20838
21066
|
return /* @__PURE__ */ jsxRuntime.jsxs("li", { className: "flex items-center gap-2", children: [
|
|
20839
|
-
isEllipsis ? /* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "small", color: "muted", children: item.label }) : item.href || item.path ? /* @__PURE__ */ jsxRuntime.jsxs(
|
|
21067
|
+
isEllipsis ? /* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "small", color: "muted", children: item.label }) : (item.href || item.path) && !item.event && !fromNavStack ? /* @__PURE__ */ jsxRuntime.jsxs(
|
|
20840
21068
|
"a",
|
|
20841
21069
|
{
|
|
20842
21070
|
href: item.href || item.path,
|
|
@@ -20862,7 +21090,12 @@ var init_Breadcrumb = __esm({
|
|
|
20862
21090
|
{
|
|
20863
21091
|
type: "button",
|
|
20864
21092
|
onClick: () => {
|
|
20865
|
-
|
|
21093
|
+
const href = item.path ?? item.href;
|
|
21094
|
+
if (item.event) {
|
|
21095
|
+
eventBus.emit(`UI:${item.event}`, { label: item.label, href, index });
|
|
21096
|
+
} else if (fromNavStack && href) {
|
|
21097
|
+
navStack.goTo(href);
|
|
21098
|
+
}
|
|
20866
21099
|
item.onClick?.();
|
|
20867
21100
|
},
|
|
20868
21101
|
className: cn(
|
|
@@ -27691,6 +27924,196 @@ var init_PageTransition = __esm({
|
|
|
27691
27924
|
PageTransition.displayName = "PageTransition";
|
|
27692
27925
|
}
|
|
27693
27926
|
});
|
|
27927
|
+
function ConfettiBurst({ item, lifeMs }) {
|
|
27928
|
+
const particles = createConfettiParticles(item.particleCount ?? 30, item.id);
|
|
27929
|
+
const left = (item.x ?? 0.5) * 100;
|
|
27930
|
+
const top = (item.z ?? item.y ?? 0.4) * 100;
|
|
27931
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Box, { position: "absolute", style: { left: `${left}%`, top: `${top}%` }, children: particles.map((p) => {
|
|
27932
|
+
const rad = p.angle * Math.PI / 180;
|
|
27933
|
+
const tx = Math.cos(rad) * p.distance * (item.size ?? 1);
|
|
27934
|
+
const ty = Math.sin(rad) * p.distance * (item.size ?? 1) - 20;
|
|
27935
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
27936
|
+
Box,
|
|
27937
|
+
{
|
|
27938
|
+
className: "absolute rounded-sm",
|
|
27939
|
+
style: {
|
|
27940
|
+
left: (p.left - 50) * 2,
|
|
27941
|
+
top: -10,
|
|
27942
|
+
width: p.size,
|
|
27943
|
+
height: p.size,
|
|
27944
|
+
backgroundColor: item.color ?? p.color,
|
|
27945
|
+
animation: `confetti-burst ${Math.max(lifeMs - p.delay, 200)}ms ease-out ${p.delay}ms forwards`,
|
|
27946
|
+
opacity: 0,
|
|
27947
|
+
"--confetti-tx": `${tx}px`,
|
|
27948
|
+
"--confetti-ty": `${ty}px`,
|
|
27949
|
+
"--confetti-rotate": `${p.rotation}deg`
|
|
27950
|
+
}
|
|
27951
|
+
},
|
|
27952
|
+
p.id
|
|
27953
|
+
);
|
|
27954
|
+
}) });
|
|
27955
|
+
}
|
|
27956
|
+
function SparkleBurst({ item, lifeMs }) {
|
|
27957
|
+
const count = item.particleCount ?? 8;
|
|
27958
|
+
const scale = item.size ?? 1;
|
|
27959
|
+
const left = (item.x ?? 0.5) * 100;
|
|
27960
|
+
const top = (item.z ?? item.y ?? 0.4) * 100;
|
|
27961
|
+
return /* @__PURE__ */ jsxRuntime.jsx(Box, { position: "absolute", style: { left: `${left}%`, top: `${top}%` }, children: Array.from({ length: count }, (_, i) => {
|
|
27962
|
+
const dx = (fxHash01(item.id, i * 4) - 0.5) * 160 * scale;
|
|
27963
|
+
const dy = (fxHash01(item.id, i * 4 + 1) - 0.5) * 120 * scale;
|
|
27964
|
+
const dot = (4 + fxHash01(item.id, i * 4 + 2) * 5) * scale;
|
|
27965
|
+
const delay = fxHash01(item.id, i * 4 + 3) * lifeMs * 0.4;
|
|
27966
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
27967
|
+
Box,
|
|
27968
|
+
{
|
|
27969
|
+
className: "absolute rounded-full",
|
|
27970
|
+
style: {
|
|
27971
|
+
left: dx,
|
|
27972
|
+
top: dy,
|
|
27973
|
+
width: dot,
|
|
27974
|
+
height: dot,
|
|
27975
|
+
backgroundColor: item.color ?? "gold",
|
|
27976
|
+
opacity: 0,
|
|
27977
|
+
animation: `fx-overlay-sparkle ${Math.max(lifeMs - delay, 200)}ms ease-in-out ${delay}ms forwards`
|
|
27978
|
+
}
|
|
27979
|
+
},
|
|
27980
|
+
i
|
|
27981
|
+
);
|
|
27982
|
+
}) });
|
|
27983
|
+
}
|
|
27984
|
+
function OverlayFxNode({ item, tickMs }) {
|
|
27985
|
+
const lifeMs = lifeMsOf(item, tickMs);
|
|
27986
|
+
switch (item.effect ?? "sparkle") {
|
|
27987
|
+
case "confetti":
|
|
27988
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ConfettiBurst, { item, lifeMs });
|
|
27989
|
+
case "flash":
|
|
27990
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
27991
|
+
Box,
|
|
27992
|
+
{
|
|
27993
|
+
position: "absolute",
|
|
27994
|
+
className: "inset-0",
|
|
27995
|
+
style: {
|
|
27996
|
+
backgroundColor: item.color ?? "#ffffff",
|
|
27997
|
+
opacity: 0,
|
|
27998
|
+
animation: `fx-overlay-flash ${lifeMs}ms ease-out forwards`
|
|
27999
|
+
}
|
|
28000
|
+
}
|
|
28001
|
+
);
|
|
28002
|
+
case "streak-glow":
|
|
28003
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
28004
|
+
Box,
|
|
28005
|
+
{
|
|
28006
|
+
position: "absolute",
|
|
28007
|
+
className: "inset-0",
|
|
28008
|
+
style: {
|
|
28009
|
+
boxShadow: `inset 0 0 ${60 * (item.size ?? 1)}px ${item.color ?? "var(--color-warning)"}`,
|
|
28010
|
+
opacity: 0,
|
|
28011
|
+
animation: `fx-overlay-glow ${lifeMs}ms ease-in-out forwards`
|
|
28012
|
+
}
|
|
28013
|
+
}
|
|
28014
|
+
);
|
|
28015
|
+
case "float-text": {
|
|
28016
|
+
if (!item.message) return null;
|
|
28017
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
28018
|
+
Box,
|
|
28019
|
+
{
|
|
28020
|
+
position: "absolute",
|
|
28021
|
+
style: {
|
|
28022
|
+
left: `${(item.x ?? 0.5) * 100}%`,
|
|
28023
|
+
top: `${(item.z ?? item.y ?? 0.4) * 100}%`,
|
|
28024
|
+
color: item.color ?? "var(--color-success)",
|
|
28025
|
+
fontWeight: 700,
|
|
28026
|
+
fontSize: 16 * (item.size ?? 1),
|
|
28027
|
+
textShadow: "0 1px 2px rgba(0,0,0,0.4)",
|
|
28028
|
+
opacity: 0,
|
|
28029
|
+
animation: `fx-overlay-float ${lifeMs}ms ease-out forwards`,
|
|
28030
|
+
whiteSpace: "nowrap"
|
|
28031
|
+
},
|
|
28032
|
+
children: item.message
|
|
28033
|
+
}
|
|
28034
|
+
);
|
|
28035
|
+
}
|
|
28036
|
+
case "shake":
|
|
28037
|
+
return null;
|
|
28038
|
+
default:
|
|
28039
|
+
return /* @__PURE__ */ jsxRuntime.jsx(SparkleBurst, { item, lifeMs });
|
|
28040
|
+
}
|
|
28041
|
+
}
|
|
28042
|
+
var DEFAULT_TICK_MS2, FX_OVERLAY_KEYFRAMES, lifeMsOf, FxOverlay;
|
|
28043
|
+
var init_FxOverlay = __esm({
|
|
28044
|
+
"components/core/molecules/FxOverlay.tsx"() {
|
|
28045
|
+
"use client";
|
|
28046
|
+
init_cn();
|
|
28047
|
+
init_Box();
|
|
28048
|
+
init_fx();
|
|
28049
|
+
DEFAULT_TICK_MS2 = 500;
|
|
28050
|
+
FX_OVERLAY_KEYFRAMES = `
|
|
28051
|
+
${CONFETTI_BURST_KEYFRAMES}
|
|
28052
|
+
@keyframes fx-overlay-flash {
|
|
28053
|
+
0% { opacity: 0.75; }
|
|
28054
|
+
100% { opacity: 0; }
|
|
28055
|
+
}
|
|
28056
|
+
@keyframes fx-overlay-glow {
|
|
28057
|
+
0% { opacity: 0.9; }
|
|
28058
|
+
60% { opacity: 0.6; }
|
|
28059
|
+
100% { opacity: 0; }
|
|
28060
|
+
}
|
|
28061
|
+
@keyframes fx-overlay-sparkle {
|
|
28062
|
+
0% { opacity: 0; transform: scale(0); }
|
|
28063
|
+
30% { opacity: 1; transform: scale(1); }
|
|
28064
|
+
100% { opacity: 0; transform: scale(0.3); }
|
|
28065
|
+
}
|
|
28066
|
+
@keyframes fx-overlay-float {
|
|
28067
|
+
0% { opacity: 0; transform: translate(-50%, 8px); }
|
|
28068
|
+
15% { opacity: 1; }
|
|
28069
|
+
100% { opacity: 0; transform: translate(-50%, -40px); }
|
|
28070
|
+
}
|
|
28071
|
+
@keyframes fx-overlay-shake {
|
|
28072
|
+
0% { transform: translateX(0); }
|
|
28073
|
+
15% { transform: translateX(-6px); }
|
|
28074
|
+
30% { transform: translateX(5px); }
|
|
28075
|
+
45% { transform: translateX(-4px); }
|
|
28076
|
+
60% { transform: translateX(3px); }
|
|
28077
|
+
75% { transform: translateX(-2px); }
|
|
28078
|
+
100% { transform: translateX(0); }
|
|
28079
|
+
}
|
|
28080
|
+
`;
|
|
28081
|
+
lifeMsOf = (it, tickMs) => Math.max(it.maxTtl ?? it.ttl, it.ttl, 1) * tickMs;
|
|
28082
|
+
FxOverlay = ({ items, tickMs = DEFAULT_TICK_MS2, children, className }) => {
|
|
28083
|
+
const screenItems = (Array.isArray(items) ? items : []).filter(
|
|
28084
|
+
(it) => Boolean(it) && typeof it.id === "string" && it.space !== "world"
|
|
28085
|
+
);
|
|
28086
|
+
const shakeItem = [...screenItems].reverse().find((it) => it.effect === "shake");
|
|
28087
|
+
const overlay = /* @__PURE__ */ jsxRuntime.jsxs(
|
|
28088
|
+
Box,
|
|
28089
|
+
{
|
|
28090
|
+
position: "absolute",
|
|
28091
|
+
className: cn("inset-0 pointer-events-none overflow-hidden z-50", !children && className),
|
|
28092
|
+
"aria-hidden": "true",
|
|
28093
|
+
children: [
|
|
28094
|
+
screenItems.map((it) => /* @__PURE__ */ jsxRuntime.jsx(OverlayFxNode, { item: it, tickMs }, it.id)),
|
|
28095
|
+
/* @__PURE__ */ jsxRuntime.jsx("style", { children: FX_OVERLAY_KEYFRAMES })
|
|
28096
|
+
]
|
|
28097
|
+
}
|
|
28098
|
+
);
|
|
28099
|
+
if (children !== void 0 && children !== null) {
|
|
28100
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(Box, { position: "relative", className, children: [
|
|
28101
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
28102
|
+
Box,
|
|
28103
|
+
{
|
|
28104
|
+
style: shakeItem ? { animation: `fx-overlay-shake ${Math.min(lifeMsOf(shakeItem, tickMs), 600)}ms ease-in-out` } : void 0,
|
|
28105
|
+
children
|
|
28106
|
+
},
|
|
28107
|
+
shakeItem?.id ?? "steady"
|
|
28108
|
+
),
|
|
28109
|
+
overlay
|
|
28110
|
+
] });
|
|
28111
|
+
}
|
|
28112
|
+
return overlay;
|
|
28113
|
+
};
|
|
28114
|
+
FxOverlay.displayName = "FxOverlay";
|
|
28115
|
+
}
|
|
28116
|
+
});
|
|
27694
28117
|
function computePopoverStyle(position, triggerRect, popoverWidth) {
|
|
27695
28118
|
if (position === "left" || position === "right") {
|
|
27696
28119
|
return {
|
|
@@ -29696,7 +30119,7 @@ var init_MathCanvas = __esm({
|
|
|
29696
30119
|
x: mapX((first.x + last.x) / 2),
|
|
29697
30120
|
y: (mapY(region.samples[mid].y) + mapY(baseline)) / 2,
|
|
29698
30121
|
text: region.label,
|
|
29699
|
-
color
|
|
30122
|
+
color,
|
|
29700
30123
|
fontSize: 11
|
|
29701
30124
|
});
|
|
29702
30125
|
}
|
|
@@ -29729,14 +30152,14 @@ var init_MathCanvas = __esm({
|
|
|
29729
30152
|
const px = mapX(guide.at);
|
|
29730
30153
|
out.push({ type: "line", x1: px, y1: margin, x2: px, y2: height - margin, color, dash });
|
|
29731
30154
|
if (guide.label) {
|
|
29732
|
-
out.push({ type: "text", x: px + 4, y: margin + 10, text: guide.label, color
|
|
30155
|
+
out.push({ type: "text", x: px + 4, y: margin + 10, text: guide.label, color, fontSize: 11 });
|
|
29733
30156
|
}
|
|
29734
30157
|
} else {
|
|
29735
30158
|
if (guide.at < yMin || guide.at > yMax) continue;
|
|
29736
30159
|
const py = mapY(guide.at);
|
|
29737
30160
|
out.push({ type: "line", x1: margin, y1: py, x2: width - margin, y2: py, color, dash });
|
|
29738
30161
|
if (guide.label) {
|
|
29739
|
-
out.push({ type: "text", x: width - margin - 4, y: py - 8, text: guide.label, color
|
|
30162
|
+
out.push({ type: "text", x: width - margin - 4, y: py - 8, text: guide.label, color, fontSize: 11, align: "right" });
|
|
29740
30163
|
}
|
|
29741
30164
|
}
|
|
29742
30165
|
}
|
|
@@ -29802,7 +30225,7 @@ var init_MathCanvas = __esm({
|
|
|
29802
30225
|
x: (x1 + x2) / 2,
|
|
29803
30226
|
y: xAxisY - peak - 8,
|
|
29804
30227
|
text: hop.label,
|
|
29805
|
-
color
|
|
30228
|
+
color,
|
|
29806
30229
|
fontSize: 10,
|
|
29807
30230
|
align: "center"
|
|
29808
30231
|
});
|
|
@@ -29829,7 +30252,7 @@ var init_MathCanvas = __esm({
|
|
|
29829
30252
|
x: mapX(angle.x + 1.35 * radius * Math.cos(rad)),
|
|
29830
30253
|
y: mapY(angle.y + 1.35 * radius * Math.sin(rad)),
|
|
29831
30254
|
text: angle.label,
|
|
29832
|
-
color
|
|
30255
|
+
color,
|
|
29833
30256
|
fontSize: 11,
|
|
29834
30257
|
align: "center"
|
|
29835
30258
|
});
|
|
@@ -29847,7 +30270,7 @@ var init_MathCanvas = __esm({
|
|
|
29847
30270
|
fill: isOpen ? "#ffffff" : p.color ?? "#dc2626"
|
|
29848
30271
|
});
|
|
29849
30272
|
if (p.label) {
|
|
29850
|
-
out.push({ type: "text", x: mapX(p.x) + 8, y: mapY(p.y) - 8, text: p.label, color: "#111827", fontSize: 12 });
|
|
30273
|
+
out.push({ type: "text", x: mapX(p.x) + 8, y: mapY(p.y) - 8, text: p.label, color: p.color ?? "#111827", fontSize: 12 });
|
|
29851
30274
|
}
|
|
29852
30275
|
}
|
|
29853
30276
|
for (const v of vectors) {
|
|
@@ -29858,7 +30281,7 @@ var init_MathCanvas = __esm({
|
|
|
29858
30281
|
const y2 = mapY(v.y + v.vy);
|
|
29859
30282
|
out.push({ type: "arrow", x1, y1, x2, y2, color: v.color ?? "#7c3aed", lineWidth: 2 });
|
|
29860
30283
|
if (v.label) {
|
|
29861
|
-
out.push({ type: "text", x: x2 + 6, y: y2 - 6, text: v.label, color: "#
|
|
30284
|
+
out.push({ type: "text", x: x2 + 6, y: y2 - 6, text: v.label, color: v.color ?? "#7c3aed", fontSize: 12 });
|
|
29862
30285
|
}
|
|
29863
30286
|
}
|
|
29864
30287
|
out.push(...shapes);
|
|
@@ -41271,6 +41694,7 @@ var init_DetailPanel = __esm({
|
|
|
41271
41694
|
init_Box();
|
|
41272
41695
|
init_Stack();
|
|
41273
41696
|
init_SimpleGrid();
|
|
41697
|
+
init_Menu();
|
|
41274
41698
|
init_LoadingState();
|
|
41275
41699
|
init_ErrorState();
|
|
41276
41700
|
init_EmptyState();
|
|
@@ -41288,6 +41712,7 @@ var init_DetailPanel = __esm({
|
|
|
41288
41712
|
avatar,
|
|
41289
41713
|
sections: propSections,
|
|
41290
41714
|
actions,
|
|
41715
|
+
maxInlineActions,
|
|
41291
41716
|
backAction,
|
|
41292
41717
|
footer,
|
|
41293
41718
|
slideOver = false,
|
|
@@ -41522,7 +41947,7 @@ var init_DetailPanel = __esm({
|
|
|
41522
41947
|
}
|
|
41523
41948
|
) }),
|
|
41524
41949
|
/* @__PURE__ */ jsxRuntime.jsxs(HStack, { justify: "end", align: "center", gap: "xs", children: [
|
|
41525
|
-
otherActions.map((action, idx) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
41950
|
+
(maxInlineActions != null ? otherActions.slice(0, maxInlineActions) : otherActions).map((action, idx) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
41526
41951
|
Button,
|
|
41527
41952
|
{
|
|
41528
41953
|
variant: action.variant || "secondary",
|
|
@@ -41537,6 +41962,22 @@ var init_DetailPanel = __esm({
|
|
|
41537
41962
|
},
|
|
41538
41963
|
idx
|
|
41539
41964
|
)),
|
|
41965
|
+
maxInlineActions != null && otherActions.length > maxInlineActions && /* @__PURE__ */ jsxRuntime.jsx(
|
|
41966
|
+
Menu,
|
|
41967
|
+
{
|
|
41968
|
+
position: "bottom-end",
|
|
41969
|
+
trigger: /* @__PURE__ */ jsxRuntime.jsx(Button, { variant: "ghost", size: "sm", "aria-label": t("common.actions"), "data-testid": "action-overflow", children: /* @__PURE__ */ jsxRuntime.jsx(Icon, { name: "more-horizontal", size: "xs" }) }),
|
|
41970
|
+
items: otherActions.slice(maxInlineActions).map((action) => ({
|
|
41971
|
+
// ONE firing path: onClick → handleActionClick (emits with
|
|
41972
|
+
// the {id, row} payload). Passing `event` too would make
|
|
41973
|
+
// Menu emit a second, payload-less copy of the same event.
|
|
41974
|
+
label: action.label,
|
|
41975
|
+
icon: action.icon,
|
|
41976
|
+
variant: action.variant === "danger" ? "danger" : "default",
|
|
41977
|
+
onClick: () => handleActionClick(action, normalizedData)
|
|
41978
|
+
}))
|
|
41979
|
+
}
|
|
41980
|
+
),
|
|
41540
41981
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
41541
41982
|
Button,
|
|
41542
41983
|
{
|
|
@@ -47412,6 +47853,7 @@ var init_component_registry_generated = __esm({
|
|
|
47412
47853
|
init_DocSidebar();
|
|
47413
47854
|
init_DocTOC();
|
|
47414
47855
|
init_DocumentViewer();
|
|
47856
|
+
init_DrawFxLayer();
|
|
47415
47857
|
init_DrawGroup();
|
|
47416
47858
|
init_DrawMesh();
|
|
47417
47859
|
init_DrawShape();
|
|
@@ -47442,6 +47884,7 @@ var init_component_registry_generated = __esm({
|
|
|
47442
47884
|
init_FormField();
|
|
47443
47885
|
init_FormSection();
|
|
47444
47886
|
init_FormSectionHeader();
|
|
47887
|
+
init_FxOverlay();
|
|
47445
47888
|
init_GameAudioToggle();
|
|
47446
47889
|
init_GameHud();
|
|
47447
47890
|
init_GameIcon();
|
|
@@ -47682,6 +48125,7 @@ var init_component_registry_generated = __esm({
|
|
|
47682
48125
|
"DocSidebar": DocSidebar,
|
|
47683
48126
|
"DocTOC": DocTOC,
|
|
47684
48127
|
"DocumentViewer": DocumentViewer,
|
|
48128
|
+
"DrawFxLayer": DrawFxLayer,
|
|
47685
48129
|
"DrawGroup": DrawGroup,
|
|
47686
48130
|
"DrawMesh": DrawMesh,
|
|
47687
48131
|
"DrawShape": DrawShape,
|
|
@@ -47712,6 +48156,7 @@ var init_component_registry_generated = __esm({
|
|
|
47712
48156
|
"FormField": FormField,
|
|
47713
48157
|
"FormLayout": FormLayout,
|
|
47714
48158
|
"FormSectionHeader": FormSectionHeader,
|
|
48159
|
+
"FxOverlay": FxOverlay,
|
|
47715
48160
|
"GameAudioToggle": GameAudioToggle,
|
|
47716
48161
|
"GameHud": GameHud,
|
|
47717
48162
|
"GameIcon": GameIcon,
|
|
@@ -48977,7 +49422,7 @@ function runTickFrame(entityId, orderedWriters, store) {
|
|
|
48977
49422
|
}
|
|
48978
49423
|
var log3 = logger.createLogger("almadar:ui:effects:client-handlers");
|
|
48979
49424
|
function createClientEffectHandlers(options) {
|
|
48980
|
-
const { eventBus, slotSetter, navigate, notify, callService, liveEntity } = options;
|
|
49425
|
+
const { eventBus, slotSetter, navigate, navigateBack, notify, callService, liveEntity } = options;
|
|
48981
49426
|
return {
|
|
48982
49427
|
emit: (event, payload, source) => {
|
|
48983
49428
|
const prefixedEvent = event.startsWith("UI:") ? event : `UI:${event}`;
|
|
@@ -49027,6 +49472,9 @@ function createClientEffectHandlers(options) {
|
|
|
49027
49472
|
}
|
|
49028
49473
|
log3.warn("No navigate handler, ignoring", { path });
|
|
49029
49474
|
}),
|
|
49475
|
+
navigateBack: navigateBack ?? (() => {
|
|
49476
|
+
log3.warn("No navigate-back handler, ignoring");
|
|
49477
|
+
}),
|
|
49030
49478
|
notify: notify ?? ((msg, type) => {
|
|
49031
49479
|
log3.debug("notify", { type, message: msg });
|
|
49032
49480
|
})
|
|
@@ -49666,6 +50114,7 @@ function useTraitStateMachine(traitBindings, uiSlots, options) {
|
|
|
49666
50114
|
}
|
|
49667
50115
|
},
|
|
49668
50116
|
navigate: optionsRef.current?.navigate,
|
|
50117
|
+
navigateBack: optionsRef.current?.navigateBack,
|
|
49669
50118
|
notify: optionsRef.current?.notify,
|
|
49670
50119
|
callService: optionsRef.current?.callService,
|
|
49671
50120
|
// The canonical client `set` writes `(set @entity.X)` straight into
|
|
@@ -49727,6 +50176,7 @@ function useTraitStateMachine(traitBindings, uiSlots, options) {
|
|
|
49727
50176
|
emit: clientHandlers.emit,
|
|
49728
50177
|
renderUI: clientHandlers.renderUI,
|
|
49729
50178
|
navigate: clientHandlers.navigate,
|
|
50179
|
+
navigateBack: clientHandlers.navigateBack,
|
|
49730
50180
|
notify: clientHandlers.notify
|
|
49731
50181
|
};
|
|
49732
50182
|
}
|
|
@@ -50449,7 +50899,7 @@ function normalizeChild(child) {
|
|
|
50449
50899
|
props: { ...rest, ...normalizedChildren !== void 0 ? { children: normalizedChildren } : {} }
|
|
50450
50900
|
};
|
|
50451
50901
|
}
|
|
50452
|
-
function applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraits) {
|
|
50902
|
+
function applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraits, onNavigateBack) {
|
|
50453
50903
|
for (const eff of effects) {
|
|
50454
50904
|
if (eff.type === "render-ui" && eff.slot && eff.pattern) {
|
|
50455
50905
|
if (eff.traitName && activeTraits && !activeTraits.has(eff.traitName)) {
|
|
@@ -50495,7 +50945,9 @@ function applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, active
|
|
|
50495
50945
|
});
|
|
50496
50946
|
}
|
|
50497
50947
|
} else if (eff.type === "navigate" && eff.route && onNavigate) {
|
|
50498
|
-
onNavigate(eff.route, eff.params);
|
|
50948
|
+
onNavigate(eff.route, eff.params, eff.crumb);
|
|
50949
|
+
} else if (eff.type === "navigate-back" && onNavigateBack) {
|
|
50950
|
+
onNavigateBack();
|
|
50499
50951
|
}
|
|
50500
50952
|
}
|
|
50501
50953
|
}
|
|
@@ -50518,7 +50970,17 @@ function collectServerActiveTraits(ir, allTraits, mountedTraitNames) {
|
|
|
50518
50970
|
}
|
|
50519
50971
|
return active;
|
|
50520
50972
|
}
|
|
50521
|
-
function
|
|
50973
|
+
function NavStackRefBridge({ apiRef }) {
|
|
50974
|
+
const api = providers.useNavStack();
|
|
50975
|
+
React85.useEffect(() => {
|
|
50976
|
+
apiRef.current = api;
|
|
50977
|
+
return () => {
|
|
50978
|
+
apiRef.current = null;
|
|
50979
|
+
};
|
|
50980
|
+
}, [api, apiRef]);
|
|
50981
|
+
return null;
|
|
50982
|
+
}
|
|
50983
|
+
function TraitInitializer({ traits: traits2, routeParams, orbitalNames, onNavigate, onNavigateBack, onLocalFallback, persistence, traitConfigsByName, orbitalsByTrait, embeddedTraits, serverActiveTraits, children }) {
|
|
50522
50984
|
const bridge = providers.useServerBridge();
|
|
50523
50985
|
const activeTraitNames = React85.useMemo(
|
|
50524
50986
|
() => new Set(traits2.map((b) => b.trait.name).filter((n) => !!n)),
|
|
@@ -50544,10 +51006,10 @@ function TraitInitializer({ traits: traits2, routeParams, orbitalNames, onNaviga
|
|
|
50544
51006
|
for (const name of targets) {
|
|
50545
51007
|
const { effects, meta } = await bridge.sendEvent(name, event, withActiveTraits(payload));
|
|
50546
51008
|
recordServerResponse(name, event, meta);
|
|
50547
|
-
applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraitNames);
|
|
51009
|
+
applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraitNames, onNavigateBack);
|
|
50548
51010
|
}
|
|
50549
|
-
}, [bridge.connected, bridge.sendEvent, orbitalNames, uiSlots, onNavigate, embeddedTraits, activeTraitNames, withActiveTraits]);
|
|
50550
|
-
const opts = orbitalNames ? { onEventProcessed, navigate: onNavigate, traitConfigsByName, orbitalsByTrait, embeddedTraits, initPayload: routeParams } : { navigate: onNavigate, persistence, traitConfigsByName, orbitalsByTrait, embeddedTraits, initPayload: routeParams };
|
|
51011
|
+
}, [bridge.connected, bridge.sendEvent, orbitalNames, uiSlots, onNavigate, onNavigateBack, embeddedTraits, activeTraitNames, withActiveTraits]);
|
|
51012
|
+
const opts = orbitalNames ? { onEventProcessed, navigate: onNavigate, navigateBack: onNavigateBack, traitConfigsByName, orbitalsByTrait, embeddedTraits, initPayload: routeParams } : { navigate: onNavigate, navigateBack: onNavigateBack, persistence, traitConfigsByName, orbitalsByTrait, embeddedTraits, initPayload: routeParams };
|
|
50551
51013
|
const { sendEvent, entityBindingSource } = useTraitStateMachine(traits2, uiSlots, opts);
|
|
50552
51014
|
const initSentRef = React85.useRef(false);
|
|
50553
51015
|
const prevTraitsRef = React85.useRef(void 0);
|
|
@@ -50606,13 +51068,13 @@ function TraitInitializer({ traits: traits2, routeParams, orbitalNames, onNaviga
|
|
|
50606
51068
|
effects: effectTraces,
|
|
50607
51069
|
timestamp: Date.now()
|
|
50608
51070
|
});
|
|
50609
|
-
applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraitNames);
|
|
51071
|
+
applyServerEffects(effects, uiSlots, onNavigate, embeddedTraits, activeTraitNames, onNavigateBack);
|
|
50610
51072
|
}
|
|
50611
51073
|
})();
|
|
50612
|
-
}, [bridge.connected, orbitalNames, bridge.sendEvent, uiSlots, onNavigate, embeddedTraits, activeTraitNames, withActiveTraits, routeParams]);
|
|
51074
|
+
}, [bridge.connected, orbitalNames, bridge.sendEvent, uiSlots, onNavigate, onNavigateBack, embeddedTraits, activeTraitNames, withActiveTraits, routeParams]);
|
|
50613
51075
|
return /* @__PURE__ */ jsxRuntime.jsx(providers.EntityBindingContext.Provider, { value: entityBindingSource, children });
|
|
50614
51076
|
}
|
|
50615
|
-
function SchemaRunner({ schema, serverUrl, transport, mockData, pageName, routeParams, onNavigate, onLocalFallback, persistence }) {
|
|
51077
|
+
function SchemaRunner({ schema, serverUrl, transport, mockData, pageName, routeParams, onNavigate, onNavigateBack, onLocalFallback, persistence }) {
|
|
50616
51078
|
const { traits: traits2, allEntities, allTraits, ir } = useResolvedSchema(schema, pageName);
|
|
50617
51079
|
const allPageTraits = React85.useMemo(() => {
|
|
50618
51080
|
let base;
|
|
@@ -50760,6 +51222,7 @@ function SchemaRunner({ schema, serverUrl, transport, mockData, pageName, routeP
|
|
|
50760
51222
|
embeddedTraits,
|
|
50761
51223
|
serverActiveTraits,
|
|
50762
51224
|
onNavigate,
|
|
51225
|
+
onNavigateBack,
|
|
50763
51226
|
onLocalFallback,
|
|
50764
51227
|
persistence,
|
|
50765
51228
|
children: /* @__PURE__ */ jsxRuntime.jsx(providers.OrbitalThemeProvider, { theme: activeOrbitalTheme, children: /* @__PURE__ */ jsxRuntime.jsx(Box, { className: "h-full min-h-full overflow-auto p-4", children: /* @__PURE__ */ jsxRuntime.jsx(UISlotRenderer, { includeHud: true, hudMode: "inline", includeFloating: true }) }) })
|
|
@@ -50852,6 +51315,15 @@ function OrbPreview({
|
|
|
50852
51315
|
const resolved = pages.find((p) => p.page.name === activePageName)?.page.path;
|
|
50853
51316
|
return resolved ?? initialPagePath;
|
|
50854
51317
|
}, [pages, currentPage, initialPagePath]);
|
|
51318
|
+
const navPages = React85.useMemo(
|
|
51319
|
+
() => pages.filter((p) => typeof p.page.path === "string" && p.page.path.length > 0).map((p) => ({ path: p.page.path, name: p.page.name, orbital: p.orbitalName })),
|
|
51320
|
+
[pages]
|
|
51321
|
+
);
|
|
51322
|
+
const concreteCurrentPath = React85.useMemo(() => {
|
|
51323
|
+
const pattern = currentPagePath ?? "/";
|
|
51324
|
+
return pattern.replace(/:([A-Za-z0-9_]+)/g, (whole, key) => routeParams[key] ?? whole);
|
|
51325
|
+
}, [currentPagePath, routeParams]);
|
|
51326
|
+
const navStackRef = React85.useRef(null);
|
|
50855
51327
|
const handleNavigate = React85.useCallback((path) => {
|
|
50856
51328
|
const hit = providers.matchPathAmong(pages, path, (entry) => entry.page.path);
|
|
50857
51329
|
const match = hit?.candidate;
|
|
@@ -50873,6 +51345,16 @@ function OrbPreview({
|
|
|
50873
51345
|
}
|
|
50874
51346
|
}
|
|
50875
51347
|
}, [pages]);
|
|
51348
|
+
const handleNavigateEffect = React85.useCallback(
|
|
51349
|
+
(path, _params, crumb) => {
|
|
51350
|
+
navStackRef.current?.beginNavigate(path, crumb);
|
|
51351
|
+
handleNavigate(path);
|
|
51352
|
+
},
|
|
51353
|
+
[handleNavigate]
|
|
51354
|
+
);
|
|
51355
|
+
const handleNavigateBack = React85.useCallback(() => {
|
|
51356
|
+
navStackRef.current?.back();
|
|
51357
|
+
}, []);
|
|
50876
51358
|
React85.useEffect(() => {
|
|
50877
51359
|
const unsubscribe = eventBus.on("UI:NAVIGATE", (event) => {
|
|
50878
51360
|
const url = event.payload?.url;
|
|
@@ -50925,20 +51407,33 @@ function OrbPreview({
|
|
|
50925
51407
|
style: { height },
|
|
50926
51408
|
children: [
|
|
50927
51409
|
localFallback && /* @__PURE__ */ jsxRuntime.jsx(Box, { className: "px-3 py-2 bg-[var(--color-warning)] bg-opacity-10 border-b border-[var(--color-warning)] flex items-center gap-2", children: /* @__PURE__ */ jsxRuntime.jsx(Typography, { variant: "caption", className: "text-[var(--color-warning-foreground)] flex-1", children: "Preview server unreachable \u2014 running locally. Server-side state and persistence are disabled." }) }),
|
|
50928
|
-
/* @__PURE__ */ jsxRuntime.jsx(providers.CurrentPagePathProvider, { value: currentPagePath, children: /* @__PURE__ */ jsxRuntime.
|
|
50929
|
-
|
|
51410
|
+
/* @__PURE__ */ jsxRuntime.jsx(providers.CurrentPagePathProvider, { value: currentPagePath, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
51411
|
+
providers.NavStackProvider,
|
|
50930
51412
|
{
|
|
50931
|
-
|
|
50932
|
-
|
|
50933
|
-
|
|
50934
|
-
|
|
50935
|
-
|
|
50936
|
-
|
|
50937
|
-
|
|
50938
|
-
|
|
50939
|
-
|
|
50940
|
-
|
|
50941
|
-
|
|
51413
|
+
pages: navPages,
|
|
51414
|
+
currentPath: concreteCurrentPath,
|
|
51415
|
+
navigate: handleNavigate,
|
|
51416
|
+
storageKey: `almadar:navstack:${parseResult.schema.name ?? "preview"}`,
|
|
51417
|
+
children: [
|
|
51418
|
+
/* @__PURE__ */ jsxRuntime.jsx(NavStackRefBridge, { apiRef: navStackRef }),
|
|
51419
|
+
/* @__PURE__ */ jsxRuntime.jsx(providers.OrbitalProvider, { initialData: effectiveMockData, skipTheme: true, verification: true, isolated, children: /* @__PURE__ */ jsxRuntime.jsx(context.UISlotProvider, { children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
51420
|
+
SchemaRunner,
|
|
51421
|
+
{
|
|
51422
|
+
schema: parseResult.schema,
|
|
51423
|
+
serverUrl,
|
|
51424
|
+
transport,
|
|
51425
|
+
mockData: effectiveMockData,
|
|
51426
|
+
pageName: currentPage,
|
|
51427
|
+
routeParams,
|
|
51428
|
+
onNavigate: handleNavigateEffect,
|
|
51429
|
+
onNavigateBack: handleNavigateBack,
|
|
51430
|
+
onLocalFallback: handleLocalFallback,
|
|
51431
|
+
persistence
|
|
51432
|
+
}
|
|
51433
|
+
) }) })
|
|
51434
|
+
]
|
|
51435
|
+
}
|
|
51436
|
+
) })
|
|
50942
51437
|
]
|
|
50943
51438
|
}
|
|
50944
51439
|
);
|