@wukonglabs/wukong 0.1.1 → 0.1.3

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.
Files changed (54) hide show
  1. package/README.md +17 -8
  2. package/dist/cli/help.d.ts.map +1 -1
  3. package/dist/cli/help.js +4 -1
  4. package/dist/cli/help.js.map +1 -1
  5. package/dist/index.js +171 -54
  6. package/dist/index.js.map +1 -1
  7. package/dist/tui/app.d.ts +15 -1
  8. package/dist/tui/app.d.ts.map +1 -1
  9. package/dist/tui/app.js +51 -11
  10. package/dist/tui/app.js.map +1 -1
  11. package/dist/tui/hint-bar.js +1 -1
  12. package/dist/tui/hint-bar.js.map +1 -1
  13. package/dist/tui/history-entry.d.ts +3 -1
  14. package/dist/tui/history-entry.d.ts.map +1 -1
  15. package/dist/tui/history-entry.js +23 -4
  16. package/dist/tui/history-entry.js.map +1 -1
  17. package/dist/tui/history-item.d.ts +14 -8
  18. package/dist/tui/history-item.d.ts.map +1 -1
  19. package/dist/tui/live-block.js +1 -1
  20. package/dist/tui/live-block.js.map +1 -1
  21. package/dist/tui/permission-card.d.ts.map +1 -1
  22. package/dist/tui/permission-card.js +3 -1
  23. package/dist/tui/permission-card.js.map +1 -1
  24. package/dist/tui/plan-panel.d.ts.map +1 -1
  25. package/dist/tui/plan-panel.js +3 -1
  26. package/dist/tui/plan-panel.js.map +1 -1
  27. package/dist/tui/response-panel.d.ts +6 -1
  28. package/dist/tui/response-panel.d.ts.map +1 -1
  29. package/dist/tui/response-panel.js +10 -1
  30. package/dist/tui/response-panel.js.map +1 -1
  31. package/dist/tui/run-ink.d.ts +18 -0
  32. package/dist/tui/run-ink.d.ts.map +1 -1
  33. package/dist/tui/run-ink.js +74 -2
  34. package/dist/tui/run-ink.js.map +1 -1
  35. package/dist/tui/slash/menu.d.ts.map +1 -1
  36. package/dist/tui/slash/menu.js +4 -2
  37. package/dist/tui/slash/menu.js.map +1 -1
  38. package/dist/tui/slash/registry.js +1 -1
  39. package/dist/tui/slash/registry.js.map +1 -1
  40. package/dist/tui/text-input.d.ts +16 -1
  41. package/dist/tui/text-input.d.ts.map +1 -1
  42. package/dist/tui/text-input.js +96 -42
  43. package/dist/tui/text-input.js.map +1 -1
  44. package/dist/tui/theme/theme.d.ts +4 -0
  45. package/dist/tui/theme/theme.d.ts.map +1 -1
  46. package/dist/tui/theme/theme.js +14 -10
  47. package/dist/tui/theme/theme.js.map +1 -1
  48. package/dist/tui/thinking-panel.d.ts.map +1 -1
  49. package/dist/tui/thinking-panel.js +7 -5
  50. package/dist/tui/thinking-panel.js.map +1 -1
  51. package/dist/tui/welcome.js +1 -1
  52. package/dist/tui/welcome.js.map +1 -1
  53. package/package.json +2 -2
  54. package/wukong.json +12 -3
