@momoyu-ink/kit 0.10.0 → 0.11.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/AGENTS.md +3 -2
- package/dist/{jsx-dev-runtime-gGlb6FbX.d.mts → jsx-dev-runtime-BasPxDFu.d.mts} +246 -3
- package/dist/{jsx-dev-runtime-gGlb6FbX.d.ts → jsx-dev-runtime-BasPxDFu.d.ts} +246 -3
- package/dist/jsx-dev-runtime.d.mts +1 -1
- package/dist/jsx-dev-runtime.d.ts +1 -1
- package/dist/jsx-runtime.d.mts +1 -1
- package/dist/jsx-runtime.d.ts +1 -1
- package/dist/lib.cjs +647 -138
- package/dist/lib.d.mts +88 -15
- package/dist/lib.d.ts +88 -15
- package/dist/lib.mjs +657 -137
- package/package.json +2 -1
package/dist/lib.cjs
CHANGED
|
@@ -34,14 +34,18 @@ __export(lib_exports, {
|
|
|
34
34
|
Button: () => Button,
|
|
35
35
|
Checkbox: () => Checkbox,
|
|
36
36
|
DEBUG_EMPTY_PAGE: () => DEBUG_EMPTY_PAGE,
|
|
37
|
+
Input: () => Input,
|
|
37
38
|
OverlayParamsContext: () => OverlayParamsContext,
|
|
38
39
|
PageParamsContext: () => PageParamsContext,
|
|
40
|
+
Radio: () => Radio,
|
|
41
|
+
RadioGroup: () => RadioGroup,
|
|
39
42
|
ScrollView: () => ScrollView,
|
|
40
43
|
Select: () => Select,
|
|
41
44
|
Slider: () => Slider,
|
|
42
45
|
StageContextProvider: () => StageContextProvider,
|
|
43
46
|
a: () => animated,
|
|
44
47
|
addEventListener: () => addEventListener,
|
|
48
|
+
addFluidObserver: () => addFluidObserver,
|
|
45
49
|
animated: () => animated,
|
|
46
50
|
autoState: () => autoState,
|
|
47
51
|
createBubbleEvent: () => createBubbleEvent,
|
|
@@ -68,6 +72,7 @@ __export(lib_exports, {
|
|
|
68
72
|
moyu: () => moyu_exports,
|
|
69
73
|
nextLine: () => nextLine,
|
|
70
74
|
registerAppStateAdapter: () => registerAppStateAdapter,
|
|
75
|
+
removeFluidObserver: () => removeFluidObserver,
|
|
71
76
|
replaceUiData: () => replaceUiData,
|
|
72
77
|
setDefaultAutoTailMs: () => setDefaultAutoTailMs,
|
|
73
78
|
setWaiting: () => setWaiting,
|
|
@@ -110,10 +115,12 @@ var import_constants = require("react-reconciler/constants.js");
|
|
|
110
115
|
var moyu_exports = {};
|
|
111
116
|
__export(moyu_exports, {
|
|
112
117
|
addChild: () => addChild,
|
|
118
|
+
blurEditable: () => blurEditable,
|
|
113
119
|
createInstance: () => createInstance,
|
|
114
120
|
destroyInstance: () => destroyInstance,
|
|
115
121
|
executeNodeCommand: () => executeNodeCommand,
|
|
116
122
|
executePluginCommand: () => executePluginCommand,
|
|
123
|
+
focusEditable: () => focusEditable,
|
|
117
124
|
insertChild: () => insertChild,
|
|
118
125
|
insertChildBefore: () => insertChildBefore,
|
|
119
126
|
removeChild: () => removeChild,
|
|
@@ -151,6 +158,12 @@ function removeChild(nodeId, childNodeId) {
|
|
|
151
158
|
function updateProps(nodeId, props) {
|
|
152
159
|
moyu.pushCommand("update_props", [nodeId, props]);
|
|
153
160
|
}
|
|
161
|
+
function focusEditable(nodeId) {
|
|
162
|
+
moyu.pushCommand("focus_editable", [nodeId]);
|
|
163
|
+
}
|
|
164
|
+
function blurEditable(nodeId) {
|
|
165
|
+
moyu.pushCommand("blur_editable", [nodeId]);
|
|
166
|
+
}
|
|
154
167
|
function executeNodeCommand(nodeId, payload) {
|
|
155
168
|
return moyu.executeNodeCommand(nodeId, payload);
|
|
156
169
|
}
|
|
@@ -794,7 +807,9 @@ globalThis.__moyu_eval_sandbox = (code) => {
|
|
|
794
807
|
var spring_exports = {};
|
|
795
808
|
__export(spring_exports, {
|
|
796
809
|
a: () => animated,
|
|
797
|
-
|
|
810
|
+
addFluidObserver: () => addFluidObserver,
|
|
811
|
+
animated: () => animated,
|
|
812
|
+
removeFluidObserver: () => removeFluidObserver
|
|
798
813
|
});
|
|
799
814
|
var import_animated = require("@react-spring/animated");
|
|
800
815
|
var import_shared = require("@react-spring/shared");
|
|
@@ -827,6 +842,8 @@ var host = (0, import_animated.createHost)(primitives, {
|
|
|
827
842
|
}
|
|
828
843
|
});
|
|
829
844
|
var animated = host.animated;
|
|
845
|
+
var addFluidObserver = import_shared.addFluidObserver;
|
|
846
|
+
var removeFluidObserver = import_shared.removeFluidObserver;
|
|
830
847
|
|
|
831
848
|
// src/lib.ts
|
|
832
849
|
__reExport(lib_exports, spring_exports, module.exports);
|
|
@@ -851,7 +868,8 @@ function createBubbleEvent(body, targetId) {
|
|
|
851
868
|
|
|
852
869
|
// src/events/globals.ts
|
|
853
870
|
var globalEventListeners = {};
|
|
854
|
-
var globalRequestAnimationFrameListeners =
|
|
871
|
+
var globalRequestAnimationFrameListeners = /* @__PURE__ */ new Map();
|
|
872
|
+
var nextAnimationFrameHandle = 0;
|
|
855
873
|
var BUBBLE_EVENT_NAMES = ["mouseevent", "touchevent", "keyboardevent", "wheelevent"];
|
|
856
874
|
globalThis.__moyu_receive_event = (raw_event) => {
|
|
857
875
|
const { name, body } = raw_event;
|
|
@@ -878,7 +896,8 @@ globalThis.__moyu_receive_event = (raw_event) => {
|
|
|
878
896
|
return;
|
|
879
897
|
}
|
|
880
898
|
case "animationframecallbackevent": {
|
|
881
|
-
const listeners = globalRequestAnimationFrameListeners.
|
|
899
|
+
const listeners = [...globalRequestAnimationFrameListeners.values()];
|
|
900
|
+
globalRequestAnimationFrameListeners.clear();
|
|
882
901
|
const { timestamp } = body;
|
|
883
902
|
for (const listener of listeners) {
|
|
884
903
|
listener?.(timestamp);
|
|
@@ -936,10 +955,13 @@ function handleBubbleEvent(name, body) {
|
|
|
936
955
|
}
|
|
937
956
|
if (globalThis.__moyu_native) {
|
|
938
957
|
globalThis.requestAnimationFrame = (callback) => {
|
|
939
|
-
|
|
958
|
+
const handle = nextAnimationFrameHandle;
|
|
959
|
+
nextAnimationFrameHandle += 1;
|
|
960
|
+
globalRequestAnimationFrameListeners.set(handle, callback);
|
|
961
|
+
return handle;
|
|
940
962
|
};
|
|
941
963
|
globalThis.cancelAnimationFrame = (handle) => {
|
|
942
|
-
globalRequestAnimationFrameListeners.
|
|
964
|
+
globalRequestAnimationFrameListeners.delete(handle);
|
|
943
965
|
};
|
|
944
966
|
}
|
|
945
967
|
|
|
@@ -1260,6 +1282,7 @@ function Button({
|
|
|
1260
1282
|
textOffsetX,
|
|
1261
1283
|
textOffsetY,
|
|
1262
1284
|
textAlign = "center",
|
|
1285
|
+
children,
|
|
1263
1286
|
anchor,
|
|
1264
1287
|
pivot = anchor,
|
|
1265
1288
|
interactive,
|
|
@@ -1274,6 +1297,20 @@ function Button({
|
|
|
1274
1297
|
}) {
|
|
1275
1298
|
const [hovered, setHovered] = (0, import_react4.useState)(false);
|
|
1276
1299
|
const [pressed, setPressed] = (0, import_react4.useState)(false);
|
|
1300
|
+
(0, import_react4.useEffect)(() => {
|
|
1301
|
+
if (!pressed) {
|
|
1302
|
+
return;
|
|
1303
|
+
}
|
|
1304
|
+
const release = () => setPressed(false);
|
|
1305
|
+
const removeMouseUp = addEventListener("mouseup", release);
|
|
1306
|
+
const removeTouchEnd = addEventListener("touchend", release);
|
|
1307
|
+
const removeTouchCancel = addEventListener("touchcancel", release);
|
|
1308
|
+
return () => {
|
|
1309
|
+
removeMouseUp();
|
|
1310
|
+
removeTouchEnd();
|
|
1311
|
+
removeTouchCancel();
|
|
1312
|
+
};
|
|
1313
|
+
}, [pressed]);
|
|
1277
1314
|
(0, import_react4.useEffect)(() => {
|
|
1278
1315
|
if (disabled) {
|
|
1279
1316
|
setHovered(false);
|
|
@@ -1323,18 +1360,21 @@ function Button({
|
|
|
1323
1360
|
setPressed(false);
|
|
1324
1361
|
}),
|
|
1325
1362
|
onClick: (event) => event.stopPropagation(),
|
|
1326
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime.
|
|
1327
|
-
|
|
1328
|
-
|
|
1329
|
-
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1363
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime.jsxs)("sprite", { ...spriteProps, src: resolveControlStateValue(src, state), cursor: "pointer", children: [
|
|
1364
|
+
text !== void 0 ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1365
|
+
"text",
|
|
1366
|
+
{
|
|
1367
|
+
...resolvedTextStyle,
|
|
1368
|
+
text,
|
|
1369
|
+
x: textOffsetX,
|
|
1370
|
+
y: textOffsetY,
|
|
1371
|
+
interactive: false,
|
|
1372
|
+
anchor: textAnchor,
|
|
1373
|
+
pivot: textAnchor
|
|
1374
|
+
}
|
|
1375
|
+
) : void 0,
|
|
1376
|
+
children
|
|
1377
|
+
] })
|
|
1338
1378
|
}
|
|
1339
1379
|
);
|
|
1340
1380
|
}
|
|
@@ -1372,8 +1412,343 @@ function Checkbox({
|
|
|
1372
1412
|
);
|
|
1373
1413
|
}
|
|
1374
1414
|
|
|
1375
|
-
// src/components/
|
|
1415
|
+
// src/components/input.tsx
|
|
1376
1416
|
var import_react6 = require("react");
|
|
1417
|
+
var Input = (0, import_react6.forwardRef)(function Input2({
|
|
1418
|
+
value,
|
|
1419
|
+
defaultValue = "",
|
|
1420
|
+
placeholder = "",
|
|
1421
|
+
disabled = false,
|
|
1422
|
+
readOnly = false,
|
|
1423
|
+
autoFocus = false,
|
|
1424
|
+
width,
|
|
1425
|
+
height,
|
|
1426
|
+
paddingX = 0,
|
|
1427
|
+
textStyle,
|
|
1428
|
+
placeholderStyle,
|
|
1429
|
+
caret,
|
|
1430
|
+
background,
|
|
1431
|
+
onInput,
|
|
1432
|
+
onChange,
|
|
1433
|
+
onFocus,
|
|
1434
|
+
onBlur,
|
|
1435
|
+
onCompositionStart,
|
|
1436
|
+
onCompositionUpdate,
|
|
1437
|
+
onCompositionEnd,
|
|
1438
|
+
interactive,
|
|
1439
|
+
cursor = "text",
|
|
1440
|
+
onMouseEnter,
|
|
1441
|
+
onMouseLeave,
|
|
1442
|
+
onMouseDown,
|
|
1443
|
+
onMouseUp,
|
|
1444
|
+
onTouchStart,
|
|
1445
|
+
onTouchEnd,
|
|
1446
|
+
onTouchCancel,
|
|
1447
|
+
...nodeProps
|
|
1448
|
+
}, ref) {
|
|
1449
|
+
const editableRef = (0, import_react6.useRef)(null);
|
|
1450
|
+
const initialValueRef = (0, import_react6.useRef)(value ?? defaultValue);
|
|
1451
|
+
const initialValue = initialValueRef.current;
|
|
1452
|
+
const stateRef = (0, import_react6.useRef)({
|
|
1453
|
+
value: initialValue,
|
|
1454
|
+
isComposing: false,
|
|
1455
|
+
compositionText: ""
|
|
1456
|
+
});
|
|
1457
|
+
const [state, setState] = (0, import_react6.useState)(stateRef.current);
|
|
1458
|
+
const [focused, setFocused] = (0, import_react6.useState)(false);
|
|
1459
|
+
const [hovered, setHovered] = (0, import_react6.useState)(false);
|
|
1460
|
+
const [pressed, setPressed] = (0, import_react6.useState)(false);
|
|
1461
|
+
const [caretPosition, setCaretPosition] = (0, import_react6.useState)();
|
|
1462
|
+
const [caretVisible, setCaretVisible] = (0, import_react6.useState)(true);
|
|
1463
|
+
const shouldAutoFocusRef = (0, import_react6.useRef)(autoFocus && !disabled);
|
|
1464
|
+
const viewportWidth = Math.max(0, Math.round(width));
|
|
1465
|
+
const viewportHeight = Math.max(0, Math.round(height));
|
|
1466
|
+
const contentWidth = Math.max(0, viewportWidth - paddingX * 2);
|
|
1467
|
+
const { width: caretWidth, height: configuredCaretHeight, blinkInterval, ...caretSpriteProps } = caret;
|
|
1468
|
+
const caretHeight = configuredCaretHeight ?? textStyle.fontSize ?? viewportHeight;
|
|
1469
|
+
const backgroundStyle = background && "idle" in background ? disabled ? background.disabled ?? background.idle : readOnly ? background.readOnly ?? background.idle : pressed ? background.press ?? background.idle : focused ? background.focused ?? background.idle : hovered ? background.hover ?? background.idle : background.idle : background;
|
|
1470
|
+
const displayValue = state.value + state.compositionText;
|
|
1471
|
+
const updateState = (0, import_react6.useCallback)((nextState) => {
|
|
1472
|
+
const previousState = stateRef.current;
|
|
1473
|
+
if (previousState.value === nextState.value && previousState.isComposing === nextState.isComposing && previousState.compositionText === nextState.compositionText) {
|
|
1474
|
+
return;
|
|
1475
|
+
}
|
|
1476
|
+
const displayValueChanged = previousState.value + previousState.compositionText !== nextState.value + nextState.compositionText;
|
|
1477
|
+
stateRef.current = nextState;
|
|
1478
|
+
setState(nextState);
|
|
1479
|
+
if (displayValueChanged) {
|
|
1480
|
+
setCaretPosition(void 0);
|
|
1481
|
+
}
|
|
1482
|
+
setCaretVisible(true);
|
|
1483
|
+
}, []);
|
|
1484
|
+
const handleInput = (0, import_react6.useCallback)(
|
|
1485
|
+
(event) => {
|
|
1486
|
+
updateState(event.state);
|
|
1487
|
+
onInput?.(event.state);
|
|
1488
|
+
},
|
|
1489
|
+
[onInput, updateState]
|
|
1490
|
+
);
|
|
1491
|
+
const handleChange = (0, import_react6.useCallback)(
|
|
1492
|
+
(event) => {
|
|
1493
|
+
updateState(event.state);
|
|
1494
|
+
onChange?.(event.state, event.source);
|
|
1495
|
+
},
|
|
1496
|
+
[onChange, updateState]
|
|
1497
|
+
);
|
|
1498
|
+
const handleFocus = (0, import_react6.useCallback)(
|
|
1499
|
+
(event) => {
|
|
1500
|
+
updateState(event.state);
|
|
1501
|
+
setFocused(true);
|
|
1502
|
+
onFocus?.(event.state);
|
|
1503
|
+
},
|
|
1504
|
+
[onFocus, updateState]
|
|
1505
|
+
);
|
|
1506
|
+
const handleBlur = (0, import_react6.useCallback)(
|
|
1507
|
+
(event) => {
|
|
1508
|
+
updateState(event.state);
|
|
1509
|
+
setFocused(false);
|
|
1510
|
+
onBlur?.(event.state);
|
|
1511
|
+
},
|
|
1512
|
+
[onBlur, updateState]
|
|
1513
|
+
);
|
|
1514
|
+
const handleCompositionStart = (0, import_react6.useCallback)(
|
|
1515
|
+
(event) => {
|
|
1516
|
+
updateState(event.state);
|
|
1517
|
+
onCompositionStart?.(event.state);
|
|
1518
|
+
},
|
|
1519
|
+
[onCompositionStart, updateState]
|
|
1520
|
+
);
|
|
1521
|
+
const handleCompositionUpdate = (0, import_react6.useCallback)(
|
|
1522
|
+
(event) => {
|
|
1523
|
+
updateState(event.state);
|
|
1524
|
+
onCompositionUpdate?.(event.state);
|
|
1525
|
+
},
|
|
1526
|
+
[onCompositionUpdate, updateState]
|
|
1527
|
+
);
|
|
1528
|
+
const handleCompositionEnd = (0, import_react6.useCallback)(
|
|
1529
|
+
(event) => {
|
|
1530
|
+
updateState(event.state);
|
|
1531
|
+
onCompositionEnd?.(event.state);
|
|
1532
|
+
},
|
|
1533
|
+
[onCompositionEnd, updateState]
|
|
1534
|
+
);
|
|
1535
|
+
const handleTextLayout = (0, import_react6.useCallback)((event) => {
|
|
1536
|
+
if (event.text === stateRef.current.value + stateRef.current.compositionText) {
|
|
1537
|
+
setCaretPosition(event.endCursorPosition);
|
|
1538
|
+
}
|
|
1539
|
+
}, []);
|
|
1540
|
+
(0, import_react6.useImperativeHandle)(
|
|
1541
|
+
ref,
|
|
1542
|
+
() => ({
|
|
1543
|
+
focus: () => {
|
|
1544
|
+
if (editableRef.current) {
|
|
1545
|
+
focusEditable(editableRef.current.nodeId);
|
|
1546
|
+
}
|
|
1547
|
+
},
|
|
1548
|
+
blur: () => {
|
|
1549
|
+
if (editableRef.current) {
|
|
1550
|
+
blurEditable(editableRef.current.nodeId);
|
|
1551
|
+
}
|
|
1552
|
+
},
|
|
1553
|
+
getState: () => stateRef.current
|
|
1554
|
+
}),
|
|
1555
|
+
[]
|
|
1556
|
+
);
|
|
1557
|
+
(0, import_react6.useEffect)(() => {
|
|
1558
|
+
if (value === void 0 || value === stateRef.current.value) {
|
|
1559
|
+
return;
|
|
1560
|
+
}
|
|
1561
|
+
editableRef.current?.executeCommand({ subCommand: "setValue", value });
|
|
1562
|
+
const nextState = editableRef.current?.executeCommand({ subCommand: "getState" });
|
|
1563
|
+
if (nextState) {
|
|
1564
|
+
updateState(nextState);
|
|
1565
|
+
}
|
|
1566
|
+
}, [updateState, value]);
|
|
1567
|
+
(0, import_react6.useEffect)(() => {
|
|
1568
|
+
if (shouldAutoFocusRef.current && editableRef.current) {
|
|
1569
|
+
focusEditable(editableRef.current.nodeId);
|
|
1570
|
+
}
|
|
1571
|
+
}, []);
|
|
1572
|
+
(0, import_react6.useEffect)(() => {
|
|
1573
|
+
if (!pressed) {
|
|
1574
|
+
return;
|
|
1575
|
+
}
|
|
1576
|
+
const release = () => setPressed(false);
|
|
1577
|
+
const removeMouseUp = addEventListener("mouseup", release);
|
|
1578
|
+
const removeTouchEnd = addEventListener("touchend", release);
|
|
1579
|
+
const removeTouchCancel = addEventListener("touchcancel", release);
|
|
1580
|
+
return () => {
|
|
1581
|
+
removeMouseUp();
|
|
1582
|
+
removeTouchEnd();
|
|
1583
|
+
removeTouchCancel();
|
|
1584
|
+
};
|
|
1585
|
+
}, [pressed]);
|
|
1586
|
+
(0, import_react6.useEffect)(() => {
|
|
1587
|
+
if (disabled) {
|
|
1588
|
+
setHovered(false);
|
|
1589
|
+
setPressed(false);
|
|
1590
|
+
}
|
|
1591
|
+
}, [disabled]);
|
|
1592
|
+
(0, import_react6.useEffect)(() => {
|
|
1593
|
+
if (!focused) {
|
|
1594
|
+
setCaretVisible(false);
|
|
1595
|
+
return;
|
|
1596
|
+
}
|
|
1597
|
+
const expectedDisplayValue = displayValue;
|
|
1598
|
+
setCaretVisible(true);
|
|
1599
|
+
const timer = setInterval(() => {
|
|
1600
|
+
if (stateRef.current.value + stateRef.current.compositionText === expectedDisplayValue) {
|
|
1601
|
+
setCaretVisible((visible) => !visible);
|
|
1602
|
+
}
|
|
1603
|
+
}, blinkInterval ?? 500);
|
|
1604
|
+
return () => clearInterval(timer);
|
|
1605
|
+
}, [blinkInterval, displayValue, focused]);
|
|
1606
|
+
(0, import_react6.useEffect)(() => {
|
|
1607
|
+
if (!focused || !caretPosition) {
|
|
1608
|
+
return;
|
|
1609
|
+
}
|
|
1610
|
+
editableRef.current?.executeCommand({
|
|
1611
|
+
subCommand: "setCaretRect",
|
|
1612
|
+
x: paddingX + caretPosition[0],
|
|
1613
|
+
y: (viewportHeight - caretHeight) / 2,
|
|
1614
|
+
width: caretWidth,
|
|
1615
|
+
height: caretHeight
|
|
1616
|
+
});
|
|
1617
|
+
}, [caretHeight, caretPosition, caretWidth, focused, paddingX, viewportHeight]);
|
|
1618
|
+
const caretX = caretPosition?.[0] ?? 0;
|
|
1619
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsxs)(
|
|
1620
|
+
"editable",
|
|
1621
|
+
{
|
|
1622
|
+
...nodeProps,
|
|
1623
|
+
ref: editableRef,
|
|
1624
|
+
value: initialValue,
|
|
1625
|
+
disabled,
|
|
1626
|
+
readOnly,
|
|
1627
|
+
interactive: disabled ? false : interactive,
|
|
1628
|
+
cursor,
|
|
1629
|
+
onMouseEnter: mergeEvent(onMouseEnter, () => setHovered(true)),
|
|
1630
|
+
onMouseLeave: mergeEvent(onMouseLeave, () => {
|
|
1631
|
+
setHovered(false);
|
|
1632
|
+
setPressed(false);
|
|
1633
|
+
}),
|
|
1634
|
+
onMouseDown: mergeEvent(onMouseDown, () => setPressed(true)),
|
|
1635
|
+
onMouseUp: mergeEvent(onMouseUp, () => {
|
|
1636
|
+
setPressed(false);
|
|
1637
|
+
setHovered(true);
|
|
1638
|
+
}),
|
|
1639
|
+
onTouchStart: mergeEvent(onTouchStart, () => setPressed(true)),
|
|
1640
|
+
onTouchEnd: mergeEvent(onTouchEnd, () => {
|
|
1641
|
+
setPressed(false);
|
|
1642
|
+
setHovered(true);
|
|
1643
|
+
}),
|
|
1644
|
+
onTouchCancel: mergeEvent(onTouchCancel, () => {
|
|
1645
|
+
setHovered(false);
|
|
1646
|
+
setPressed(false);
|
|
1647
|
+
}),
|
|
1648
|
+
onInput: handleInput,
|
|
1649
|
+
onChange: handleChange,
|
|
1650
|
+
onFocus: handleFocus,
|
|
1651
|
+
onBlur: handleBlur,
|
|
1652
|
+
onCompositionStart: handleCompositionStart,
|
|
1653
|
+
onCompositionUpdate: handleCompositionUpdate,
|
|
1654
|
+
onCompositionEnd: handleCompositionEnd,
|
|
1655
|
+
children: [
|
|
1656
|
+
backgroundStyle ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)("sprite", { ...backgroundStyle, targetWidth: viewportWidth, targetHeight: viewportHeight, interactive: false }) : null,
|
|
1657
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsxs)("clip", { x: paddingX, width: contentWidth, height: viewportHeight, interactive: false, children: [
|
|
1658
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1659
|
+
"text",
|
|
1660
|
+
{
|
|
1661
|
+
...textStyle,
|
|
1662
|
+
text: displayValue,
|
|
1663
|
+
parseMarkup: false,
|
|
1664
|
+
printMode: "instant",
|
|
1665
|
+
anchor: [0, 0.5],
|
|
1666
|
+
pivot: [0, 0.5],
|
|
1667
|
+
interactive: false,
|
|
1668
|
+
onTextLayout: handleTextLayout
|
|
1669
|
+
}
|
|
1670
|
+
),
|
|
1671
|
+
state.value.length === 0 && state.compositionText.length === 0 && placeholder ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1672
|
+
"text",
|
|
1673
|
+
{
|
|
1674
|
+
...textStyle,
|
|
1675
|
+
...placeholderStyle,
|
|
1676
|
+
text: placeholder,
|
|
1677
|
+
parseMarkup: false,
|
|
1678
|
+
printMode: "instant",
|
|
1679
|
+
anchor: [0, 0.5],
|
|
1680
|
+
pivot: [0, 0.5],
|
|
1681
|
+
interactive: false
|
|
1682
|
+
}
|
|
1683
|
+
) : null,
|
|
1684
|
+
/* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1685
|
+
"sprite",
|
|
1686
|
+
{
|
|
1687
|
+
...caretSpriteProps,
|
|
1688
|
+
x: caretX,
|
|
1689
|
+
y: (viewportHeight - caretHeight) / 2,
|
|
1690
|
+
mode: "nineslice",
|
|
1691
|
+
bounds: [0, 0, 0, 0],
|
|
1692
|
+
targetWidth: caretWidth,
|
|
1693
|
+
targetHeight: caretHeight,
|
|
1694
|
+
visible: focused && caretVisible && caretPosition !== void 0,
|
|
1695
|
+
interactive: false
|
|
1696
|
+
}
|
|
1697
|
+
)
|
|
1698
|
+
] })
|
|
1699
|
+
]
|
|
1700
|
+
}
|
|
1701
|
+
);
|
|
1702
|
+
});
|
|
1703
|
+
|
|
1704
|
+
// src/components/radio.tsx
|
|
1705
|
+
var import_react7 = require("react");
|
|
1706
|
+
var RadioGroupContext = (0, import_react7.createContext)(null);
|
|
1707
|
+
function RadioGroup({ value, defaultValue, onValueChange, children, ...containerProps }) {
|
|
1708
|
+
const [internalValue, setInternalValue] = (0, import_react7.useState)(defaultValue);
|
|
1709
|
+
const currentValue = value ?? internalValue;
|
|
1710
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1711
|
+
RadioGroupContext.Provider,
|
|
1712
|
+
{
|
|
1713
|
+
value: {
|
|
1714
|
+
value: currentValue,
|
|
1715
|
+
select: (nextValue) => {
|
|
1716
|
+
if (nextValue === currentValue) {
|
|
1717
|
+
return;
|
|
1718
|
+
}
|
|
1719
|
+
if (value === void 0) {
|
|
1720
|
+
setInternalValue(nextValue);
|
|
1721
|
+
}
|
|
1722
|
+
onValueChange?.(nextValue);
|
|
1723
|
+
}
|
|
1724
|
+
},
|
|
1725
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)("container", { ...containerProps, children })
|
|
1726
|
+
}
|
|
1727
|
+
);
|
|
1728
|
+
}
|
|
1729
|
+
function Radio({ value, uncheckedSprite, checkedSprite, onPress, ...buttonProps }) {
|
|
1730
|
+
const group = (0, import_react7.useContext)(RadioGroupContext);
|
|
1731
|
+
if (!group) {
|
|
1732
|
+
throw new Error("Radio must be rendered inside a RadioGroup.");
|
|
1733
|
+
}
|
|
1734
|
+
const checked = group.value === value;
|
|
1735
|
+
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1736
|
+
Button,
|
|
1737
|
+
{
|
|
1738
|
+
...buttonProps,
|
|
1739
|
+
sprite: checked ? checkedSprite : uncheckedSprite,
|
|
1740
|
+
onPress: (event) => {
|
|
1741
|
+
onPress?.(event);
|
|
1742
|
+
if (!event.defaultPrevented) {
|
|
1743
|
+
group.select(value);
|
|
1744
|
+
}
|
|
1745
|
+
}
|
|
1746
|
+
}
|
|
1747
|
+
);
|
|
1748
|
+
}
|
|
1749
|
+
|
|
1750
|
+
// src/components/select.tsx
|
|
1751
|
+
var import_react8 = require("react");
|
|
1377
1752
|
function Select({
|
|
1378
1753
|
value,
|
|
1379
1754
|
defaultValue,
|
|
@@ -1392,8 +1767,8 @@ function Select({
|
|
|
1392
1767
|
pivot = anchor,
|
|
1393
1768
|
...containerProps
|
|
1394
1769
|
}) {
|
|
1395
|
-
const [internalValue, setInternalValue] = (0,
|
|
1396
|
-
const [open, setOpen] = (0,
|
|
1770
|
+
const [internalValue, setInternalValue] = (0, import_react8.useState)(defaultValue);
|
|
1771
|
+
const [open, setOpen] = (0, import_react8.useState)(false);
|
|
1397
1772
|
const currentValue = value ?? internalValue;
|
|
1398
1773
|
const currentOption = options.find((item) => item.value === currentValue);
|
|
1399
1774
|
const { paddingX = 0, paddingY = 0, gap = 0, offsetX = 0, offsetY = 0, ...listSprite } = list;
|
|
@@ -1425,43 +1800,57 @@ function Select({
|
|
|
1425
1800
|
}
|
|
1426
1801
|
}
|
|
1427
1802
|
),
|
|
1428
|
-
open && !disabled ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1429
|
-
|
|
1803
|
+
open && !disabled ? /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1804
|
+
"sprite",
|
|
1430
1805
|
{
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
|
|
1434
|
-
|
|
1435
|
-
|
|
1436
|
-
|
|
1437
|
-
|
|
1438
|
-
|
|
1439
|
-
|
|
1440
|
-
|
|
1441
|
-
|
|
1442
|
-
|
|
1443
|
-
|
|
1444
|
-
|
|
1445
|
-
|
|
1446
|
-
|
|
1447
|
-
|
|
1448
|
-
|
|
1449
|
-
|
|
1450
|
-
|
|
1806
|
+
...listSprite,
|
|
1807
|
+
excludeFromLayout: true,
|
|
1808
|
+
targetHeight: listHeight,
|
|
1809
|
+
x: offsetX,
|
|
1810
|
+
y: (trigger.targetHeight ?? 0) + offsetY,
|
|
1811
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)("vbox", { x: paddingX, y: paddingY, gap, children: options.map((item) => /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1812
|
+
Button,
|
|
1813
|
+
{
|
|
1814
|
+
sprite: option,
|
|
1815
|
+
lockOn: item.value === currentValue ? "press" : void 0,
|
|
1816
|
+
text: item.text,
|
|
1817
|
+
textStyle,
|
|
1818
|
+
textOffsetX,
|
|
1819
|
+
textOffsetY,
|
|
1820
|
+
textAlign,
|
|
1821
|
+
onPress: (event) => {
|
|
1822
|
+
if (event.defaultPrevented) {
|
|
1823
|
+
return;
|
|
1824
|
+
}
|
|
1825
|
+
if (value === void 0) {
|
|
1826
|
+
setInternalValue(item.value);
|
|
1827
|
+
}
|
|
1828
|
+
onValueChange?.(item.value, item);
|
|
1829
|
+
setOpen(false);
|
|
1830
|
+
}
|
|
1831
|
+
},
|
|
1832
|
+
item.value
|
|
1833
|
+
)) })
|
|
1834
|
+
}
|
|
1835
|
+
) : void 0
|
|
1451
1836
|
]
|
|
1452
1837
|
}
|
|
1453
1838
|
);
|
|
1454
1839
|
}
|
|
1455
1840
|
|
|
1456
1841
|
// src/components/slider.tsx
|
|
1457
|
-
var
|
|
1842
|
+
var import_react9 = require("react");
|
|
1458
1843
|
function clampValue(value) {
|
|
1844
|
+
if (Number.isNaN(value)) {
|
|
1845
|
+
return 0;
|
|
1846
|
+
}
|
|
1459
1847
|
return Math.max(0, Math.min(1, value));
|
|
1460
1848
|
}
|
|
1461
1849
|
function Slider({
|
|
1462
1850
|
value,
|
|
1463
1851
|
defaultValue = 0,
|
|
1464
1852
|
onValueChange,
|
|
1853
|
+
onValueCommit,
|
|
1465
1854
|
onPress,
|
|
1466
1855
|
disabled = false,
|
|
1467
1856
|
track,
|
|
@@ -1480,101 +1869,145 @@ function Slider({
|
|
|
1480
1869
|
onTouchCancel,
|
|
1481
1870
|
...containerProps
|
|
1482
1871
|
}) {
|
|
1483
|
-
const [internalValue, setInternalValue] = (0,
|
|
1484
|
-
const [
|
|
1485
|
-
const [dragging, setDragging] = (0, import_react7.useState)(false);
|
|
1486
|
-
const draggingRef = (0, import_react7.useRef)(false);
|
|
1872
|
+
const [internalValue, setInternalValue] = (0, import_react9.useState)(() => clampValue(defaultValue));
|
|
1873
|
+
const [dragging, setDragging] = (0, import_react9.useState)(false);
|
|
1487
1874
|
const currentValue = clampValue(value ?? internalValue);
|
|
1875
|
+
const currentValueRef = (0, import_react9.useRef)(currentValue);
|
|
1876
|
+
currentValueRef.current = currentValue;
|
|
1877
|
+
const dragStateRef = (0, import_react9.useRef)(null);
|
|
1488
1878
|
const distance = Math.max(0, track.targetWidth - thumb.targetWidth);
|
|
1489
|
-
const
|
|
1490
|
-
|
|
1491
|
-
|
|
1492
|
-
const updateValue = (event) => {
|
|
1493
|
-
event.stopPropagation();
|
|
1494
|
-
if (distance === 0) {
|
|
1495
|
-
return;
|
|
1496
|
-
}
|
|
1497
|
-
const nextValue = clampValue((event.offsetX - thumb.targetWidth / 2) / distance);
|
|
1879
|
+
const setSliderValue = (0, import_react9.useCallback)((nextValue) => {
|
|
1880
|
+
const clampedValue = clampValue(nextValue);
|
|
1881
|
+
currentValueRef.current = clampedValue;
|
|
1498
1882
|
if (value === void 0) {
|
|
1499
|
-
setInternalValue(
|
|
1883
|
+
setInternalValue(clampedValue);
|
|
1500
1884
|
}
|
|
1501
|
-
onValueChange?.(
|
|
1502
|
-
};
|
|
1503
|
-
const endDragging = (0,
|
|
1504
|
-
|
|
1885
|
+
onValueChange?.(clampedValue);
|
|
1886
|
+
}, [onValueChange, value]);
|
|
1887
|
+
const endDragging = (0, import_react9.useCallback)((commit) => {
|
|
1888
|
+
if (dragStateRef.current === null) {
|
|
1889
|
+
return;
|
|
1890
|
+
}
|
|
1891
|
+
dragStateRef.current = null;
|
|
1505
1892
|
setDragging(false);
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1893
|
+
if (commit) {
|
|
1894
|
+
onValueCommit?.(currentValueRef.current);
|
|
1895
|
+
}
|
|
1896
|
+
}, [onValueCommit]);
|
|
1897
|
+
(0, import_react9.useEffect)(() => {
|
|
1898
|
+
const handleMouseUp = () => endDragging(true);
|
|
1899
|
+
const handleTouchEnd = (event) => {
|
|
1900
|
+
if (dragStateRef.current?.touchIdentifier === event.identifier) {
|
|
1901
|
+
endDragging(true);
|
|
1902
|
+
}
|
|
1903
|
+
};
|
|
1904
|
+
const handleTouchCancel2 = (event) => {
|
|
1905
|
+
if (dragStateRef.current?.touchIdentifier === event.identifier) {
|
|
1906
|
+
endDragging(false);
|
|
1511
1907
|
}
|
|
1512
1908
|
};
|
|
1513
|
-
const removeMouseUp = addEventListener("mouseup",
|
|
1514
|
-
const removeTouchEnd = addEventListener("touchend",
|
|
1515
|
-
const removeTouchCancel = addEventListener("touchcancel",
|
|
1909
|
+
const removeMouseUp = addEventListener("mouseup", handleMouseUp);
|
|
1910
|
+
const removeTouchEnd = addEventListener("touchend", handleTouchEnd);
|
|
1911
|
+
const removeTouchCancel = addEventListener("touchcancel", handleTouchCancel2);
|
|
1516
1912
|
return () => {
|
|
1517
1913
|
removeMouseUp();
|
|
1518
1914
|
removeTouchEnd();
|
|
1519
1915
|
removeTouchCancel();
|
|
1520
1916
|
};
|
|
1521
1917
|
}, [endDragging]);
|
|
1522
|
-
(0,
|
|
1918
|
+
(0, import_react9.useEffect)(() => {
|
|
1523
1919
|
if (disabled) {
|
|
1524
|
-
endDragging();
|
|
1525
|
-
setHovered(false);
|
|
1920
|
+
endDragging(false);
|
|
1526
1921
|
}
|
|
1527
1922
|
}, [disabled, endDragging]);
|
|
1528
1923
|
const startDragging = (event) => {
|
|
1924
|
+
event.stopPropagation();
|
|
1925
|
+
if (dragStateRef.current !== null) {
|
|
1926
|
+
return;
|
|
1927
|
+
}
|
|
1928
|
+
const thumbPosition = currentValueRef.current * distance;
|
|
1929
|
+
dragStateRef.current = {
|
|
1930
|
+
startPosition: event.offsetX,
|
|
1931
|
+
startValue: currentValueRef.current,
|
|
1932
|
+
touchIdentifier: "identifier" in event ? event.identifier : void 0,
|
|
1933
|
+
startedOnThumb: event.offsetX >= thumbPosition && event.offsetX <= thumbPosition + thumb.targetWidth,
|
|
1934
|
+
moved: false
|
|
1935
|
+
};
|
|
1936
|
+
setDragging(true);
|
|
1937
|
+
};
|
|
1938
|
+
const moveDragging = (event) => {
|
|
1939
|
+
const dragState = dragStateRef.current;
|
|
1940
|
+
if (dragState === null || "identifier" in event && dragState.touchIdentifier !== event.identifier || distance === 0) {
|
|
1941
|
+
return;
|
|
1942
|
+
}
|
|
1943
|
+
event.stopPropagation();
|
|
1944
|
+
const delta = event.offsetX - dragState.startPosition;
|
|
1945
|
+
if (delta !== 0) {
|
|
1946
|
+
dragState.moved = true;
|
|
1947
|
+
}
|
|
1948
|
+
setSliderValue(dragState.startValue + delta / distance);
|
|
1949
|
+
};
|
|
1950
|
+
const handlePress = (event) => {
|
|
1951
|
+
const dragState = dragStateRef.current;
|
|
1952
|
+
if (dragState === null || "identifier" in event && dragState.touchIdentifier !== event.identifier) {
|
|
1953
|
+
return;
|
|
1954
|
+
}
|
|
1529
1955
|
onPress?.(event);
|
|
1530
1956
|
if (event.defaultPrevented) {
|
|
1957
|
+
endDragging(false);
|
|
1531
1958
|
return;
|
|
1532
1959
|
}
|
|
1533
|
-
|
|
1534
|
-
|
|
1535
|
-
|
|
1960
|
+
if (!dragState.moved && !dragState.startedOnThumb && distance > 0) {
|
|
1961
|
+
setSliderValue((event.offsetX - thumb.targetWidth / 2) / distance);
|
|
1962
|
+
}
|
|
1963
|
+
endDragging(true);
|
|
1964
|
+
};
|
|
1965
|
+
const handleTouchCancel = (event) => {
|
|
1966
|
+
if (dragStateRef.current?.touchIdentifier === event.identifier) {
|
|
1967
|
+
endDragging(false);
|
|
1968
|
+
}
|
|
1536
1969
|
};
|
|
1537
1970
|
return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1538
|
-
|
|
1971
|
+
Button,
|
|
1539
1972
|
{
|
|
1540
1973
|
...containerProps,
|
|
1541
1974
|
anchor,
|
|
1542
1975
|
pivot,
|
|
1543
|
-
interactive
|
|
1544
|
-
|
|
1545
|
-
|
|
1546
|
-
|
|
1547
|
-
|
|
1548
|
-
|
|
1549
|
-
|
|
1550
|
-
}
|
|
1976
|
+
interactive,
|
|
1977
|
+
disabled,
|
|
1978
|
+
lockOn: dragging ? "press" : void 0,
|
|
1979
|
+
sprite: {
|
|
1980
|
+
...track,
|
|
1981
|
+
pivot: [0, 0.5],
|
|
1982
|
+
y: (track.targetHeight ?? 0) / 2
|
|
1983
|
+
},
|
|
1984
|
+
onPress: handlePress,
|
|
1985
|
+
onMouseEnter,
|
|
1986
|
+
onMouseLeave,
|
|
1551
1987
|
onMouseDown: mergeEvent(onMouseDown, startDragging),
|
|
1552
|
-
onMouseUp
|
|
1553
|
-
onMouseMove: mergeEvent(onMouseMove,
|
|
1554
|
-
if (draggingRef.current) {
|
|
1555
|
-
updateValue(event);
|
|
1556
|
-
}
|
|
1557
|
-
}),
|
|
1988
|
+
onMouseUp,
|
|
1989
|
+
onMouseMove: mergeEvent(onMouseMove, moveDragging),
|
|
1558
1990
|
onTouchStart: mergeEvent(onTouchStart, startDragging),
|
|
1559
|
-
onTouchMove: mergeEvent(onTouchMove,
|
|
1560
|
-
|
|
1561
|
-
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
onTouchEnd: mergeEvent(onTouchEnd, endDragging),
|
|
1565
|
-
onTouchCancel: mergeEvent(onTouchCancel, endDragging),
|
|
1566
|
-
onClick: (event) => event.stopPropagation(),
|
|
1567
|
-
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)("sprite", { ...trackProps, src: resolveControlStateValue(trackSrc, state), cursor: "pointer", children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1568
|
-
"sprite",
|
|
1991
|
+
onTouchMove: mergeEvent(onTouchMove, moveDragging),
|
|
1992
|
+
onTouchEnd,
|
|
1993
|
+
onTouchCancel: mergeEvent(onTouchCancel, handleTouchCancel),
|
|
1994
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime.jsx)(
|
|
1995
|
+
Button,
|
|
1569
1996
|
{
|
|
1570
|
-
|
|
1571
|
-
|
|
1997
|
+
sprite: {
|
|
1998
|
+
...thumb,
|
|
1999
|
+
anchor: [0, 0.5],
|
|
2000
|
+
pivot: [0, 0.5],
|
|
2001
|
+
x: 0,
|
|
2002
|
+
interactive: false
|
|
2003
|
+
},
|
|
2004
|
+
lockOn: dragging ? "press" : void 0,
|
|
2005
|
+
x: currentValue * distance,
|
|
1572
2006
|
anchor: [0, 0.5],
|
|
1573
2007
|
pivot: [0, 0.5],
|
|
1574
|
-
x: currentValue * distance,
|
|
1575
2008
|
interactive: false
|
|
1576
2009
|
}
|
|
1577
|
-
)
|
|
2010
|
+
)
|
|
1578
2011
|
}
|
|
1579
2012
|
);
|
|
1580
2013
|
}
|
|
@@ -1944,6 +2377,7 @@ var debugSessionController = {
|
|
|
1944
2377
|
throw new Error("Page switching is not supported by the app state adapter");
|
|
1945
2378
|
}
|
|
1946
2379
|
await appStateAdapter.switchPage(routeName, params);
|
|
2380
|
+
await syncCurrentExecutionCursor();
|
|
1947
2381
|
return;
|
|
1948
2382
|
}
|
|
1949
2383
|
if (navigator.hasOverlay(routeName)) {
|
|
@@ -2534,7 +2968,7 @@ function useFadeOut(outTime, pause = false, onFinished) {
|
|
|
2534
2968
|
|
|
2535
2969
|
// src/hooks/useScrollView.ts
|
|
2536
2970
|
var import_core = require("@react-spring/core");
|
|
2537
|
-
var
|
|
2971
|
+
var import_react10 = require("react");
|
|
2538
2972
|
function clamp(value, min, max) {
|
|
2539
2973
|
return Math.max(min, Math.min(max, value));
|
|
2540
2974
|
}
|
|
@@ -2554,21 +2988,21 @@ function useScrollView({
|
|
|
2554
2988
|
initialPosition = "start",
|
|
2555
2989
|
wheelStep = 72
|
|
2556
2990
|
}) {
|
|
2557
|
-
const [contentHeight, setContentHeight] = (0,
|
|
2558
|
-
const [hasContentLayout, setHasContentLayout] = (0,
|
|
2559
|
-
const scrollTargetRef = (0,
|
|
2560
|
-
const didSetInitialPositionRef = (0,
|
|
2561
|
-
const touchDraggingRef = (0,
|
|
2562
|
-
const touchStartYRef = (0,
|
|
2563
|
-
const touchStartOffsetRef = (0,
|
|
2991
|
+
const [contentHeight, setContentHeight] = (0, import_react10.useState)(0);
|
|
2992
|
+
const [hasContentLayout, setHasContentLayout] = (0, import_react10.useState)(false);
|
|
2993
|
+
const scrollTargetRef = (0, import_react10.useRef)(0);
|
|
2994
|
+
const didSetInitialPositionRef = (0, import_react10.useRef)(false);
|
|
2995
|
+
const touchDraggingRef = (0, import_react10.useRef)(false);
|
|
2996
|
+
const touchStartYRef = (0, import_react10.useRef)(0);
|
|
2997
|
+
const touchStartOffsetRef = (0, import_react10.useRef)(0);
|
|
2564
2998
|
const scrollOffset = (0, import_core.useSpringValue)(0, {
|
|
2565
2999
|
config: {
|
|
2566
3000
|
tension: 320,
|
|
2567
3001
|
friction: 32
|
|
2568
3002
|
}
|
|
2569
3003
|
});
|
|
2570
|
-
const maxScroll = (0,
|
|
2571
|
-
const scrollTo = (0,
|
|
3004
|
+
const maxScroll = (0, import_react10.useMemo)(() => Math.max(0, contentHeight - viewportHeight), [contentHeight, viewportHeight]);
|
|
3005
|
+
const scrollTo = (0, import_react10.useCallback)(
|
|
2572
3006
|
(nextOffset, immediate = false) => {
|
|
2573
3007
|
const offset = clamp(nextOffset, 0, maxScroll);
|
|
2574
3008
|
if (offset === scrollTargetRef.current && !immediate) {
|
|
@@ -2579,13 +3013,13 @@ function useScrollView({
|
|
|
2579
3013
|
},
|
|
2580
3014
|
[maxScroll, scrollOffset]
|
|
2581
3015
|
);
|
|
2582
|
-
const scrollToRatio = (0,
|
|
3016
|
+
const scrollToRatio = (0, import_react10.useCallback)(
|
|
2583
3017
|
(ratio, immediate = false) => {
|
|
2584
3018
|
scrollTo(clamp(ratio, 0, 1) * maxScroll, immediate);
|
|
2585
3019
|
},
|
|
2586
3020
|
[maxScroll, scrollTo]
|
|
2587
3021
|
);
|
|
2588
|
-
const handleContentLayout = (0,
|
|
3022
|
+
const handleContentLayout = (0, import_react10.useCallback)(
|
|
2589
3023
|
(event) => {
|
|
2590
3024
|
if (!didSetInitialPositionRef.current) {
|
|
2591
3025
|
const initialOffset = initialPosition === "end" ? Math.max(0, event.height - viewportHeight) : 0;
|
|
@@ -2598,13 +3032,13 @@ function useScrollView({
|
|
|
2598
3032
|
},
|
|
2599
3033
|
[initialPosition, scrollOffset, viewportHeight]
|
|
2600
3034
|
);
|
|
2601
|
-
(0,
|
|
3035
|
+
(0, import_react10.useEffect)(() => {
|
|
2602
3036
|
if (!hasContentLayout) {
|
|
2603
3037
|
return;
|
|
2604
3038
|
}
|
|
2605
3039
|
scrollTo(scrollTargetRef.current, true);
|
|
2606
3040
|
}, [hasContentLayout, maxScroll, scrollTo]);
|
|
2607
|
-
const handleWheel = (0,
|
|
3041
|
+
const handleWheel = (0, import_react10.useCallback)(
|
|
2608
3042
|
(event) => {
|
|
2609
3043
|
if (maxScroll <= 0) {
|
|
2610
3044
|
return;
|
|
@@ -2619,7 +3053,7 @@ function useScrollView({
|
|
|
2619
3053
|
},
|
|
2620
3054
|
[maxScroll, scrollTo, viewportHeight, wheelStep]
|
|
2621
3055
|
);
|
|
2622
|
-
const handleTouchStart = (0,
|
|
3056
|
+
const handleTouchStart = (0, import_react10.useCallback)(
|
|
2623
3057
|
(event) => {
|
|
2624
3058
|
if (maxScroll <= 0) {
|
|
2625
3059
|
return;
|
|
@@ -2631,7 +3065,7 @@ function useScrollView({
|
|
|
2631
3065
|
},
|
|
2632
3066
|
[maxScroll]
|
|
2633
3067
|
);
|
|
2634
|
-
const handleTouchMove = (0,
|
|
3068
|
+
const handleTouchMove = (0, import_react10.useCallback)(
|
|
2635
3069
|
(event) => {
|
|
2636
3070
|
if (!touchDraggingRef.current) {
|
|
2637
3071
|
return;
|
|
@@ -2641,7 +3075,7 @@ function useScrollView({
|
|
|
2641
3075
|
},
|
|
2642
3076
|
[scrollTo]
|
|
2643
3077
|
);
|
|
2644
|
-
const handleTouchEnd = (0,
|
|
3078
|
+
const handleTouchEnd = (0, import_react10.useCallback)((event) => {
|
|
2645
3079
|
if (!touchDraggingRef.current) {
|
|
2646
3080
|
return;
|
|
2647
3081
|
}
|
|
@@ -2663,7 +3097,7 @@ function useScrollView({
|
|
|
2663
3097
|
}
|
|
2664
3098
|
|
|
2665
3099
|
// src/hooks/useScenario.ts
|
|
2666
|
-
var
|
|
3100
|
+
var import_react11 = require("react");
|
|
2667
3101
|
var currentScenarioSession = null;
|
|
2668
3102
|
var scenarioSessionId = 0;
|
|
2669
3103
|
var scenarioLifecycleQueue = Promise.resolve();
|
|
@@ -2805,7 +3239,7 @@ function setWaiting(time, skippable) {
|
|
|
2805
3239
|
executePluginCommand("scenario", { subCommand: "setWaiting", time, skippable });
|
|
2806
3240
|
}
|
|
2807
3241
|
function useScenario(stories, startName, entryName, goNextOnLoad = false) {
|
|
2808
|
-
(0,
|
|
3242
|
+
(0, import_react11.useEffect)(() => {
|
|
2809
3243
|
const session = acquireScenarioSession({
|
|
2810
3244
|
stories: normalizeStories(stories),
|
|
2811
3245
|
startName,
|
|
@@ -2819,9 +3253,9 @@ function useScenario(stories, startName, entryName, goNextOnLoad = false) {
|
|
|
2819
3253
|
}
|
|
2820
3254
|
|
|
2821
3255
|
// src/hooks/useSoundEffect.ts
|
|
2822
|
-
var
|
|
3256
|
+
var import_react12 = require("react");
|
|
2823
3257
|
function useSoundEffect(src) {
|
|
2824
|
-
(0,
|
|
3258
|
+
(0, import_react12.useEffect)(() => {
|
|
2825
3259
|
return () => {
|
|
2826
3260
|
try {
|
|
2827
3261
|
if (src) {
|
|
@@ -2836,7 +3270,7 @@ function useSoundEffect(src) {
|
|
|
2836
3270
|
}
|
|
2837
3271
|
};
|
|
2838
3272
|
}, [src]);
|
|
2839
|
-
return (0,
|
|
3273
|
+
return (0, import_react12.useCallback)(() => {
|
|
2840
3274
|
try {
|
|
2841
3275
|
if (src) {
|
|
2842
3276
|
executePluginCommand("audio", {
|
|
@@ -2852,7 +3286,7 @@ function useSoundEffect(src) {
|
|
|
2852
3286
|
}
|
|
2853
3287
|
|
|
2854
3288
|
// src/hooks/useStage.ts
|
|
2855
|
-
var
|
|
3289
|
+
var import_react13 = require("react");
|
|
2856
3290
|
var import_valtio5 = require("valtio");
|
|
2857
3291
|
var SKIP_INTERVAL_MS = 80;
|
|
2858
3292
|
var DEFAULT_FAST_FORWARD_STEP_LIMIT = 1e4;
|
|
@@ -2938,6 +3372,9 @@ function createStage() {
|
|
|
2938
3372
|
return addToRegistry(interruptCallbacks, cb);
|
|
2939
3373
|
}
|
|
2940
3374
|
function tryInterrupt() {
|
|
3375
|
+
if (tryFinishActiveWait()) {
|
|
3376
|
+
return true;
|
|
3377
|
+
}
|
|
2941
3378
|
for (const cb of interruptCallbacks) {
|
|
2942
3379
|
try {
|
|
2943
3380
|
if (cb()) return true;
|
|
@@ -2985,6 +3422,8 @@ function createStage() {
|
|
|
2985
3422
|
let _autoTicketSeq = 0;
|
|
2986
3423
|
const _pendingAutoTickets = /* @__PURE__ */ new Map();
|
|
2987
3424
|
let _fastForwardRuntime = null;
|
|
3425
|
+
let _activeWait = null;
|
|
3426
|
+
let _activeWaitSeq = 0;
|
|
2988
3427
|
let _managedAdvanceInFlight = false;
|
|
2989
3428
|
let _managedAdvancePending = false;
|
|
2990
3429
|
function resetManagedAdvanceState() {
|
|
@@ -3073,12 +3512,53 @@ function createStage() {
|
|
|
3073
3512
|
});
|
|
3074
3513
|
}
|
|
3075
3514
|
function requestNextLine() {
|
|
3515
|
+
if (_activeWait !== null) {
|
|
3516
|
+
return;
|
|
3517
|
+
}
|
|
3076
3518
|
if (isManagedAdvanceActive()) {
|
|
3077
3519
|
scheduleManagedAdvance();
|
|
3078
3520
|
return;
|
|
3079
3521
|
}
|
|
3080
3522
|
void Promise.resolve(nextLine()).catch(handleManagedAdvanceError);
|
|
3081
3523
|
}
|
|
3524
|
+
function invalidateActiveWait() {
|
|
3525
|
+
if (_activeWait === null) {
|
|
3526
|
+
return;
|
|
3527
|
+
}
|
|
3528
|
+
_activeWait.settled = true;
|
|
3529
|
+
_activeWait = null;
|
|
3530
|
+
}
|
|
3531
|
+
function settleActiveWait(wait, error) {
|
|
3532
|
+
if (_activeWait !== wait || wait.settled) {
|
|
3533
|
+
return;
|
|
3534
|
+
}
|
|
3535
|
+
wait.settled = true;
|
|
3536
|
+
_activeWait = null;
|
|
3537
|
+
if (error !== void 0) {
|
|
3538
|
+
console.error(`[Stage] Promise hold ${wait.id} rejected:`, error);
|
|
3539
|
+
}
|
|
3540
|
+
requestNextLine();
|
|
3541
|
+
}
|
|
3542
|
+
function tryFinishActiveWait() {
|
|
3543
|
+
const wait = _activeWait;
|
|
3544
|
+
if (wait === null || !wait.skippable || wait.settled) {
|
|
3545
|
+
return false;
|
|
3546
|
+
}
|
|
3547
|
+
const finish = wait.until.finish;
|
|
3548
|
+
if (typeof finish === "function") {
|
|
3549
|
+
try {
|
|
3550
|
+
finish.call(wait.until);
|
|
3551
|
+
} catch (error) {
|
|
3552
|
+
console.error(`[Stage] Failed to finish Promise hold ${wait.id}:`, error);
|
|
3553
|
+
}
|
|
3554
|
+
} else {
|
|
3555
|
+
console.warn(
|
|
3556
|
+
`[Stage] Skipping Promise hold ${wait.id} without finish(); the underlying operation may continue.`
|
|
3557
|
+
);
|
|
3558
|
+
}
|
|
3559
|
+
settleActiveWait(wait);
|
|
3560
|
+
return true;
|
|
3561
|
+
}
|
|
3082
3562
|
function clearAutoResumeTimer() {
|
|
3083
3563
|
if (_autoResumeTimer !== null) {
|
|
3084
3564
|
clearTimeout(_autoResumeTimer);
|
|
@@ -3266,7 +3746,11 @@ function createStage() {
|
|
|
3266
3746
|
if (isAnyBlockerActive()) return;
|
|
3267
3747
|
skipState.active = true;
|
|
3268
3748
|
invokeSkipCallbacks();
|
|
3749
|
+
const activeWait = _activeWait;
|
|
3269
3750
|
tryInterrupt();
|
|
3751
|
+
if (activeWait !== null && activeWait !== _activeWait) {
|
|
3752
|
+
return;
|
|
3753
|
+
}
|
|
3270
3754
|
scheduleSkipNextLine();
|
|
3271
3755
|
}
|
|
3272
3756
|
function stopSkip() {
|
|
@@ -3285,6 +3769,7 @@ function createStage() {
|
|
|
3285
3769
|
if (fastForwardState.active) return;
|
|
3286
3770
|
if (isAnyAutoBlockerActive()) return;
|
|
3287
3771
|
autoState.active = true;
|
|
3772
|
+
if (_activeWait !== null) return;
|
|
3288
3773
|
tryInterrupt();
|
|
3289
3774
|
scheduleAutoNextLine();
|
|
3290
3775
|
}
|
|
@@ -3321,6 +3806,7 @@ function createStage() {
|
|
|
3321
3806
|
return fastForwardState.active;
|
|
3322
3807
|
}
|
|
3323
3808
|
function resetRuntimeState() {
|
|
3809
|
+
invalidateActiveWait();
|
|
3324
3810
|
skipState.active = false;
|
|
3325
3811
|
autoState.active = false;
|
|
3326
3812
|
fastForwardState.active = false;
|
|
@@ -3366,7 +3852,7 @@ function createStage() {
|
|
|
3366
3852
|
setWaiting(time, skippable);
|
|
3367
3853
|
}
|
|
3368
3854
|
},
|
|
3369
|
-
hold() {
|
|
3855
|
+
hold(until, skippable = false) {
|
|
3370
3856
|
handled = true;
|
|
3371
3857
|
if (warpActive) {
|
|
3372
3858
|
return;
|
|
@@ -3375,6 +3861,24 @@ function createStage() {
|
|
|
3375
3861
|
requestNextLine();
|
|
3376
3862
|
return;
|
|
3377
3863
|
}
|
|
3864
|
+
if (until !== void 0) {
|
|
3865
|
+
invalidateActiveWait();
|
|
3866
|
+
const wait = {
|
|
3867
|
+
id: ++_activeWaitSeq,
|
|
3868
|
+
until,
|
|
3869
|
+
skippable,
|
|
3870
|
+
settled: false
|
|
3871
|
+
};
|
|
3872
|
+
_activeWait = wait;
|
|
3873
|
+
void Promise.resolve(until).then(
|
|
3874
|
+
() => settleActiveWait(wait),
|
|
3875
|
+
(error) => settleActiveWait(wait, error)
|
|
3876
|
+
);
|
|
3877
|
+
if (skipState.active) {
|
|
3878
|
+
tryFinishActiveWait();
|
|
3879
|
+
}
|
|
3880
|
+
return;
|
|
3881
|
+
}
|
|
3378
3882
|
if (skipState.active && !unskippableFlag) {
|
|
3379
3883
|
if (isAnyBlockerActive()) {
|
|
3380
3884
|
stopSkip();
|
|
@@ -3434,6 +3938,7 @@ function createStage() {
|
|
|
3434
3938
|
return parsed.data;
|
|
3435
3939
|
}
|
|
3436
3940
|
function dispatchCommand(e) {
|
|
3941
|
+
invalidateActiveWait();
|
|
3437
3942
|
for (const cb of beforeHandleCommandCallbacks) {
|
|
3438
3943
|
try {
|
|
3439
3944
|
cb(e);
|
|
@@ -3462,6 +3967,7 @@ function createStage() {
|
|
|
3462
3967
|
}
|
|
3463
3968
|
}
|
|
3464
3969
|
function dispatchTextLine(e) {
|
|
3970
|
+
invalidateActiveWait();
|
|
3465
3971
|
const { control, wasHandled } = buildControl();
|
|
3466
3972
|
for (const handler of textLineHandlers) {
|
|
3467
3973
|
handler(e, control);
|
|
@@ -3495,6 +4001,7 @@ function createStage() {
|
|
|
3495
4001
|
})
|
|
3496
4002
|
];
|
|
3497
4003
|
return () => {
|
|
4004
|
+
resetRuntimeState();
|
|
3498
4005
|
for (const cleanup of cleanups) cleanup();
|
|
3499
4006
|
};
|
|
3500
4007
|
}
|
|
@@ -3515,52 +4022,54 @@ function createStage() {
|
|
|
3515
4022
|
startAuto,
|
|
3516
4023
|
stopAuto,
|
|
3517
4024
|
isAutoing,
|
|
4025
|
+
setDefaultAutoTailMs,
|
|
3518
4026
|
startFastForward,
|
|
3519
4027
|
stopFastForward,
|
|
3520
4028
|
isFastForwarding,
|
|
4029
|
+
getSeekingType,
|
|
3521
4030
|
resetRuntimeState,
|
|
3522
4031
|
bindEvents
|
|
3523
4032
|
};
|
|
3524
4033
|
}
|
|
3525
|
-
var StageContext = (0,
|
|
4034
|
+
var StageContext = (0, import_react13.createContext)(null);
|
|
3526
4035
|
function useStageContext() {
|
|
3527
|
-
const ctx = (0,
|
|
4036
|
+
const ctx = (0, import_react13.useContext)(StageContext);
|
|
3528
4037
|
if (!ctx) throw new Error("useStageContext must be used within StageContextProvider");
|
|
3529
4038
|
return ctx;
|
|
3530
4039
|
}
|
|
3531
4040
|
function StageContextProvider({ stage, children }) {
|
|
3532
|
-
(0,
|
|
4041
|
+
(0, import_react13.useEffect)(() => {
|
|
3533
4042
|
return stage.bindEvents();
|
|
3534
4043
|
}, [stage]);
|
|
3535
|
-
return (0,
|
|
4044
|
+
return (0, import_react13.createElement)(StageContext.Provider, { value: stage }, children);
|
|
3536
4045
|
}
|
|
3537
4046
|
function useSkipCallback(callback) {
|
|
3538
4047
|
const stage = useStageContext();
|
|
3539
|
-
(0,
|
|
4048
|
+
(0, import_react13.useEffect)(() => {
|
|
3540
4049
|
return stage.addSkipCallback(callback);
|
|
3541
4050
|
}, [stage, callback]);
|
|
3542
4051
|
}
|
|
3543
4052
|
function useInterruptCallback(callback) {
|
|
3544
4053
|
const stage = useStageContext();
|
|
3545
|
-
(0,
|
|
4054
|
+
(0, import_react13.useEffect)(() => {
|
|
3546
4055
|
return stage.addInterruptCallback(callback);
|
|
3547
4056
|
}, [stage, callback]);
|
|
3548
4057
|
}
|
|
3549
4058
|
function useSkipBlocker(callback) {
|
|
3550
4059
|
const stage = useStageContext();
|
|
3551
|
-
(0,
|
|
4060
|
+
(0, import_react13.useEffect)(() => {
|
|
3552
4061
|
return stage.addSkipBlocker(callback);
|
|
3553
4062
|
}, [stage, callback]);
|
|
3554
4063
|
}
|
|
3555
4064
|
function useAutoBlocker(callback) {
|
|
3556
4065
|
const stage = useStageContext();
|
|
3557
|
-
(0,
|
|
4066
|
+
(0, import_react13.useEffect)(() => {
|
|
3558
4067
|
return stage.addAutoBlocker(callback);
|
|
3559
4068
|
}, [stage, callback]);
|
|
3560
4069
|
}
|
|
3561
4070
|
function useAutoTicket() {
|
|
3562
4071
|
const stage = useStageContext();
|
|
3563
|
-
return (0,
|
|
4072
|
+
return (0, import_react13.useCallback)(
|
|
3564
4073
|
(options) => {
|
|
3565
4074
|
return stage.issueAutoTicket(options);
|
|
3566
4075
|
},
|
|
@@ -3569,7 +4078,7 @@ function useAutoTicket() {
|
|
|
3569
4078
|
}
|
|
3570
4079
|
function useBeforeHandleCommandCallback(callback) {
|
|
3571
4080
|
const stage = useStageContext();
|
|
3572
|
-
(0,
|
|
4081
|
+
(0, import_react13.useEffect)(() => {
|
|
3573
4082
|
return stage.addBeforeHandleCommandCallback(callback);
|
|
3574
4083
|
}, [stage, callback]);
|
|
3575
4084
|
}
|