@@ -1 +1 @@
1
- {"version":3,"file":"history-item.d.ts","sourceRoot":"","sources":["../../src/tui/history-item.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,UAAU,GAAG,WAAW,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;IACtG,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,WAAW,EAAE;YAAE,MAAM,EAAE,MAAM,CAAC;YAAC,UAAU,EAAE,MAAM,CAAA;SAAE,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IACnG,8CAA8C;IAC9C,IAAI,CAAC,EAAE;QACL,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,MAAM,CAAC;QAClB,aAAa,CAAC,EAAE,MAAM,CAAC;QACvB,OAAO,CAAC,EAAE,OAAO,CAAC;QAClB,UAAU,EAAE,MAAM,CAAC;QACnB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;IACF,uDAAuD;IACvD,IAAI,CAAC,EAAE;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE;YAAE,OAAO,EAAE,MAAM,CAAC;YAAC,MAAM,EAAE,MAAM,CAAA;SAAE,EAAE,CAAA;KAAE,CAAC;IAC1F,6CAA6C;IAC7C,SAAS,CAAC,EAAE,KAAK,CAAC,YAAY,CAAC;CAChC"}
1
+ {"version":3,"file":"history-item.d.ts","sourceRoot":"","sources":["../../src/tui/history-item.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,MAAM,WAAW,QAAQ;IACvB,iEAAiE;IACjE,YAAY,EAAE,MAAM,CAAC;IACrB,WAAW,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IACpD,4CAA4C;IAC5C,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,4BAA4B;IAC5B,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,UAAU,GAAG,WAAW,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,GAAG,MAAM,GAAG,SAAS,CAAC;IACtG,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,QAAQ,CAAC;IACjB,8CAA8C;IAC9C,IAAI,CAAC,EAAE;QACL,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,MAAM,CAAC;QAClB,aAAa,CAAC,EAAE,MAAM,CAAC;QACvB,OAAO,CAAC,EAAE,OAAO,CAAC;QAClB,UAAU,EAAE,MAAM,CAAC;QACnB,IAAI,EAAE,MAAM,CAAC;KACd,CAAC;IACF,uDAAuD;IACvD,IAAI,CAAC,EAAE;QAAE,SAAS,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE;YAAE,OAAO,EAAE,MAAM,CAAC;YAAC,MAAM,EAAE,MAAM,CAAA;SAAE,EAAE,CAAA;KAAE,CAAC;IAC1F,6CAA6C;IAC7C,SAAS,CAAC,EAAE,KAAK,CAAC,YAAY,CAAC;CAChC"}
@@ -67,6 +67,6 @@ export function LiveBlock({ thinkingText, thinkingStreaming, activeTools, stream
67
67
  }
68
68
  const statsSuffix = statsParts.length > 0 ? ` (${statsParts.join(' · ')})` : '';
69
69
  const activityLine = `${icon} ${verb}…${statsSuffix}`;
70
- return (_jsxs(Box, { flexDirection: "column", children: [_jsx(Box, { paddingX: 1, children: _jsx(Text, { color: theme.status, bold: true, children: activityLine }) }), hasThinking && (_jsx(Box, { paddingX: 1, children: _jsx(ThinkingPanel, { thinking: thinkingText, streaming: thinkingStreaming, tailLines: thinkingStreaming ? thinkingRows : 0 }) })), hasTools && _jsx(ToolCards, { tools: activeTools, maxVisible: toolsVisible }), hasResponse && (_jsx(Box, { flexDirection: "column", paddingX: 1, children: tailLines.length === 0 ? (_jsx(Text, { color: "cyan", dimColor: true, children: "\u231B \u6B63\u5728\u751F\u6210\u54CD\u5E94\u2026" })) : (tailLines.map((line, i) => (_jsxs(Text, { color: "cyan", dimColor: true, children: [line, i === tailLines.length - 1 ? '▍' : ''] }, i)))) })), (streaming || awaitingLlm) && (_jsx(Box, { paddingX: 1, children: _jsx(Text, { dimColor: true, children: `Tip: /clear 重置会话 · esc 取消当前 run` }) }))] }));
70
+ return (_jsxs(Box, { flexDirection: "column", children: [_jsx(Box, { paddingX: 1, children: _jsx(Text, { color: theme.status, bold: true, children: activityLine }) }), hasThinking && (_jsx(Box, { paddingX: 1, children: _jsx(ThinkingPanel, { thinking: thinkingText, streaming: thinkingStreaming, tailLines: thinkingStreaming ? thinkingRows : 0 }) })), hasTools && _jsx(ToolCards, { tools: activeTools, maxVisible: toolsVisible }), hasResponse && (_jsx(Box, { flexDirection: "column", paddingX: 1, children: tailLines.length === 0 ? (_jsx(Text, { color: theme.assistant, dimColor: true, children: "\u231B \u6B63\u5728\u751F\u6210\u54CD\u5E94\u2026" })) : (tailLines.map((line, i) => (_jsxs(Text, { color: theme.assistant, dimColor: true, children: [line, i === tailLines.length - 1 ? '▍' : ''] }, i)))) })), (streaming || awaitingLlm) && (_jsx(Box, { paddingX: 1, children: _jsx(Text, { dimColor: true, children: `Tip: /clear 重置会话 · esc 取消当前 run` }) }))] }));
71
71
  }
72
72
  //# sourceMappingURL=live-block.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"live-block.js","sourceRoot":"","sources":["../../src/tui/live-block.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"live-block.js","sourceRoot":"","sources":["../../src/tui/live-block.tsx"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"permission-card.d.ts","sourceRoot":"","sources":["../../src/tui/permission-card.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AACH,OAAO,KAAmB,MAAM,OAAO,CAAC;AAExC,OAAO,KAAK,EAAE,oBAAoB,EAAE,mBAAmB,EAAyB,MAAM,8BAA8B,CAAC;AAErH,MAAM,WAAW,mBAAmB;IAClC,WAAW;IACX,OAAO,EAAE,oBAAoB,CAAC;IAC9B,aAAa;IACb,QAAQ,EAAE,CAAC,MAAM,EAAE,mBAAmB,KAAK,IAAI,CAAC;CACjD;AAED,wBAAgB,cAAc,CAAC,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE,mBAAmB,GAAG,KAAK,CAAC,YAAY,CA+E7F"}
1
+ {"version":3,"file":"permission-card.d.ts","sourceRoot":"","sources":["../../src/tui/permission-card.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;GAgBG;AACH,OAAO,KAAmB,MAAM,OAAO,CAAC;AAExC,OAAO,KAAK,EAAE,oBAAoB,EAAE,mBAAmB,EAAyB,MAAM,8BAA8B,CAAC;AAGrH,MAAM,WAAW,mBAAmB;IAClC,WAAW;IACX,OAAO,EAAE,oBAAoB,CAAC;IAC9B,aAAa;IACb,QAAQ,EAAE,CAAC,MAAM,EAAE,mBAAmB,KAAK,IAAI,CAAC;CACjD;AAED,wBAAgB,cAAc,CAAC,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE,mBAAmB,GAAG,KAAK,CAAC,YAAY,CAgF7F"}
@@ -18,8 +18,10 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
18
18
  */
19
19
  import { useState } from 'react';
20
20
  import { Box, Text, useInput } from 'ink';
21
+ import { useTheme } from './theme/context.js';
21
22
  export function PermissionCard({ request, onSubmit }) {
22
23
  const [showFullArgs, setShowFullArgs] = useState(false);
24
+ const { theme } = useTheme();
23
25
  useInput((input, key) => {
24
26
  const c = input.toLowerCase();
25
27
  let result = null;
@@ -55,7 +57,7 @@ export function PermissionCard({ request, onSubmit }) {
55
57
  }
56
58
  });
57
59
  const argsPreview = formatArgsPreview(request.argumentsJson, showFullArgs ? undefined : 200);
58
- return (_jsxs(Box, { flexDirection: "column", borderStyle: "round", borderColor: "yellow", paddingX: 1, children: [_jsxs(Box, { children: [_jsx(Text, { color: "yellow", bold: true, children: "\uD83D\uDD12 \u6388\u6743\u8BF7\u6C42" }), _jsxs(Text, { dimColor: true, children: [" (step ", request.step, ")"] })] }), _jsxs(Box, { children: [_jsx(Text, { bold: true, children: "\u5DE5\u5177: " }), _jsx(Text, { color: "cyan", children: request.toolName })] }), _jsxs(Box, { flexDirection: "column", children: [_jsx(Text, { bold: true, children: "\u53C2\u6570:" }), _jsx(Text, { dimColor: true, children: argsPreview }), !showFullArgs && request.argumentsJson.length > 200 && (_jsx(Text, { dimColor: true, color: "gray", children: "(\u6309 v \u67E5\u770B\u5B8C\u6574\u53C2\u6570)" }))] }), _jsx(Box, { marginTop: 1, children: _jsx(Text, { bold: true, children: "\u9009\u62E9: " }) }), _jsxs(Box, { children: [_jsx(Text, { color: "green", children: "[y]" }), _jsx(Text, { children: " \u4EC5\u672C\u6B21 " }), _jsx(Text, { color: "green", children: "[s]" }), _jsx(Text, { children: " \u672C\u6B21session " }), _jsx(Text, { color: "green", children: "[l]" }), _jsx(Text, { children: " \u672C\u9879\u76EE\u6C38\u4E45 " }), _jsx(Text, { color: "green", children: "[g]" }), _jsx(Text, { children: " \u5168\u5C40\u6C38\u4E45" })] }), _jsxs(Box, { children: [_jsx(Text, { color: "red", children: "[n]" }), _jsx(Text, { children: " \u62D2\u7EDD " }), _jsx(Text, { color: "red", children: "[x]" }), _jsx(Text, { children: " \u6C38\u4E45\u62D2\u7EDD " }), _jsx(Text, { dimColor: true, children: "[v] \u67E5\u770B\u53C2\u6570" })] })] }));
60
+ return (_jsxs(Box, { flexDirection: "column", borderStyle: "round", borderColor: "yellow", paddingX: 1, children: [_jsxs(Box, { children: [_jsx(Text, { color: "yellow", bold: true, children: "\uD83D\uDD12 \u6388\u6743\u8BF7\u6C42" }), _jsxs(Text, { dimColor: true, children: [" (step ", request.step, ")"] })] }), _jsxs(Box, { children: [_jsx(Text, { bold: true, children: "\u5DE5\u5177: " }), _jsx(Text, { color: theme.status, children: request.toolName })] }), _jsxs(Box, { flexDirection: "column", children: [_jsx(Text, { bold: true, children: "\u53C2\u6570:" }), _jsx(Text, { dimColor: true, children: argsPreview }), !showFullArgs && request.argumentsJson.length > 200 && (_jsx(Text, { dimColor: true, color: "gray", children: "(\u6309 v \u67E5\u770B\u5B8C\u6574\u53C2\u6570)" }))] }), _jsx(Box, { marginTop: 1, children: _jsx(Text, { bold: true, children: "\u9009\u62E9: " }) }), _jsxs(Box, { children: [_jsx(Text, { color: "green", children: "[y]" }), _jsx(Text, { children: " \u4EC5\u672C\u6B21 " }), _jsx(Text, { color: "green", children: "[s]" }), _jsx(Text, { children: " \u672C\u6B21session " }), _jsx(Text, { color: "green", children: "[l]" }), _jsx(Text, { children: " \u672C\u9879\u76EE\u6C38\u4E45 " }), _jsx(Text, { color: "green", children: "[g]" }), _jsx(Text, { children: " \u5168\u5C40\u6C38\u4E45" })] }), _jsxs(Box, { children: [_jsx(Text, { color: "red", children: "[n]" }), _jsx(Text, { children: " \u62D2\u7EDD " }), _jsx(Text, { color: "red", children: "[x]" }), _jsx(Text, { children: " \u6C38\u4E45\u62D2\u7EDD " }), _jsx(Text, { dimColor: true, children: "[v] \u67E5\u770B\u53C2\u6570" })] })] }));
59
61
  }
60
62
  /** 格式化参数预览(截断到 maxLen) */
61
63
  function formatArgsPreview(argsJson, maxLen) {
@@ -1 +1 @@
1
- {"version":3,"file":"permission-card.js","sourceRoot":"","sources":["../../src/tui/permission-card.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"permission-card.js","sourceRoot":"","sources":["../../src/tui/permission-card.tsx"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"plan-panel.d.ts","sourceRoot":"","sources":["../../src/tui/plan-panel.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAG1B,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,SAAS,GAAG,aAAa,GAAG,WAAW,GAAG,WAAW,CAAC;CAC/D;AAED,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,yBAAyB;IACzB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,wBAAgB,SAAS,CAAC,EAAE,KAAK,EAAE,UAAe,EAAE,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,GAAG,IAAI,CAwB/F"}
1
+ {"version":3,"file":"plan-panel.d.ts","sourceRoot":"","sources":["../../src/tui/plan-panel.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;GAiBG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAI1B,MAAM,WAAW,QAAQ;IACvB,EAAE,EAAE,MAAM,CAAC;IACX,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,SAAS,GAAG,aAAa,GAAG,WAAW,GAAG,WAAW,CAAC;CAC/D;AAED,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,QAAQ,EAAE,CAAC;IAClB,yBAAyB;IACzB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,wBAAgB,SAAS,CAAC,EAAE,KAAK,EAAE,UAAe,EAAE,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,GAAG,IAAI,CAyB/F"}
@@ -1,6 +1,8 @@
1
1
  import { jsxs as _jsxs, jsx as _jsx } from "react/jsx-runtime";
2
2
  import { Box, Text } from 'ink';
3
+ import { useTheme } from './theme/context.js';
3
4
  export function PlanPanel({ todos, maxVisible = 10 }) {
5
+ const { theme } = useTheme();
4
6
  if (todos.length === 0)
5
7
  return null;
6
8
  const completed = todos.filter((t) => t.status === 'completed').length;
@@ -9,7 +11,7 @@ export function PlanPanel({ todos, maxVisible = 10 }) {
9
11
  // 策略:已完成的折叠到头部和尾部,进行中的可见(用户最关心的状态)
10
12
  const visible = todos.slice(0, maxVisible);
11
13
  const hidden = total - visible.length;
12
- return (_jsxs(Box, { flexDirection: "column", marginY: 0, children: [_jsxs(Text, { color: "cyan", bold: true, children: ["\u25B6 Plan (", completed, "/", total, ")"] }), visible.map((t, i) => (_jsx(TodoRow, { index: i + 1, todo: t }, t.id))), hidden > 0 && (_jsxs(Text, { dimColor: true, children: [" \u2026 \u8FD8\u6709 ", hidden, " \u4E2A todo(\u5DF2\u6298\u53E0)"] }))] }));
14
+ return (_jsxs(Box, { flexDirection: "column", marginY: 0, children: [_jsxs(Text, { color: theme.status, bold: true, children: ["\u25B6 Plan (", completed, "/", total, ")"] }), visible.map((t, i) => (_jsx(TodoRow, { index: i + 1, todo: t }, t.id))), hidden > 0 && (_jsxs(Text, { dimColor: true, children: [" \u2026 \u8FD8\u6709 ", hidden, " \u4E2A todo(\u5DF2\u6298\u53E0)"] }))] }));
13
15
  }
14
16
  function TodoRow({ index, todo }) {
15
17
  const { icon, color } = statusIcon(todo.status);
@@ -1 +1 @@
1
- {"version":3,"file":"plan-panel.js","sourceRoot":"","sources":["../../src/tui/plan-panel.tsx"],"names":[],"mappings":";AAmBA,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,KAAK,CAAC;AAchC,MAAM,UAAU,SAAS,CAAC,EAAE,KAAK,EAAE,UAAU,GAAG,EAAE,EAAkB;IAClE,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IAEpC,MAAM,SAAS,GAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,WAAW,CAAC,CAAC,MAAM,CAAC;IACvE,MAAM,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC;IAE3B,2CAA2C;IAC3C,mCAAmC;IACnC,MAAM,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC;IAC3C,MAAM,MAAM,GAAG,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC;IAEtC,OAAO,CACL,MAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,OAAO,EAAE,CAAC,aACpC,MAAC,IAAI,IAAC,KAAK,EAAC,MAAM,EAAC,IAAI,oCACZ,SAAS,OAAG,KAAK,SACrB,EACN,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CACrB,KAAC,OAAO,IAAY,KAAK,EAAE,CAAC,GAAG,CAAC,EAAE,IAAI,EAAE,CAAC,IAA3B,CAAC,CAAC,EAAE,CAA2B,CAC9C,CAAC,EACD,MAAM,GAAG,CAAC,IAAI,CACb,MAAC,IAAI,IAAC,QAAQ,6CAAS,MAAM,wCAAoB,CAClD,IACG,CACP,CAAC;AACJ,CAAC;AAED,SAAS,OAAO,CAAC,EAAE,KAAK,EAAE,IAAI,EAAqC;IACjE,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,UAAU,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;IAChD,OAAO,CACL,MAAC,GAAG,eACF,KAAC,IAAI,IAAC,KAAK,EAAE,KAAK,YAAG,IAAI,GAAQ,EACjC,MAAC,IAAI,IAAC,QAAQ,wBAAG,KAAK,UAAU,EAChC,MAAC,IAAI,IAAC,KAAK,EAAE,KAAK,KAAK,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,aAC9C,IAAI,CAAC,OAAO,EACZ,IAAI,CAAC,MAAM,KAAK,aAAa,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,IACxC,IACH,CACP,CAAC;AACJ,CAAC;AAED,SAAS,UAAU,CAAC,MAA0B;IAC5C,QAAQ,MAAM,EAAE,CAAC;QACf,KAAK,WAAW;YACd,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;QACvC,KAAK,aAAa;YAChB,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC;QACxC,KAAK,WAAW;YACd,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC;QACrC;YACE,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IACxC,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"plan-panel.js","sourceRoot":"","sources":["../../src/tui/plan-panel.tsx"],"names":[],"mappings":";AAmBA,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,KAAK,CAAC;AAChC,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAc9C,MAAM,UAAU,SAAS,CAAC,EAAE,KAAK,EAAE,UAAU,GAAG,EAAE,EAAkB;IAClE,MAAM,EAAE,KAAK,EAAE,GAAG,QAAQ,EAAE,CAAC;IAC7B,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IAEpC,MAAM,SAAS,GAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,WAAW,CAAC,CAAC,MAAM,CAAC;IACvE,MAAM,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC;IAE3B,2CAA2C;IAC3C,mCAAmC;IACnC,MAAM,OAAO,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,UAAU,CAAC,CAAC;IAC3C,MAAM,MAAM,GAAG,KAAK,GAAG,OAAO,CAAC,MAAM,CAAC;IAEtC,OAAO,CACL,MAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,OAAO,EAAE,CAAC,aACpC,MAAC,IAAI,IAAC,KAAK,EAAE,KAAK,CAAC,MAAM,EAAE,IAAI,oCACpB,SAAS,OAAG,KAAK,SACrB,EACN,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CACrB,KAAC,OAAO,IAAY,KAAK,EAAE,CAAC,GAAG,CAAC,EAAE,IAAI,EAAE,CAAC,IAA3B,CAAC,CAAC,EAAE,CAA2B,CAC9C,CAAC,EACD,MAAM,GAAG,CAAC,IAAI,CACb,MAAC,IAAI,IAAC,QAAQ,6CAAS,MAAM,wCAAoB,CAClD,IACG,CACP,CAAC;AACJ,CAAC;AAED,SAAS,OAAO,CAAC,EAAE,KAAK,EAAE,IAAI,EAAqC;IACjE,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,UAAU,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;IAChD,OAAO,CACL,MAAC,GAAG,eACF,KAAC,IAAI,IAAC,KAAK,EAAE,KAAK,YAAG,IAAI,GAAQ,EACjC,MAAC,IAAI,IAAC,QAAQ,wBAAG,KAAK,UAAU,EAChC,MAAC,IAAI,IAAC,KAAK,EAAE,KAAK,KAAK,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,aAC9C,IAAI,CAAC,OAAO,EACZ,IAAI,CAAC,MAAM,KAAK,aAAa,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,IACxC,IACH,CACP,CAAC;AACJ,CAAC;AAED,SAAS,UAAU,CAAC,MAA0B;IAC5C,QAAQ,MAAM,EAAE,CAAC;QACf,KAAK,WAAW;YACd,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;QACvC,KAAK,aAAa;YAChB,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,QAAQ,EAAE,CAAC;QACxC,KAAK,WAAW;YACd,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC;QACrC;YACE,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IACxC,CAAC;AACH,CAAC"}
@@ -24,11 +24,16 @@ export interface ToolCallState {
24
24
  }
25
25
  export interface CompletedRun {
26
26
  response: string;
27
- steps: number;
27
+ /** 单次 Agent run 发起的 Provider 方法调用数,包含外层重试和 mid-run compaction */
28
+ requestCount: number;
28
29
  totalTokens: {
29
30
  prompt: number;
30
31
  completion: number;
31
32
  };
33
+ /** Provider 上报的累计 prompt cache 命中 tokens */
34
+ cachedPromptTokens?: number;
35
+ /** Provider 归一化后的缓存命中率分母 */
36
+ cacheInputTokens?: number;
32
37
  durationMs: number;
33
38
  }
34
39
  export interface ResponsePanelProps {
@@ -1 +1 @@
1
- {"version":3,"file":"response-panel.d.ts","sourceRoot":"","sources":["../../src/tui/response-panel.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAK1B,MAAM,WAAW,aAAa;IAC5B,UAAU,EAAE,MAAM,CAAC;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,yCAAyC;IACzC,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,YAAY;IAC3B,QAAQ,EAAE,MAAM,CAAC;IACjB,KAAK,EAAE,MAAM,CAAC;IACd,WAAW,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IACpD,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,kBAAkB;IACjC,kCAAkC;IAClC,aAAa,EAAE,MAAM,CAAC;IACtB,eAAe;IACf,SAAS,EAAE,OAAO,CAAC;IACnB,4BAA4B;IAC5B,aAAa,CAAC,EAAE,YAAY,CAAC;IAC7B,sBAAsB;IACtB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,wBAAgB,aAAa,CAAC,EAC5B,aAAkB,EAClB,SAAS,EACT,aAAa,EACb,QAAY,GACb,EAAE,kBAAkB,GAAG,KAAK,CAAC,YAAY,CAiCzC"}
1
+ {"version":3,"file":"response-panel.d.ts","sourceRoot":"","sources":["../../src/tui/response-panel.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAM1B,MAAM,WAAW,aAAa;IAC5B,UAAU,EAAE,MAAM,CAAC;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB,yCAAyC;IACzC,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,YAAY;IAC3B,QAAQ,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,YAAY,EAAE,MAAM,CAAC;IACrB,WAAW,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IACpD,4CAA4C;IAC5C,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,4BAA4B;IAC5B,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,kBAAkB;IACjC,kCAAkC;IAClC,aAAa,EAAE,MAAM,CAAC;IACtB,eAAe;IACf,SAAS,EAAE,OAAO,CAAC;IACnB,4BAA4B;IAC5B,aAAa,CAAC,EAAE,YAAY,CAAC;IAC7B,sBAAsB;IACtB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,wBAAgB,aAAa,CAAC,EAC5B,aAAkB,EAClB,SAAS,EACT,aAAa,EACb,QAAY,GACb,EAAE,kBAAkB,GAAG,KAAK,CAAC,YAAY,CA2CzC"}
@@ -2,10 +2,19 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
2
  import { Text, Box } from 'ink';
3
3
  import { useTerminalWidth } from './use-terminal-width.js';
4
4
  import { tailVisualLines } from './tail-visual.js';
5
+ import { useTheme } from './theme/context.js';
5
6
  export function ResponsePanel({ streamingText = '', streaming, lastCompleted, maxLines = 6, }) {
6
7
  const cols = useTerminalWidth();
8
+ const { theme } = useTheme();
7
9
  const tail = tailVisualLines(streamingText, maxLines, cols);
8
10
  const tailLines = tail.length > 0 ? tail.split('\n') : [];
9
- return (_jsxs(Box, { flexDirection: "column", paddingX: 1, children: [streaming && (_jsx(Box, { flexDirection: "column", children: tailLines.length === 0 ? (_jsx(Text, { color: "cyan", dimColor: true, children: "\u231B \u6B63\u5728\u751F\u6210\u54CD\u5E94\u2026" })) : (tailLines.map((line, i) => (_jsxs(Text, { color: "cyan", dimColor: true, children: [line, i === tailLines.length - 1 ? '▍' : ''] }, i)))) })), !streaming && lastCompleted && (_jsxs(Box, { children: [_jsx(Text, { color: "green", children: "\u2713 " }), _jsxs(Text, { dimColor: true, children: ["\u672C\u8F6E\u54CD\u5E94\u5DF2\u5B8C\u6210(\u6B63\u6587\u89C1\u4E0A\u65B9,\u5171 ", lastCompleted.response.length, " \u5B57\u7B26, \u6B65\u9AA4", ' ', lastCompleted.steps, ", \u8017\u65F6 ", (lastCompleted.durationMs / 1000).toFixed(1), "s)"] })] }))] }));
11
+ const completedCacheRate = lastCompleted?.cachedPromptTokens !== undefined &&
12
+ lastCompleted.cacheInputTokens !== undefined &&
13
+ lastCompleted.cacheInputTokens > 0
14
+ ? (lastCompleted.cachedPromptTokens / lastCompleted.cacheInputTokens) * 100
15
+ : undefined;
16
+ return (_jsxs(Box, { flexDirection: "column", paddingX: 1, children: [streaming && (_jsx(Box, { flexDirection: "column", children: tailLines.length === 0 ? (_jsx(Text, { color: theme.assistant, dimColor: true, children: "\u231B \u6B63\u5728\u751F\u6210\u54CD\u5E94\u2026" })) : (tailLines.map((line, i) => (_jsxs(Text, { color: theme.assistant, dimColor: true, children: [line, i === tailLines.length - 1 ? '▍' : ''] }, i)))) })), !streaming && lastCompleted && (_jsxs(Box, { children: [_jsx(Text, { color: "green", children: "\u2713 " }), _jsxs(Text, { dimColor: true, children: ["\u672C\u8F6E\u54CD\u5E94\u5DF2\u5B8C\u6210(\u6B63\u6587\u89C1\u4E0A\u65B9,\u5171 ", lastCompleted.response.length, " \u5B57\u7B26, Request Count:", ' ', lastCompleted.requestCount, completedCacheRate !== undefined
17
+ ? `, Cached Tokens(%): ${completedCacheRate.toFixed(1)}%`
18
+ : '', `, Duration: ${(lastCompleted.durationMs / 1000).toFixed(1)}s)`] })] }))] }));
10
19
  }
11
20
  //# sourceMappingURL=response-panel.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"response-panel.js","sourceRoot":"","sources":["../../src/tui/response-panel.tsx"],"names":[],"mappings":";AAaA,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,MAAM,KAAK,CAAC;AAChC,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAgCnD,MAAM,UAAU,aAAa,CAAC,EAC5B,aAAa,GAAG,EAAE,EAClB,SAAS,EACT,aAAa,EACb,QAAQ,GAAG,CAAC,GACO;IACnB,MAAM,IAAI,GAAG,gBAAgB,EAAE,CAAC;IAChC,MAAM,IAAI,GAAG,eAAe,CAAC,aAAa,EAAE,QAAQ,EAAE,IAAI,CAAC,CAAC;IAC5D,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IAE1D,OAAO,CACL,MAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,QAAQ,EAAE,CAAC,aACpC,SAAS,IAAI,CACZ,KAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,YACxB,SAAS,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,CACxB,KAAC,IAAI,IAAC,KAAK,EAAC,MAAM,EAAC,QAAQ,wEAAiB,CAC7C,CAAC,CAAC,CAAC,CACF,SAAS,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,EAAE,EAAE,CAAC,CACzB,MAAC,IAAI,IAAS,KAAK,EAAC,MAAM,EAAC,QAAQ,mBAChC,IAAI,EACJ,CAAC,KAAK,SAAS,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,KAF7B,CAAC,CAGL,CACR,CAAC,CACH,GACG,CACP,EAEA,CAAC,SAAS,IAAI,aAAa,IAAI,CAC9B,MAAC,GAAG,eACF,KAAC,IAAI,IAAC,KAAK,EAAC,OAAO,wBAAU,EAC7B,MAAC,IAAI,IAAC,QAAQ,wGACK,aAAa,CAAC,QAAQ,CAAC,MAAM,iCAAS,GAAG,EACzD,aAAa,CAAC,KAAK,qBAAO,CAAC,aAAa,CAAC,UAAU,GAAG,IAAI,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,UAClE,IACH,CACP,IACG,CACP,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"response-panel.js","sourceRoot":"","sources":["../../src/tui/response-panel.tsx"],"names":[],"mappings":";AAaA,OAAO,EAAE,IAAI,EAAE,GAAG,EAAE,MAAM,KAAK,CAAC;AAChC,OAAO,EAAE,gBAAgB,EAAE,MAAM,yBAAyB,CAAC;AAC3D,OAAO,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AACnD,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAqC9C,MAAM,UAAU,aAAa,CAAC,EAC5B,aAAa,GAAG,EAAE,EAClB,SAAS,EACT,aAAa,EACb,QAAQ,GAAG,CAAC,GACO;IACnB,MAAM,IAAI,GAAG,gBAAgB,EAAE,CAAC;IAChC,MAAM,EAAE,KAAK,EAAE,GAAG,QAAQ,EAAE,CAAC;IAC7B,MAAM,IAAI,GAAG,eAAe,CAAC,aAAa,EAAE,QAAQ,EAAE,IAAI,CAAC,CAAC;IAC5D,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC;IAC1D,MAAM,kBAAkB,GAAG,aAAa,EAAE,kBAAkB,KAAK,SAAS;QACxE,aAAa,CAAC,gBAAgB,KAAK,SAAS;QAC5C,aAAa,CAAC,gBAAgB,GAAG,CAAC;QAClC,CAAC,CAAC,CAAC,aAAa,CAAC,kBAAkB,GAAG,aAAa,CAAC,gBAAgB,CAAC,GAAG,GAAG;QAC3E,CAAC,CAAC,SAAS,CAAC;IAEd,OAAO,CACL,MAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,QAAQ,EAAE,CAAC,aACpC,SAAS,IAAI,CACZ,KAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,YACxB,SAAS,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,CACxB,KAAC,IAAI,IAAC,KAAK,EAAE,KAAK,CAAC,SAAS,EAAE,QAAQ,wEAAiB,CACxD,CAAC,CAAC,CAAC,CACF,SAAS,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,EAAE,EAAE,CAAC,CACzB,MAAC,IAAI,IAAS,KAAK,EAAE,KAAK,CAAC,SAAS,EAAE,QAAQ,mBAC3C,IAAI,EACJ,CAAC,KAAK,SAAS,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,KAF7B,CAAC,CAGL,CACR,CAAC,CACH,GACG,CACP,EAEA,CAAC,SAAS,IAAI,aAAa,IAAI,CAC9B,MAAC,GAAG,eACF,KAAC,IAAI,IAAC,KAAK,EAAC,OAAO,wBAAU,EAC7B,MAAC,IAAI,IAAC,QAAQ,wGACK,aAAa,CAAC,QAAQ,CAAC,MAAM,mCAAqB,GAAG,EACrE,aAAa,CAAC,YAAY,EAC1B,kBAAkB,KAAK,SAAS;gCAC/B,CAAC,CAAC,uBAAuB,kBAAkB,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG;gCACzD,CAAC,CAAC,EAAE,EACL,eAAe,CAAC,aAAa,CAAC,UAAU,GAAG,IAAI,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,IAAI,IAC3D,IACH,CACP,IACG,CACP,CAAC;AACJ,CAAC"}
@@ -27,8 +27,26 @@ export interface InkRunHandle {
27
27
  /** 卸载 Ink 实例(退出时调用) */
28
28
  unmount: () => void;
29
29
  }
30
+ interface CursorAnchorRef {
31
+ current: string;
32
+ }
33
+ interface FullRenderRef {
34
+ current: boolean;
35
+ }
36
+ /**
37
+ * 返回光标锚点的逆向移动。Ink 的清屏逻辑只要求回到帧末尾所在行,
38
+ * 后续 eraseLines 会自行把列归零,因此不依赖终端对 save/restore cursor 的支持。
39
+ */
40
+ export declare function getCursorAnchorRestoreSequence(anchor: string): string;
41
+ /**
42
+ * Ink 的 log-update 假设每次更新都从上一帧末尾开始。为了让 IME 跟随输入位置,
43
+ * 每帧写完后移动到输入光标;下一次 Ink 写入前按相同行数移回帧末尾,
44
+ * 否则 eraseLines 会从输入行开始清屏,造成输入框和 HintBar 逐次重复。
45
+ */
46
+ export declare function createCursorAnchoredStdout(stdout: NodeJS.WriteStream, cursorAnchorRef: CursorAnchorRef, fullRenderRef?: FullRenderRef): NodeJS.WriteStream;
30
47
  /**
31
48
  * 启动 Ink TUI。onStream 由调用方通过 streamSinkRef 桥接,不再由此处返回。
32
49
  */
33
50
  export declare function runInk(opts: InkRunOptions): InkRunHandle;
51
+ export {};
34
52
  //# sourceMappingURL=run-ink.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"run-ink.d.ts","sourceRoot":"","sources":["../../src/tui/run-ink.tsx"],"names":[],"mappings":"AASA,OAAO,EAAO,WAAW,EAAE,OAAO,EAAE,MAAM,UAAU,CAAC;AAGrD,MAAM,WAAW,aAAa;IAC5B,KAAK,EAAE,MAAM,CAAC;IACd,gBAAgB,EAAE,MAAM,CAAC;IACzB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,WAAW,CAAC;IACtB,cAAc,CAAC,EAAE,MAAM,EAAE,CAAC;IAC1B;;;OAGG;IACH,aAAa,EAAE,OAAO,CAAC;IACvB,qBAAqB;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,6BAA6B;IAC7B,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAgB;IAChB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,kBAAkB;IAClB,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,yCAAyC;IACzC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,yBAAyB;IACzB,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED,MAAM,WAAW,YAAY;IAC3B,uBAAuB;IACvB,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,IAAI,EAAE,aAAa,GAAG,YAAY,CAuBxD"}
1
+ {"version":3,"file":"run-ink.d.ts","sourceRoot":"","sources":["../../src/tui/run-ink.tsx"],"names":[],"mappings":"AASA,OAAO,EAAO,WAAW,EAAE,OAAO,EAAE,MAAM,UAAU,CAAC;AAGrD,MAAM,WAAW,aAAa;IAC5B,KAAK,EAAE,MAAM,CAAC;IACd,gBAAgB,EAAE,MAAM,CAAC;IACzB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,WAAW,CAAC;IACtB,cAAc,CAAC,EAAE,MAAM,EAAE,CAAC;IAC1B;;;OAGG;IACH,aAAa,EAAE,OAAO,CAAC;IACvB,qBAAqB;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,6BAA6B;IAC7B,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,gBAAgB;IAChB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,kBAAkB;IAClB,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,yCAAyC;IACzC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,yBAAyB;IACzB,YAAY,CAAC,EAAE,MAAM,CAAC;CACvB;AAED,MAAM,WAAW,YAAY;IAC3B,uBAAuB;IACvB,OAAO,EAAE,MAAM,IAAI,CAAC;CACrB;AAED,UAAU,eAAe;IACvB,OAAO,EAAE,MAAM,CAAC;CACjB;AAED,UAAU,aAAa;IACrB,OAAO,EAAE,OAAO,CAAC;CAClB;AAED;;;GAGG;AACH,wBAAgB,8BAA8B,CAAC,MAAM,EAAE,MAAM,GAAG,MAAM,CAGrE;AAED;;;;GAIG;AACH,wBAAgB,0BAA0B,CACxC,MAAM,EAAE,MAAM,CAAC,WAAW,EAC1B,eAAe,EAAE,eAAe,EAChC,aAAa,GAAE,aAAkC,GAChD,MAAM,CAAC,WAAW,CAsCpB;AAED;;GAEG;AACH,wBAAgB,MAAM,CAAC,IAAI,EAAE,aAAa,GAAG,YAAY,CA8CxD"}
@@ -10,13 +10,85 @@ import { jsx as _jsx } from "react/jsx-runtime";
10
10
  import { render } from 'ink';
11
11
  import { App } from './app.js';
12
12
  import { ThemeProvider } from './theme/context.js';
13
+ /**
14
+ * 返回光标锚点的逆向移动。Ink 的清屏逻辑只要求回到帧末尾所在行,
15
+ * 后续 eraseLines 会自行把列归零,因此不依赖终端对 save/restore cursor 的支持。
16
+ */
17
+ export function getCursorAnchorRestoreSequence(anchor) {
18
+ const match = /^\x1b\[(\d+)A/.exec(anchor);
19
+ return match ? `\x1b[${match[1]}B` : '';
20
+ }
21
+ /**
22
+ * Ink 的 log-update 假设每次更新都从上一帧末尾开始。为了让 IME 跟随输入位置,
23
+ * 每帧写完后移动到输入光标;下一次 Ink 写入前按相同行数移回帧末尾,
24
+ * 否则 eraseLines 会从输入行开始清屏,造成输入框和 HintBar 逐次重复。
25
+ */
26
+ export function createCursorAnchoredStdout(stdout, cursorAnchorRef, fullRenderRef = { current: false }) {
27
+ const originalWrite = stdout.write.bind(stdout);
28
+ let anchorScheduled = false;
29
+ let restoreFrameEnd = '';
30
+ const scheduleAnchor = () => {
31
+ if (anchorScheduled)
32
+ return;
33
+ anchorScheduled = true;
34
+ queueMicrotask(() => {
35
+ anchorScheduled = false;
36
+ const anchor = cursorAnchorRef.current;
37
+ if (anchor) {
38
+ originalWrite(anchor);
39
+ restoreFrameEnd = getCursorAnchorRestoreSequence(anchor);
40
+ }
41
+ });
42
+ };
43
+ const anchoredWrite = ((...args) => {
44
+ if (restoreFrameEnd) {
45
+ originalWrite(restoreFrameEnd);
46
+ restoreFrameEnd = '';
47
+ }
48
+ const result = originalWrite(...args);
49
+ scheduleAnchor();
50
+ return result;
51
+ });
52
+ return new Proxy(stdout, {
53
+ get(target, property) {
54
+ if (property === 'write')
55
+ return anchoredWrite;
56
+ // Ink 在 outputHeight >= stdout.rows 时会使用 clearTerminal + 完整帧输出。
57
+ // resize 的同步处理期间临时返回 1,避免旧行被终端 reflow 后按失效行数增量擦除。
58
+ if (property === 'rows' && fullRenderRef.current)
59
+ return 1;
60
+ const value = Reflect.get(target, property, target);
61
+ return typeof value === 'function' ? value.bind(target) : value;
62
+ },
63
+ });
64
+ }
13
65
  /**
14
66
  * 启动 Ink TUI。onStream 由调用方通过 streamSinkRef 桥接,不再由此处返回。
15
67
  */
16
68
  export function runInk(opts) {
17
- const inkInstance = render(_jsx(ThemeProvider, { children: _jsx(App, { model: opts.model, sessionUuidShort: opts.sessionUuidShort, workspaceRoot: opts.workspaceRoot, handlers: opts.handlers, initialHistory: opts.initialHistory, streamSinkRef: opts.streamSinkRef, appVersion: opts.appVersion, configPath: opts.configPath, sessionRecordCount: opts.sessionRecordCount, sessionCreated: opts.sessionCreated, toolsCount: opts.toolsCount, skillsLoaded: opts.skillsLoaded }) }));
69
+ const cursorAnchorRef = { current: '' };
70
+ const fullRenderRef = { current: false };
71
+ const stdout = createCursorAnchoredStdout(process.stdout, cursorAnchorRef, fullRenderRef);
72
+ const inkInstance = render(_jsx(ThemeProvider, { children: _jsx(App, { model: opts.model, sessionUuidShort: opts.sessionUuidShort, workspaceRoot: opts.workspaceRoot, handlers: opts.handlers, initialHistory: opts.initialHistory, streamSinkRef: opts.streamSinkRef, appVersion: opts.appVersion, configPath: opts.configPath, sessionRecordCount: opts.sessionRecordCount, sessionCreated: opts.sessionCreated, toolsCount: opts.toolsCount, skillsLoaded: opts.skillsLoaded, cursorAnchorRef: cursorAnchorRef }) }), { stdout });
73
+ /*
74
+ * 终端 resize 会按新列宽重排旧帧,Ink 的 previousLineCount 不再可信。
75
+ * 监听器排在 Ink 自带 resize 监听器之前:本次同步 resize 周期内让 stdout.rows=1,
76
+ * 使 Ink 走内置 clearTerminal + 完整帧输出;事件结束后立即恢复真实 rows。
77
+ * 不手动 clear、不 rerender,也不 remount App。
78
+ */
79
+ const handleResize = () => {
80
+ fullRenderRef.current = true;
81
+ queueMicrotask(() => {
82
+ fullRenderRef.current = false;
83
+ });
84
+ };
85
+ process.stdout.prependListener('resize', handleResize);
18
86
  return {
19
- unmount: () => inkInstance.unmount(),
87
+ unmount: () => {
88
+ process.stdout.off('resize', handleResize);
89
+ cursorAnchorRef.current = '';
90
+ inkInstance.unmount();
91
+ },
20
92
  };
21
93
  }
22
94
  //# sourceMappingURL=run-ink.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"run-ink.js","sourceRoot":"","sources":["../../src/tui/run-ink.tsx"],"names":[],"mappings":";AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,MAAM,EAAE,MAAM,KAAK,CAAC;AAC7B,OAAO,EAAE,GAAG,EAAwB,MAAM,UAAU,CAAC;AACrD,OAAO,EAAE,aAAa,EAAE,MAAM,oBAAoB,CAAC;AAgCnD;;GAEG;AACH,MAAM,UAAU,MAAM,CAAC,IAAmB;IACxC,MAAM,WAAW,GAAG,MAAM,CACxB,KAAC,aAAa,cACZ,KAAC,GAAG,IACF,KAAK,EAAE,IAAI,CAAC,KAAK,EACjB,gBAAgB,EAAE,IAAI,CAAC,gBAAgB,EACvC,aAAa,EAAE,IAAI,CAAC,aAAa,EACjC,QAAQ,EAAE,IAAI,CAAC,QAAQ,EACvB,cAAc,EAAE,IAAI,CAAC,cAAc,EACnC,aAAa,EAAE,IAAI,CAAC,aAAa,EACjC,UAAU,EAAE,IAAI,CAAC,UAAU,EAC3B,UAAU,EAAE,IAAI,CAAC,UAAU,EAC3B,kBAAkB,EAAE,IAAI,CAAC,kBAAkB,EAC3C,cAAc,EAAE,IAAI,CAAC,cAAc,EACnC,UAAU,EAAE,IAAI,CAAC,UAAU,EAC3B,YAAY,EAAE,IAAI,CAAC,YAAY,GAC/B,GACY,CACjB,CAAC;IAEF,OAAO;QACL,OAAO,EAAE,GAAG,EAAE,CAAC,WAAW,CAAC,OAAO,EAAE;KACrC,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"run-ink.js","sourceRoot":"","sources":["../../src/tui/run-ink.tsx"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"menu.d.ts","sourceRoot":"","sources":["../../../src/tui/slash/menu.tsx"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAE1B,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAElD,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE,YAAY,EAAE,CAAC;IACzB,sBAAsB;IACtB,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,wBAAgB,SAAS,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,GAAG,IAAI,CAiB5F"}
1
+ {"version":3,"file":"menu.d.ts","sourceRoot":"","sources":["../../../src/tui/slash/menu.tsx"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAE1B,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAGlD,MAAM,WAAW,cAAc;IAC7B,QAAQ,EAAE,YAAY,EAAE,CAAC;IACzB,sBAAsB;IACtB,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,wBAAgB,SAAS,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAE,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,GAAG,IAAI,CAkB5F"}
@@ -1,11 +1,13 @@
1
1
  import { jsxs as _jsxs, jsx as _jsx } from "react/jsx-runtime";
2
2
  import { Box, Text } from 'ink';
3
+ import { useTheme } from '../theme/context.js';
3
4
  export function SlashMenu({ commands, highlight }) {
5
+ const { theme } = useTheme();
4
6
  if (commands.length === 0)
5
7
  return null;
6
- return (_jsx(Box, { flexDirection: "column", borderStyle: "round", borderColor: "cyan", paddingX: 1, children: commands.map((c, i) => {
8
+ return (_jsx(Box, { flexDirection: "column", borderStyle: "round", borderColor: theme.border, paddingX: 1, children: commands.map((c, i) => {
7
9
  const active = i === highlight;
8
- return (_jsx(Box, { children: _jsxs(Text, { inverse: active, children: [_jsxs(Text, { color: active ? 'cyan' : undefined, children: ["/", c.name] }), _jsxs(Text, { children: [" \u2014 ", c.description] })] }) }, c.name));
10
+ return (_jsx(Box, { children: _jsxs(Text, { inverse: active, children: [_jsxs(Text, { color: active ? theme.status : undefined, children: ["/", c.name] }), _jsxs(Text, { children: [" \u2014 ", c.description] })] }) }, c.name));
9
11
  }) }));
10
12
  }
11
13
  //# sourceMappingURL=menu.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"menu.js","sourceRoot":"","sources":["../../../src/tui/slash/menu.tsx"],"names":[],"mappings":";AAQA,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,KAAK,CAAC;AAShC,MAAM,UAAU,SAAS,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAkB;IAC/D,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IACvC,OAAO,CACL,KAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,WAAW,EAAC,OAAO,EAAC,WAAW,EAAC,MAAM,EAAC,QAAQ,EAAE,CAAC,YAC3E,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;YACrB,MAAM,MAAM,GAAG,CAAC,KAAK,SAAS,CAAC;YAC/B,OAAO,CACL,KAAC,GAAG,cACF,MAAC,IAAI,IAAC,OAAO,EAAE,MAAM,aACnB,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,SAAS,kBAAI,CAAC,CAAC,IAAI,IAAQ,EAC1D,MAAC,IAAI,2BAAK,CAAC,CAAC,WAAW,IAAQ,IAC1B,IAJC,CAAC,CAAC,IAAI,CAKV,CACP,CAAC;QACJ,CAAC,CAAC,GACE,CACP,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"menu.js","sourceRoot":"","sources":["../../../src/tui/slash/menu.tsx"],"names":[],"mappings":";AAQA,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,KAAK,CAAC;AAEhC,OAAO,EAAE,QAAQ,EAAE,MAAM,qBAAqB,CAAC;AAQ/C,MAAM,UAAU,SAAS,CAAC,EAAE,QAAQ,EAAE,SAAS,EAAkB;IAC/D,MAAM,EAAE,KAAK,EAAE,GAAG,QAAQ,EAAE,CAAC;IAC7B,IAAI,QAAQ,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC;IACvC,OAAO,CACL,KAAC,GAAG,IAAC,aAAa,EAAC,QAAQ,EAAC,WAAW,EAAC,OAAO,EAAC,WAAW,EAAE,KAAK,CAAC,MAAM,EAAE,QAAQ,EAAE,CAAC,YACnF,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;YACrB,MAAM,MAAM,GAAG,CAAC,KAAK,SAAS,CAAC;YAC/B,OAAO,CACL,KAAC,GAAG,cACF,MAAC,IAAI,IAAC,OAAO,EAAE,MAAM,aACnB,MAAC,IAAI,IAAC,KAAK,EAAE,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,SAAS,kBAAI,CAAC,CAAC,IAAI,IAAQ,EAChE,MAAC,IAAI,2BAAK,CAAC,CAAC,WAAW,IAAQ,IAC1B,IAJC,CAAC,CAAC,IAAI,CAKV,CACP,CAAC;QACJ,CAAC,CAAC,GACE,CACP,CAAC;AACJ,CAAC"}
@@ -11,7 +11,7 @@ export const SLASH_COMMANDS = [
11
11
  { name: 'clear', description: '清空对话历史' },
12
12
  { name: 'quit', description: '优雅退出' },
13
13
  { name: 'exit', description: '优雅退出' },
14
- { name: 'model', description: '显示当前模型' },
14
+ { name: 'model', description: '列出或切换模型', takesArgument: true },
15
15
  { name: 'session', description: '显示 session 信息' },
16
16
  { name: 'theme', description: '切换主题(dark/light/mono)', takesArgument: true },
17
17
  { name: 'compact', description: '手动触发压缩', notEnabledHint: '压缩功能未启用' },
@@ -1 +1 @@
1
- {"version":3,"file":"registry.js","sourceRoot":"","sources":["../../../src/tui/slash/registry.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAwBH,MAAM,CAAC,MAAM,cAAc,GAAmB;IAC5C,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,QAAQ,EAAE;IACvC,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,8BAA8B,EAAE;IAC/D,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,QAAQ,EAAE;IACxC,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,QAAQ,EAAE;IACxC,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,eAAe,EAAE;IACjD,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,uBAAuB,EAAE,aAAa,EAAE,IAAI,EAAE;IAC5E,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,QAAQ,EAAE,cAAc,EAAE,SAAS,EAAE;IACrE,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,mBAAmB,EAAE,cAAc,EAAE,gBAAgB,EAAE;IACrF,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,UAAU,EAAE;CAC1C,CAAC;AAEF,+BAA+B;AAC/B,MAAM,UAAU,mBAAmB,CAAC,MAAc;IAChD,MAAM,CAAC,GAAG,MAAM,CAAC,WAAW,EAAE,CAAC;IAC/B,IAAI,CAAC,CAAC;QAAE,OAAO,cAAc,CAAC;IAC9B,OAAO,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAC;AAC5D,CAAC"}
1
+ {"version":3,"file":"registry.js","sourceRoot":"","sources":["../../../src/tui/slash/registry.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAwBH,MAAM,CAAC,MAAM,cAAc,GAAmB;IAC5C,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,QAAQ,EAAE;IACvC,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,8BAA8B,EAAE;IAC/D,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,QAAQ,EAAE;IACxC,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,EAAE;IACrC,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,aAAa,EAAE,IAAI,EAAE;IAC9D,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,eAAe,EAAE;IACjD,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,uBAAuB,EAAE,aAAa,EAAE,IAAI,EAAE;IAC5E,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,QAAQ,EAAE,cAAc,EAAE,SAAS,EAAE;IACrE,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,EAAE,mBAAmB,EAAE,cAAc,EAAE,gBAAgB,EAAE;IACrF,EAAE,IAAI,EAAE,MAAM,EAAE,WAAW,EAAE,UAAU,EAAE;CAC1C,CAAC;AAEF,+BAA+B;AAC/B,MAAM,UAAU,mBAAmB,CAAC,MAAc;IAChD,MAAM,CAAC,GAAG,MAAM,CAAC,WAAW,EAAE,CAAC;IAC/B,IAAI,CAAC,CAAC;QAAE,OAAO,cAAc,CAAC;IAC9B,OAAO,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,CAAC;AAC5D,CAAC"}
@@ -41,6 +41,12 @@ export interface TextInputProps {
41
41
  placeholder?: string;
42
42
  /** 是否禁用(等待 agent 响应时) */
43
43
  disabled?: boolean;
44
+ /** Ink 输出层使用的真实终端光标锚点 */
45
+ cursorAnchorRef?: {
46
+ current: string;
47
+ };
48
+ /** 终端列数,用于计算输入文本自动换行后的光标位置 */
49
+ terminalColumns?: number;
44
50
  /**
45
51
  * Ctrl+C 回调(§3.3 M3):由 App 层实现两次 Ctrl+C 语义。
46
52
  * Ink raw mode 拦截 Ctrl+C,不走 process SIGINT,故需显式回调。
@@ -51,7 +57,16 @@ export interface TextInputProps {
51
57
  /** 选中某个 slash 命令时回调(name + 可选参数) */
52
58
  onSlash?: (name: string, arg?: string) => void;
53
59
  }
54
- export declare function TextInput({ value, onChange, onSubmit, multiline, history, prompt, placeholder, disabled, onAbort, onExit, onSlash, }: TextInputProps): React.ReactElement;
60
+ export declare function TextInput({ value, onChange, onSubmit, multiline, history, prompt, placeholder, disabled, cursorAnchorRef, terminalColumns, onAbort, onExit, onSlash, }: TextInputProps): React.ReactElement;
61
+ /**
62
+ * 生成 Ink 完成一帧输出后,将真实终端光标移回输入位置的 ANSI 序列。
63
+ *
64
+ * 只使用相对上移 + 绝对列定位,不假设输入框贴着终端底部。输入框靠近底部时,
65
+ * 候选窗显示在光标上方还是下方交给终端和操作系统决定。
66
+ */
67
+ export declare function getCursorAnchorSequence(value: string, cursor: number, prompt: string, terminalColumns: number): string;
68
+ /** 计算终端单元格宽度(CJK / 全角字符和 emoji 通常占两列)。 */
69
+ export declare function terminalCellWidth(text: string): number;
55
70
  /** 找 pos 之前最近的 word 边界(跳过连续 whitespace + 非 word 字符) */
56
71
  export declare function prevWordBoundary(value: string, pos: number): number;
57
72
  /** 找 pos 之后最近的 word 边界 */
@@ -1 +1 @@
1
- {"version":3,"file":"text-input.d.ts","sourceRoot":"","sources":["../../src/tui/text-input.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,OAAO,KAAmD,MAAM,OAAO,CAAC;AAExE,OAAO,EACL,eAAe,EAGhB,MAAM,wBAAwB,CAAC;AAQhC,MAAM,WAAW,cAAc;IAC7B,cAAc;IACd,KAAK,EAAE,MAAM,CAAC;IACd,YAAY;IACZ,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAClC,kBAAkB;IAClB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAClC,sBAAsB;IACtB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,oBAAoB;IACpB,OAAO,CAAC,EAAE,UAAU,CAAC,OAAO,eAAe,CAAC,CAAC;IAC7C,qBAAqB;IACrB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,0BAA0B;IAC1B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,yBAAyB;IACzB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;OAGG;IACH,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;IACrB,iCAAiC;IACjC,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IACpB,oCAAoC;IACpC,OAAO,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;CAChD;AAeD,wBAAgB,SAAS,CAAC,EACxB,KAAK,EACL,QAAQ,EACR,QAAQ,EACR,SAAgB,EAChB,OAAO,EACP,MAAa,EACb,WAAgB,EAChB,QAAgB,EAChB,OAAO,EACP,MAAM,EACN,OAAO,GACR,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,CA2YrC;AAyCD,uDAAuD;AACvD,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAMnE;AAED,0BAA0B;AAC1B,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAMnE"}
1
+ {"version":3,"file":"text-input.d.ts","sourceRoot":"","sources":["../../src/tui/text-input.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,OAAO,KAAmD,MAAM,OAAO,CAAC;AAExE,OAAO,EACL,eAAe,EAGhB,MAAM,wBAAwB,CAAC;AAShC,MAAM,WAAW,cAAc;IAC7B,cAAc;IACd,KAAK,EAAE,MAAM,CAAC;IACd,YAAY;IACZ,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAClC,kBAAkB;IAClB,QAAQ,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IAClC,sBAAsB;IACtB,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,oBAAoB;IACpB,OAAO,CAAC,EAAE,UAAU,CAAC,OAAO,eAAe,CAAC,CAAC;IAC7C,qBAAqB;IACrB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,0BAA0B;IAC1B,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,yBAAyB;IACzB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,yBAAyB;IACzB,eAAe,CAAC,EAAE;QAAE,OAAO,EAAE,MAAM,CAAA;KAAE,CAAC;IACtC,8BAA8B;IAC9B,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB;;;OAGG;IACH,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;IACrB,iCAAiC;IACjC,MAAM,CAAC,EAAE,MAAM,IAAI,CAAC;IACpB,oCAAoC;IACpC,OAAO,CAAC,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;CAChD;AAeD,wBAAgB,SAAS,CAAC,EACxB,KAAK,EACL,QAAQ,EACR,QAAQ,EACR,SAAgB,EAChB,OAAO,EACP,MAAa,EACb,WAAgB,EAChB,QAAgB,EAChB,eAAe,EACf,eAAoB,EACpB,OAAO,EACP,MAAM,EACN,OAAO,GACR,EAAE,cAAc,GAAG,KAAK,CAAC,YAAY,CAmXrC;AASD;;;;;GAKG;AACH,wBAAgB,uBAAuB,CACrC,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,MAAM,EACd,eAAe,EAAE,MAAM,GACtB,MAAM,CA0BR;AAgCD,0CAA0C;AAC1C,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAQtD;AAiED,uDAAuD;AACvD,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAMnE;AAED,0BAA0B;AAC1B,wBAAgB,gBAAgB,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAMnE"}
@@ -24,11 +24,12 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
24
24
  * 所有可打印字符(单/多)统一走 insertText,彻底消除闭包陷阱,IME 候选可见、可退格改字。
25
25
  */
26
26
  import { useState, useCallback, useEffect, useRef } from 'react';
27
- import { Text, useInput, useStdin, useStdout } from 'ink';
27
+ import { Text, useInput, useStdin } from 'ink';
28
28
  import { reverseSearch, reverseSearchNext, } from './use-input-history.js';
29
29
  import { parseSlashCommand } from './slash/parse.js';
30
30
  import { filterSlashCommands } from './slash/registry.js';
31
31
  import { SlashMenu } from './slash/menu.js';
32
+ import { useTheme } from './theme/context.js';
32
33
  /** 输入长度硬上限(M11c):粘贴大文件也够,防止异常灌入撑爆 Ink */
33
34
  const MAX_INPUT_LENGTH = 100_000;
34
35
  const INITIAL_RS = {
@@ -36,13 +37,13 @@ const INITIAL_RS = {
36
37
  query: '',
37
38
  matchIndex: -1,
38
39
  };
39
- export function TextInput({ value, onChange, onSubmit, multiline = true, history, prompt = '> ', placeholder = '', disabled = false, onAbort, onExit, onSlash, }) {
40
+ export function TextInput({ value, onChange, onSubmit, multiline = true, history, prompt = '> ', placeholder = '', disabled = false, cursorAnchorRef, terminalColumns = 80, onAbort, onExit, onSlash, }) {
40
41
  const [cursor, setCursor] = useState(value.length);
41
42
  const [rs, setRs] = useState(INITIAL_RS);
42
43
  const [slashDismissed, setSlashDismissed] = useState(false);
43
44
  const [slashHighlight, setSlashHighlight] = useState(0);
44
45
  const { stdin, setRawMode } = useStdin();
45
- const { stdout } = useStdout();
46
+ const { theme } = useTheme();
46
47
  // stdin 原始模式(捕获 Ctrl+C / Ctrl+R 等控制字符)
47
48
  useEffect(() => {
48
49
  if (stdin && typeof setRawMode === 'function') {
@@ -342,57 +343,110 @@ export function TextInput({ value, onChange, onSubmit, multiline = true, history
342
343
  return;
343
344
  }
344
345
  });
345
- // ── 物理光标定位(IME 候选窗跟随)──
346
- // Ink raw mode 下每帧渲染完物理光标停在帧末尾(HintBar 后),
347
- // OS 的 IME 候选窗固定在物理光标处弹出,导致候选窗偏离输入框.
348
- // 用 setTimeout(0) 延迟到 Ink 帧刷完后重定位,避免干扰帧缓冲.
349
- useEffect(() => {
350
- if (disabled || !value)
351
- return;
352
- const s = stdout;
353
- if (!s?.write || !s.isTTY || !s.rows)
354
- return;
355
- const writeFn = s.write;
356
- const termRows = s.rows;
357
- const timer = setTimeout(() => {
358
- try {
359
- const lineStart = value.lastIndexOf('\n', cursor - 1) + 1;
360
- const colInLine = cursor - lineStart;
361
- let cursorLineIndex = 0;
362
- for (let i = 0; i < cursor; i++) {
363
- if (value[i] === '\n')
364
- cursorLineIndex++;
365
- }
366
- /*
367
- * footer 钉底结构(从屏幕底向上):
368
- * row termRows : HintBar
369
- * row termRows - 1 : 输入框下边框 ─
370
- * row termRows - 2 : 输入框内容行(光标所在)
371
- * row termRows - 3 : 输入框上边框 ─
372
- */
373
- const row = Math.max(1, termRows - 2 - cursorLineIndex);
374
- const col = Math.max(1, 2 + prompt.length + colInLine); // │ + space + prompt + 行内列
375
- writeFn(`\x1b[${row};${col}H`);
376
- }
377
- catch { /* 非TTY 或流已关闭时静默失败 */ }
378
- }, 0);
379
- return () => clearTimeout(timer);
380
- }, [value, cursor, disabled, prompt, stdout]);
346
+ // ── 物理光标锚点(IME 候选窗跟随)──
347
+ // OS 输入法读取的是终端真实光标,而 Ink 每次刷帧后会把它留在 HintBar 末尾。
348
+ // 这里同步计算锚点;run-ink 的 stdout 包装器会在每次真实写帧后的 microtask 恢复它,
349
+ // 不再用 setTimeout 与 Ink 的节流输出抢时序。
350
+ if (cursorAnchorRef) {
351
+ cursorAnchorRef.current = disabled || slashActive || rs.active
352
+ ? ''
353
+ : getCursorAnchorSequence(value, cursor, prompt, terminalColumns);
354
+ }
381
355
  // ── 渲染 ──
382
356
  if (slashActive) {
383
357
  return _jsx(SlashMenu, { commands: slashCmds, highlight: Math.min(slashHighlight, Math.max(slashCmds.length - 1, 0)) });
384
358
  }
385
359
  if (rs.active) {
386
360
  const matchText = rs.matchIndex >= 0 && history ? history.entries[rs.matchIndex] : '';
387
- return (_jsxs(Text, { children: [_jsx(Text, { dimColor: true, children: "(reverse-i-search)`" }), _jsx(Text, { children: rs.query }), _jsx(Text, { inverse: true, children: " " }), _jsx(Text, { dimColor: true, children: "`: " }), _jsx(Text, { color: matchText ? 'cyan' : 'red', children: matchText || '(无匹配 · Esc/Ctrl+G 取消)' })] }));
361
+ return (_jsxs(Text, { children: [_jsx(Text, { dimColor: true, children: "(reverse-i-search)`" }), _jsx(Text, { children: rs.query }), _jsx(Text, { inverse: true, children: " " }), _jsx(Text, { dimColor: true, children: "`: " }), _jsx(Text, { color: matchText ? theme.status : 'red', children: matchText || '(无匹配 · Esc/Ctrl+G 取消)' })] }));
388
362
  }
389
363
  if (!value && placeholder) {
390
- return (_jsxs(Text, { children: [_jsx(Text, { color: "green", children: prompt }), _jsx(Text, { inverse: true, children: " " }), _jsx(Text, { dimColor: true, children: placeholder })] }));
364
+ return (_jsxs(Text, { wrap: "truncate", children: [_jsx(Text, { color: theme.userPrompt, children: prompt }), _jsx(Text, { inverse: true, children: " " }), _jsx(Text, { dimColor: true, children: placeholder })] }));
391
365
  }
392
366
  const before = value.slice(0, cursor);
393
367
  const at = value.slice(cursor, cursor + 1);
394
368
  const after = value.slice(cursor + 1);
395
- return (_jsxs(Text, { children: [_jsx(Text, { color: "green", children: prompt }), before, _jsx(Text, { inverse: true, children: at || ' ' }), after] }));
369
+ return (_jsxs(Text, { children: [_jsx(Text, { color: theme.userPrompt, children: prompt }), before, _jsx(Text, { inverse: true, children: at || ' ' }), after] }));
370
+ }
371
+ /**
372
+ * 生成 Ink 完成一帧输出后,将真实终端光标移回输入位置的 ANSI 序列。
373
+ *
374
+ * 只使用相对上移 + 绝对列定位,不假设输入框贴着终端底部。输入框靠近底部时,
375
+ * 候选窗显示在光标上方还是下方交给终端和操作系统决定。
376
+ */
377
+ export function getCursorAnchorSequence(value, cursor, prompt, terminalColumns) {
378
+ const safeCursor = Math.max(0, Math.min(cursor, value.length));
379
+ // round 边框左右各 1 列,paddingX 左右各 1 列。
380
+ const contentColumns = Math.max(1, terminalColumns - 4);
381
+ const prefixPosition = measureVisualPosition(prompt + value.slice(0, safeCursor), contentColumns);
382
+ const cursorCell = value.slice(safeCursor)[0] ?? ' ';
383
+ const cursorPosition = normalizeCursorPosition(prefixPosition, terminalCellWidth(cursorCell), contentColumns);
384
+ // 光标在末尾时 TextInput 会额外绘制一个反色空格,它也参与自动换行和高度计算。
385
+ const renderedText = prompt + value + (safeCursor === value.length ? ' ' : '');
386
+ const endPosition = measureVisualPosition(renderedText, contentColumns);
387
+ const totalContentRows = endPosition.row + 1;
388
+ // Ink 的 log-update 会在整帧后追加换行,真实光标最终位于 HintBar 的下一行。
389
+ // 因此需要越过:追加换行后的空行 + HintBar + 输入框下边框 + 剩余内容行。
390
+ const rowsUp = 2 + totalContentRows - cursorPosition.row;
391
+ // 内容区从终端第 3 列开始:左边框 1 列 + 左 padding 1 列。
392
+ const absoluteColumn = 3 + cursorPosition.col;
393
+ return `\x1b[${rowsUp}A\x1b[${absoluteColumn}G`;
394
+ }
395
+ function measureVisualPosition(text, columns) {
396
+ const position = { row: 0, col: 0 };
397
+ for (const char of text) {
398
+ if (char === '\n') {
399
+ position.row++;
400
+ position.col = 0;
401
+ continue;
402
+ }
403
+ const charWidth = terminalCellWidth(char);
404
+ if (charWidth === 0)
405
+ continue;
406
+ if (position.col > 0 && position.col + charWidth > columns) {
407
+ position.row++;
408
+ position.col = 0;
409
+ }
410
+ position.col += charWidth;
411
+ }
412
+ return position;
413
+ }
414
+ function normalizeCursorPosition(position, cursorCellWidth, columns) {
415
+ if (position.col >= columns || position.col + cursorCellWidth > columns) {
416
+ return { row: position.row + 1, col: 0 };
417
+ }
418
+ return position;
419
+ }
420
+ /** 计算终端单元格宽度(CJK / 全角字符和 emoji 通常占两列)。 */
421
+ export function terminalCellWidth(text) {
422
+ let width = 0;
423
+ for (const char of text) {
424
+ const code = char.codePointAt(0) ?? 0;
425
+ if (isCombiningMark(code) || code === 0x200d)
426
+ continue;
427
+ width += isWideCodePoint(code) ? 2 : 1;
428
+ }
429
+ return width;
430
+ }
431
+ function isCombiningMark(code) {
432
+ return ((code >= 0x0300 && code <= 0x036f) ||
433
+ (code >= 0x1ab0 && code <= 0x1aff) ||
434
+ (code >= 0x1dc0 && code <= 0x1dff) ||
435
+ (code >= 0x20d0 && code <= 0x20ff) ||
436
+ (code >= 0xfe20 && code <= 0xfe2f));
437
+ }
438
+ function isWideCodePoint(code) {
439
+ return ((code >= 0x1100 && code <= 0x115f) ||
440
+ (code >= 0x2329 && code <= 0x232a) ||
441
+ (code >= 0x2e80 && code <= 0xa4cf) ||
442
+ (code >= 0xac00 && code <= 0xd7a3) ||
443
+ (code >= 0xf900 && code <= 0xfaff) ||
444
+ (code >= 0xfe10 && code <= 0xfe19) ||
445
+ (code >= 0xfe30 && code <= 0xfe6f) ||
446
+ (code >= 0xff00 && code <= 0xff60) ||
447
+ (code >= 0xffe0 && code <= 0xffe6) ||
448
+ (code >= 0x1f300 && code <= 0x1faff) ||
449
+ (code >= 0x20000 && code <= 0x3fffd));
396
450
  }
397
451
  function getLineInfo(value, cursor) {
398
452
  let lineStart = 0;