@oh-my-pi/pi-tui 18.4.2 → 18.4.4
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/CHANGELOG.md +56 -0
- package/dist/types/apps/cleanse-board.d.ts +17 -0
- package/dist/types/apps/git/help.d.ts +16 -0
- package/dist/types/apps/git/sidebar.d.ts +18 -0
- package/dist/types/apps/live-visualizer.d.ts +10 -0
- package/dist/types/apps/ps-top.d.ts +15 -0
- package/dist/types/apps/standalone-picker.d.ts +3 -0
- package/dist/types/autocomplete.d.ts +8 -0
- package/dist/types/chat/advisor-message.d.ts +12 -2
- package/dist/types/chat/assistant-message.d.ts +20 -0
- package/dist/types/chat/bash-execution.d.ts +9 -0
- package/dist/types/chat/chat-transcript-builder.d.ts +6 -1
- package/dist/types/chat/collab-prompt-message.d.ts +4 -0
- package/dist/types/chat/compaction-summary-message.d.ts +15 -0
- package/dist/types/chat/eval-execution.d.ts +8 -0
- package/dist/types/chat/execution-shared.d.ts +58 -0
- package/dist/types/chat/late-diagnostics-message.d.ts +15 -1
- package/dist/types/chat/read-tool-group.d.ts +15 -0
- package/dist/types/chat/skill-message.d.ts +9 -0
- package/dist/types/chat/stripped-tool-calls-placeholder.d.ts +3 -0
- package/dist/types/chat/thinking-display.d.ts +2 -0
- package/dist/types/chat/todo-reminder.d.ts +4 -1
- package/dist/types/chat/tool-execution.d.ts +25 -1
- package/dist/types/chat/transcript-actions.d.ts +37 -0
- package/dist/types/chat/transcript-entry.d.ts +3 -1
- package/dist/types/chat/user-message.d.ts +25 -0
- package/dist/types/chrome/collab-qrcode.d.ts +7 -0
- package/dist/types/chrome/context-thresholds.d.ts +11 -0
- package/dist/types/chrome/countdown-timer.d.ts +9 -3
- package/dist/types/chrome/diff.d.ts +12 -0
- package/dist/types/chrome/dynamic-border.d.ts +3 -0
- package/dist/types/chrome/format.d.ts +6 -0
- package/dist/types/chrome/message-divider.d.ts +13 -0
- package/dist/types/chrome/message-frame.d.ts +10 -0
- package/dist/types/chrome/message-notice.d.ts +23 -0
- package/dist/types/chrome/overlay-box.d.ts +11 -2
- package/dist/types/chrome/qrcode.d.ts +7 -0
- package/dist/types/chrome/segment-track.d.ts +7 -0
- package/dist/types/chrome/selector-helpers.d.ts +0 -6
- package/dist/types/chrome/status-notice.d.ts +14 -0
- package/dist/types/chrome/streaming-panel.d.ts +3 -0
- package/dist/types/chrome/tool-activity.d.ts +3 -0
- package/dist/types/chrome/transcript-container.d.ts +13 -0
- package/dist/types/chrome/transcript-status.d.ts +15 -3
- package/dist/types/components/box.d.ts +7 -0
- package/dist/types/components/disclosure.d.ts +9 -0
- package/dist/types/components/editor.d.ts +42 -0
- package/dist/types/components/form.d.ts +14 -0
- package/dist/types/components/image.d.ts +7 -0
- package/dist/types/components/input.d.ts +20 -1
- package/dist/types/components/key-value-list.d.ts +3 -0
- package/dist/types/components/layout/geometry.d.ts +16 -0
- package/dist/types/components/layout/row.d.ts +7 -0
- package/dist/types/components/layout/split-pane.d.ts +8 -0
- package/dist/types/components/layout/stack.d.ts +6 -0
- package/dist/types/components/loader.d.ts +48 -0
- package/dist/types/components/markdown.d.ts +8 -0
- package/dist/types/components/metric.d.ts +7 -0
- package/dist/types/components/progress-bar.d.ts +3 -0
- package/dist/types/components/scroll-view.d.ts +6 -0
- package/dist/types/components/section.d.ts +3 -0
- package/dist/types/components/select-list.d.ts +33 -0
- package/dist/types/components/settings-list.d.ts +68 -0
- package/dist/types/components/spacer.d.ts +4 -0
- package/dist/types/components/tab-bar.d.ts +9 -0
- package/dist/types/components/table.d.ts +7 -0
- package/dist/types/components/text.d.ts +6 -0
- package/dist/types/components/tree-view.d.ts +9 -0
- package/dist/types/components/truncated-text.d.ts +3 -0
- package/dist/types/components/wizard-step.d.ts +6 -0
- package/dist/types/hotkeys-markdown.d.ts +24 -0
- package/dist/types/index.d.ts +5 -0
- package/dist/types/latex-block.d.ts +7 -0
- package/dist/types/loop-watchdog.d.ts +9 -0
- package/dist/types/native/apply.d.ts +39 -0
- package/dist/types/native/backend.d.ts +94 -0
- package/dist/types/native/blobs.d.ts +29 -0
- package/dist/types/native/describe.d.ts +56 -0
- package/dist/types/native/encode.d.ts +50 -0
- package/dist/types/native/icons.d.ts +18 -0
- package/dist/types/native/memo.d.ts +27 -0
- package/dist/types/native/node.d.ts +107 -0
- package/dist/types/native/overlay.d.ts +64 -0
- package/dist/types/native/picker.d.ts +124 -0
- package/dist/types/native/reconcile.d.ts +41 -0
- package/dist/types/native/settle.d.ts +11 -0
- package/dist/types/native/spans.d.ts +21 -0
- package/dist/types/native/state.d.ts +6 -0
- package/dist/types/native/tone.d.ts +24 -0
- package/dist/types/overlays/advisor-config.d.ts +20 -0
- package/dist/types/overlays/agent-hub-renderer.d.ts +27 -11
- package/dist/types/overlays/agent-hub.d.ts +10 -0
- package/dist/types/overlays/agent-transcript-viewer.d.ts +7 -0
- package/dist/types/overlays/agents-hub.d.ts +8 -0
- package/dist/types/overlays/annotation-overlay.d.ts +3 -0
- package/dist/types/overlays/ask-dialog.d.ts +23 -0
- package/dist/types/overlays/bordered-loader.d.ts +3 -0
- package/dist/types/overlays/btw-history-panel.d.ts +9 -0
- package/dist/types/overlays/btw-panel.d.ts +3 -0
- package/dist/types/overlays/cleanse-panel.d.ts +5 -2
- package/dist/types/overlays/composer-shape-preview.d.ts +7 -1
- package/dist/types/overlays/copy-selector.d.ts +38 -0
- package/dist/types/overlays/error-banner.d.ts +9 -0
- package/dist/types/overlays/extensions/extension-list.d.ts +1 -0
- package/dist/types/overlays/history-search.d.ts +18 -0
- package/dist/types/overlays/hook-editor.d.ts +28 -1
- package/dist/types/overlays/hook-input.d.ts +3 -0
- package/dist/types/overlays/hook-selector.d.ts +10 -0
- package/dist/types/overlays/hub-frame.d.ts +18 -0
- package/dist/types/overlays/jobs-panel.d.ts +24 -0
- package/dist/types/overlays/login-dialog.d.ts +10 -0
- package/dist/types/overlays/logout-account-selector.d.ts +4 -0
- package/dist/types/overlays/mcp-add-wizard.d.ts +4 -0
- package/dist/types/overlays/model-browser.d.ts +69 -0
- package/dist/types/overlays/model-hub.d.ts +7 -0
- package/dist/types/overlays/model-picker.d.ts +9 -1
- package/dist/types/overlays/move-overlay.d.ts +3 -0
- package/dist/types/overlays/oauth-selector.d.ts +4 -0
- package/dist/types/overlays/omfg-panel.d.ts +3 -0
- package/dist/types/overlays/pause-screen.d.ts +12 -0
- package/dist/types/overlays/plan-review-overlay.d.ts +5 -0
- package/dist/types/overlays/plan-save-overlay.d.ts +10 -0
- package/dist/types/overlays/plugin-selector.d.ts +4 -0
- package/dist/types/overlays/plugin-settings.d.ts +30 -0
- package/dist/types/overlays/queue-mode-selector.d.ts +4 -0
- package/dist/types/overlays/reset-usage-selector.d.ts +8 -0
- package/dist/types/overlays/rewind-selector.d.ts +5 -0
- package/dist/types/overlays/session-info-overlay.d.ts +19 -1
- package/dist/types/overlays/session-selector.d.ts +64 -1
- package/dist/types/overlays/settings-defs.d.ts +14 -0
- package/dist/types/overlays/settings-selector.d.ts +21 -0
- package/dist/types/overlays/show-images-selector.d.ts +4 -0
- package/dist/types/overlays/snapcompact-shape-preview.d.ts +2 -0
- package/dist/types/overlays/stats-notice.d.ts +8 -0
- package/dist/types/overlays/theme-selector.d.ts +11 -0
- package/dist/types/overlays/thinking-selector.d.ts +4 -0
- package/dist/types/overlays/tree-selector.d.ts +60 -2
- package/dist/types/overlays/usage-dashboard.d.ts +26 -3
- package/dist/types/overlays/usage-row.d.ts +36 -2
- package/dist/types/prompt/attachment-chips.d.ts +8 -0
- package/dist/types/prompt/composer-attachments.d.ts +15 -3
- package/dist/types/prompt/composer.d.ts +18 -1
- package/dist/types/prompt/custom-editor.d.ts +48 -2
- package/dist/types/prompt/editor-top-gap.d.ts +2 -0
- package/dist/types/prompt/macos-spelling.d.ts +6 -0
- package/dist/types/prompt/magic-keywords.d.ts +9 -0
- package/dist/types/prompt/queued-messages.d.ts +23 -0
- package/dist/types/prompt/skill-tokens.d.ts +4 -2
- package/dist/types/prompt/welcome.d.ts +16 -0
- package/dist/types/render/code-cell.d.ts +10 -0
- package/dist/types/render/file-list.d.ts +8 -0
- package/dist/types/render/hyperlink.d.ts +14 -0
- package/dist/types/render/output-block.d.ts +43 -0
- package/dist/types/render/output-pane.d.ts +17 -0
- package/dist/types/render/tool-card.d.ts +8 -0
- package/dist/types/render/tree-list.d.ts +8 -0
- package/dist/types/render/width-aware-text.d.ts +7 -0
- package/dist/types/setup/scenes/outro.d.ts +7 -0
- package/dist/types/setup/scenes/sign-in.d.ts +16 -9
- package/dist/types/setup/scenes/splash.d.ts +8 -0
- package/dist/types/setup/scenes/types.d.ts +6 -27
- package/dist/types/setup/wizard-overlay.d.ts +9 -0
- package/dist/types/status-line/component.d.ts +49 -5
- package/dist/types/status-line/context-usage.d.ts +20 -0
- package/dist/types/status-line/footer.d.ts +8 -0
- package/dist/types/status-line/metrics.d.ts +1 -2
- package/dist/types/status-line/segments.d.ts +10 -1
- package/dist/types/status-line/types.d.ts +40 -1
- package/dist/types/stdin-buffer.d.ts +10 -7
- package/dist/types/terminal-capabilities.d.ts +1 -1
- package/dist/types/terminal.d.ts +36 -0
- package/dist/types/theme/defaults/index.d.ts +100 -0
- package/dist/types/theme/schema.d.ts +2 -0
- package/dist/types/theme/shimmer.d.ts +8 -0
- package/dist/types/theme/theme-class.d.ts +2 -0
- package/dist/types/theme/theme.d.ts +33 -1
- package/dist/types/tools/ask.d.ts +3 -0
- package/dist/types/tools/ast-edit.d.ts +10 -1
- package/dist/types/tools/ast-grep.d.ts +10 -1
- package/dist/types/tools/autoresearch.d.ts +21 -4
- package/dist/types/tools/bash.d.ts +30 -1
- package/dist/types/tools/cfg-render.d.ts +5 -1
- package/dist/types/tools/debug.d.ts +3 -1
- package/dist/types/tools/default-renderer.d.ts +6 -1
- package/dist/types/tools/edit.d.ts +14 -1
- package/dist/types/tools/eval.d.ts +12 -1
- package/dist/types/tools/fetch.d.ts +16 -1
- package/dist/types/tools/find.d.ts +15 -1
- package/dist/types/tools/github.d.ts +3 -0
- package/dist/types/tools/glob.d.ts +14 -1
- package/dist/types/tools/goal.d.ts +3 -1
- package/dist/types/tools/grep.d.ts +14 -1
- package/dist/types/tools/grouped-file-output.d.ts +58 -0
- package/dist/types/tools/json-tree.d.ts +20 -0
- package/dist/types/tools/lsp.d.ts +3 -10
- package/dist/types/tools/mcp.d.ts +16 -1
- package/dist/types/tools/memory.d.ts +26 -0
- package/dist/types/tools/native-view.d.ts +90 -0
- package/dist/types/tools/proc-render.d.ts +7 -1
- package/dist/types/tools/read.d.ts +23 -1
- package/dist/types/tools/renderer.d.ts +57 -0
- package/dist/types/tools/report-tool-issue.d.ts +3 -0
- package/dist/types/tools/resolve.d.ts +14 -1
- package/dist/types/tools/task.d.ts +3 -0
- package/dist/types/tools/think.d.ts +3 -0
- package/dist/types/tools/todo.d.ts +12 -0
- package/dist/types/tools/vibe.d.ts +3 -1
- package/dist/types/tools/wait.d.ts +3 -0
- package/dist/types/tools/web-search-types.d.ts +90 -0
- package/dist/types/tools/web-search.d.ts +9 -168
- package/dist/types/tools/write.d.ts +14 -1
- package/dist/types/tools/xdev.d.ts +13 -0
- package/dist/types/tui.d.ts +49 -0
- package/package.json +9 -9
- package/src/apps/autoresearch-dashboard.ts +362 -4
- package/src/apps/cleanse-board.ts +219 -1
- package/src/apps/cleanse-picker.ts +9 -1
- package/src/apps/debug/log-viewer.ts +15 -15
- package/src/apps/debug/protocol-probe.ts +2 -20
- package/src/apps/git/avatar.ts +2 -22
- package/src/apps/git/git-tui.ts +406 -59
- package/src/apps/git/help.ts +130 -0
- package/src/apps/git/sidebar.ts +491 -0
- package/src/apps/live-visualizer.ts +65 -0
- package/src/apps/ps-top.ts +448 -17
- package/src/apps/session-picker.ts +1 -0
- package/src/apps/setup-model-picker.ts +5 -1
- package/src/apps/standalone-picker.ts +55 -1
- package/src/autocomplete.ts +44 -1
- package/src/chat/advisor-message.ts +72 -3
- package/src/chat/assistant-message.ts +538 -51
- package/src/chat/background-tan-message.ts +4 -4
- package/src/chat/bash-execution.ts +81 -0
- package/src/chat/cache-invalidation-marker.ts +8 -0
- package/src/chat/chat-transcript-builder.ts +37 -6
- package/src/chat/collab-prompt-message.ts +15 -3
- package/src/chat/compaction-summary-message.ts +74 -1
- package/src/chat/custom-message.ts +3 -1
- package/src/chat/eval-execution.ts +57 -0
- package/src/chat/execution-shared.ts +153 -1
- package/src/chat/hook-message.ts +1 -0
- package/src/chat/late-diagnostics-message.ts +85 -2
- package/src/chat/read-tool-group.ts +341 -1
- package/src/chat/served-model-marker.ts +8 -0
- package/src/chat/skill-message.ts +63 -0
- package/src/chat/stripped-tool-calls-placeholder.ts +18 -10
- package/src/chat/thinking-display.ts +73 -11
- package/src/chat/todo-reminder.ts +34 -4
- package/src/chat/tool-execution.ts +385 -10
- package/src/chat/transcript-actions.ts +38 -0
- package/src/chat/transcript-browser.ts +2 -9
- package/src/chat/transcript-entry.ts +10 -1
- package/src/chat/transcript-render-helpers.ts +16 -15
- package/src/chat/ttsr-notification.ts +38 -1
- package/src/chat/user-message.ts +167 -4
- package/src/chrome/collab-qrcode.ts +27 -2
- package/src/chrome/context-thresholds.ts +34 -0
- package/src/chrome/countdown-timer.ts +24 -1
- package/src/chrome/diff.ts +60 -1
- package/src/chrome/dynamic-border.ts +7 -0
- package/src/chrome/format.ts +12 -0
- package/src/chrome/message-divider.ts +33 -1
- package/src/chrome/message-frame.ts +53 -10
- package/src/chrome/message-notice.ts +71 -0
- package/src/chrome/overlay-box.ts +45 -2
- package/src/chrome/qrcode.ts +28 -0
- package/src/chrome/segment-track.ts +26 -0
- package/src/chrome/selector-helpers.ts +1 -17
- package/src/chrome/status-notice.ts +46 -0
- package/src/chrome/streaming-panel.ts +25 -1
- package/src/chrome/tool-activity.ts +20 -0
- package/src/chrome/transcript-container.ts +139 -17
- package/src/chrome/transcript-status.ts +40 -11
- package/src/components/box.ts +51 -0
- package/src/components/disclosure.ts +33 -0
- package/src/components/editor.ts +239 -36
- package/src/components/form.ts +93 -9
- package/src/components/image.ts +30 -0
- package/src/components/input.ts +77 -26
- package/src/components/key-value-list.ts +18 -0
- package/src/components/layout/geometry.ts +44 -0
- package/src/components/layout/row.ts +30 -0
- package/src/components/layout/split-pane.ts +65 -0
- package/src/components/layout/stack.ts +27 -0
- package/src/components/loader.ts +183 -1
- package/src/components/markdown.ts +131 -56
- package/src/components/metric.ts +39 -0
- package/src/components/progress-bar.ts +28 -0
- package/src/components/scroll-view.ts +23 -0
- package/src/components/section.ts +16 -0
- package/src/components/select-list.ts +174 -25
- package/src/components/settings-list.ts +264 -7
- package/src/components/spacer.ts +17 -0
- package/src/components/tab-bar.ts +42 -0
- package/src/components/table.ts +34 -0
- package/src/components/text.ts +23 -0
- package/src/components/tree-view.ts +65 -0
- package/src/components/truncated-text.ts +14 -0
- package/src/components/wizard-step.ts +18 -9
- package/src/debug-server.ts +14 -7
- package/src/hotkeys-markdown.ts +251 -69
- package/src/index.ts +6 -0
- package/src/latex-block.ts +11 -0
- package/src/loop-watchdog.ts +38 -10
- package/src/native/apply.ts +275 -0
- package/src/native/backend.ts +682 -0
- package/src/native/blobs.ts +70 -0
- package/src/native/describe.ts +124 -0
- package/src/native/encode.ts +233 -0
- package/src/native/icons.ts +184 -0
- package/src/native/memo.ts +64 -0
- package/src/native/node.ts +112 -0
- package/src/native/overlay.ts +131 -0
- package/src/native/picker.ts +333 -0
- package/src/native/reconcile.ts +1063 -0
- package/src/native/settle.ts +23 -0
- package/src/native/spans.ts +308 -0
- package/src/native/state.ts +28 -0
- package/src/native/tone.ts +79 -0
- package/src/overlays/advisor-config.ts +420 -0
- package/src/overlays/agent-hub-renderer.ts +155 -18
- package/src/overlays/agent-hub.ts +1037 -44
- package/src/overlays/agent-transcript-viewer.ts +129 -0
- package/src/overlays/agents-hub.ts +688 -53
- package/src/overlays/annotation-overlay.ts +391 -52
- package/src/overlays/ask-dialog.ts +435 -24
- package/src/overlays/bordered-loader.ts +17 -0
- package/src/overlays/btw-history-panel.ts +182 -0
- package/src/overlays/btw-panel.ts +68 -2
- package/src/overlays/cleanse-panel.ts +105 -15
- package/src/overlays/codex-reset-fireworks.ts +65 -5
- package/src/overlays/composer-shape-preview.ts +26 -1
- package/src/overlays/copy-selector.ts +545 -23
- package/src/overlays/error-banner.ts +44 -0
- package/src/overlays/extensions/extension-list.ts +23 -17
- package/src/overlays/history-search.ts +175 -33
- package/src/overlays/hook-editor.ts +113 -6
- package/src/overlays/hook-input.ts +22 -1
- package/src/overlays/hook-selector.ts +311 -22
- package/src/overlays/hub-frame.ts +80 -0
- package/src/overlays/jobs-panel.ts +112 -0
- package/src/overlays/login-dialog.ts +183 -1
- package/src/overlays/logout-account-selector.ts +102 -4
- package/src/overlays/mcp-add-wizard.ts +232 -53
- package/src/overlays/model-browser.ts +681 -22
- package/src/overlays/model-hub.ts +1402 -78
- package/src/overlays/model-picker.ts +184 -7
- package/src/overlays/move-overlay.ts +45 -0
- package/src/overlays/oauth-selector.ts +227 -23
- package/src/overlays/omfg-panel.ts +86 -2
- package/src/overlays/pause-screen.ts +55 -4
- package/src/overlays/plan-review-overlay.ts +352 -0
- package/src/overlays/plan-save-overlay.ts +45 -0
- package/src/overlays/plugin-selector.ts +21 -1
- package/src/overlays/plugin-settings.ts +195 -5
- package/src/overlays/queue-mode-selector.ts +19 -1
- package/src/overlays/reset-usage-selector.ts +110 -40
- package/src/overlays/rewind-selector.ts +458 -44
- package/src/overlays/session-account-selector.ts +1 -1
- package/src/overlays/session-info-overlay.ts +137 -1
- package/src/overlays/session-selector.ts +807 -46
- package/src/overlays/settings-defs.ts +41 -0
- package/src/overlays/settings-selector.ts +585 -33
- package/src/overlays/show-images-selector.ts +18 -1
- package/src/overlays/snapcompact-shape-preview.ts +48 -3
- package/src/overlays/stats-notice.ts +31 -0
- package/src/overlays/theme-selector.ts +31 -1
- package/src/overlays/thinking-selector.ts +22 -1
- package/src/overlays/tree-selector.ts +570 -110
- package/src/overlays/usage-dashboard.ts +587 -12
- package/src/overlays/usage-row.ts +161 -25
- package/src/prompt/attachment-chips.ts +60 -0
- package/src/prompt/composer-attachments.ts +31 -9
- package/src/prompt/composer.ts +55 -2
- package/src/prompt/custom-editor.ts +302 -4
- package/src/prompt/editor-top-gap.ts +8 -0
- package/src/prompt/macos-spelling.ts +24 -9
- package/src/prompt/magic-keywords.ts +22 -1
- package/src/prompt/model-mention-autocomplete.ts +1 -0
- package/src/prompt/queued-messages.ts +101 -0
- package/src/prompt/skill-tokens.ts +5 -3
- package/src/prompt/welcome.ts +213 -6
- package/src/render/code-cell.ts +103 -2
- package/src/render/file-list.ts +29 -0
- package/src/render/hyperlink.ts +32 -0
- package/src/render/output-block.ts +110 -0
- package/src/render/output-pane.ts +37 -0
- package/src/render/tool-card.ts +137 -0
- package/src/render/tree-list.ts +39 -0
- package/src/render/width-aware-text.ts +20 -0
- package/src/setup/scenes/composer.ts +29 -0
- package/src/setup/scenes/glyph.ts +15 -0
- package/src/setup/scenes/model.ts +36 -8
- package/src/setup/scenes/outro.ts +28 -1
- package/src/setup/scenes/sign-in.ts +138 -24
- package/src/setup/scenes/splash.ts +28 -1
- package/src/setup/scenes/theme.ts +88 -3
- package/src/setup/scenes/types.ts +7 -28
- package/src/setup/startup-splash.ts +46 -9
- package/src/setup/wizard-overlay.ts +140 -23
- package/src/setup/wizard.ts +1 -1
- package/src/status-line/component.ts +414 -18
- package/src/status-line/context-usage.ts +279 -50
- package/src/status-line/footer.ts +94 -1
- package/src/status-line/metrics.ts +3 -6
- package/src/status-line/segments.ts +463 -97
- package/src/status-line/separators.ts +3 -16
- package/src/status-line/types.ts +43 -1
- package/src/stdin-buffer.ts +27 -21
- package/src/terminal-capabilities.ts +7 -0
- package/src/terminal.ts +153 -11
- package/src/theme/defaults/dark-neon-noir.json +100 -0
- package/src/theme/defaults/index.ts +2 -0
- package/src/theme/defaults/light-prism.json +5 -5
- package/src/theme/defaults/onyx.json +62 -62
- package/src/theme/mermaid-cache.ts +10 -1
- package/src/theme/schema.ts +15 -0
- package/src/theme/shimmer.ts +33 -0
- package/src/theme/theme-class.ts +24 -19
- package/src/theme/theme.ts +111 -9
- package/src/theme/tui-adapters.ts +14 -1
- package/src/tools/ask.ts +157 -1
- package/src/tools/ast-edit.ts +174 -1
- package/src/tools/ast-grep.ts +82 -2
- package/src/tools/autoresearch.ts +149 -1
- package/src/tools/bash.ts +233 -62
- package/src/tools/cfg-render.ts +66 -1
- package/src/tools/debug.ts +78 -1
- package/src/tools/default-renderer.ts +35 -1
- package/src/tools/edit.ts +357 -31
- package/src/tools/eval.ts +257 -1
- package/src/tools/fetch.ts +102 -3
- package/src/tools/find.ts +127 -1
- package/src/tools/github.ts +119 -10
- package/src/tools/glob.ts +116 -1
- package/src/tools/goal.ts +56 -1
- package/src/tools/grep.ts +83 -2
- package/src/tools/grouped-file-output.ts +205 -0
- package/src/tools/json-tree.ts +116 -1
- package/src/tools/lsp.ts +318 -1
- package/src/tools/mcp.ts +80 -1
- package/src/tools/memory.ts +93 -11
- package/src/tools/native-view.ts +292 -0
- package/src/tools/proc-render.ts +221 -1
- package/src/tools/read.ts +199 -4
- package/src/tools/renderer.ts +61 -0
- package/src/tools/report-tool-issue.ts +7 -1
- package/src/tools/resolve.ts +63 -1
- package/src/tools/streaming-output.ts +79 -16
- package/src/tools/task.ts +406 -4
- package/src/tools/think.ts +19 -1
- package/src/tools/todo.ts +89 -0
- package/src/tools/vibe.ts +230 -2
- package/src/tools/wait.ts +181 -1
- package/src/tools/web-search-types.ts +99 -0
- package/src/tools/web-search.ts +111 -170
- package/src/tools/write.ts +144 -5
- package/src/tools/xdev.ts +64 -1
- package/src/tui.ts +295 -4
- package/dist/types/setup/scenes/providers.d.ts +0 -3
- package/dist/types/setup/scenes/web-search.d.ts +0 -22
- package/src/setup/scenes/providers.ts +0 -110
- package/src/setup/scenes/web-search.ts +0 -165
|
@@ -16,76 +16,76 @@
|
|
|
16
16
|
"emerald": "#6fb37f"
|
|
17
17
|
},
|
|
18
18
|
"colors": {
|
|
19
|
-
"accent": "
|
|
20
|
-
"border": "
|
|
21
|
-
"borderAccent": "
|
|
22
|
-
"borderMuted": "
|
|
23
|
-
"success": "
|
|
24
|
-
"error": "
|
|
25
|
-
"warning": "
|
|
26
|
-
"muted": "
|
|
19
|
+
"accent": "vein",
|
|
20
|
+
"border": "band2",
|
|
21
|
+
"borderAccent": "vein",
|
|
22
|
+
"borderMuted": "band1",
|
|
23
|
+
"success": "emerald",
|
|
24
|
+
"error": "ruby",
|
|
25
|
+
"warning": "bronze",
|
|
26
|
+
"muted": "warmGray",
|
|
27
27
|
"dim": "#6a6760",
|
|
28
28
|
"text": "",
|
|
29
|
-
"thinkingText": "
|
|
30
|
-
"selectedBg": "
|
|
31
|
-
"userMessageBg": "
|
|
29
|
+
"thinkingText": "warmGray",
|
|
30
|
+
"selectedBg": "band2",
|
|
31
|
+
"userMessageBg": "band1",
|
|
32
32
|
"userMessageText": "",
|
|
33
|
-
"customMessageBg": "
|
|
33
|
+
"customMessageBg": "band2",
|
|
34
34
|
"customMessageText": "",
|
|
35
|
-
"customMessageLabel": "
|
|
36
|
-
"toolPendingBg": "
|
|
37
|
-
"toolSuccessBg": "
|
|
38
|
-
"toolErrorBg": "
|
|
35
|
+
"customMessageLabel": "vein",
|
|
36
|
+
"toolPendingBg": "band1",
|
|
37
|
+
"toolSuccessBg": "band1",
|
|
38
|
+
"toolErrorBg": "band1",
|
|
39
39
|
"toolTitle": "",
|
|
40
|
-
"toolOutput": "
|
|
41
|
-
"mdHeading": "
|
|
42
|
-
"mdLink": "
|
|
43
|
-
"mdLinkUrl": "
|
|
44
|
-
"mdCode": "
|
|
45
|
-
"mdCodeBlock": "
|
|
46
|
-
"mdCodeBlockBorder": "
|
|
47
|
-
"mdQuote": "
|
|
48
|
-
"mdQuoteBorder": "
|
|
49
|
-
"mdHr": "
|
|
50
|
-
"mdListBullet": "
|
|
51
|
-
"toolDiffAdded": "
|
|
52
|
-
"toolDiffRemoved": "
|
|
53
|
-
"toolDiffContext": "
|
|
40
|
+
"toolOutput": "warmGray",
|
|
41
|
+
"mdHeading": "vein",
|
|
42
|
+
"mdLink": "bronze",
|
|
43
|
+
"mdLinkUrl": "copper",
|
|
44
|
+
"mdCode": "vein",
|
|
45
|
+
"mdCodeBlock": "cream",
|
|
46
|
+
"mdCodeBlockBorder": "band3",
|
|
47
|
+
"mdQuote": "warmGray",
|
|
48
|
+
"mdQuoteBorder": "veinDim",
|
|
49
|
+
"mdHr": "band2",
|
|
50
|
+
"mdListBullet": "vein",
|
|
51
|
+
"toolDiffAdded": "emerald",
|
|
52
|
+
"toolDiffRemoved": "ruby",
|
|
53
|
+
"toolDiffContext": "warmGray",
|
|
54
54
|
"syntaxComment": "#6a6760",
|
|
55
|
-
"syntaxKeyword": "
|
|
56
|
-
"syntaxFunction": "
|
|
57
|
-
"syntaxVariable": "
|
|
58
|
-
"syntaxString": "
|
|
59
|
-
"syntaxNumber": "
|
|
60
|
-
"syntaxType": "
|
|
61
|
-
"syntaxOperator": "
|
|
62
|
-
"syntaxPunctuation": "
|
|
63
|
-
"thinkingOff": "
|
|
64
|
-
"thinkingMinimal": "
|
|
65
|
-
"thinkingLow": "
|
|
66
|
-
"thinkingMedium": "
|
|
67
|
-
"thinkingHigh": "
|
|
68
|
-
"thinkingXhigh": "
|
|
69
|
-
"bashMode": "
|
|
70
|
-
"statusLineBg": "
|
|
71
|
-
"statusLineSep": "
|
|
72
|
-
"statusLineModel": "
|
|
73
|
-
"statusLinePath": "
|
|
74
|
-
"statusLineGitClean": "
|
|
75
|
-
"statusLineGitDirty": "
|
|
76
|
-
"statusLineContext": "
|
|
77
|
-
"statusLineSpend": "
|
|
78
|
-
"statusLineStaged": "
|
|
79
|
-
"statusLineDirty": "
|
|
80
|
-
"statusLineUntracked": "
|
|
81
|
-
"statusLineOutput": "
|
|
82
|
-
"statusLineCost": "
|
|
83
|
-
"statusLineSubagents": "
|
|
55
|
+
"syntaxKeyword": "vein",
|
|
56
|
+
"syntaxFunction": "bronze",
|
|
57
|
+
"syntaxVariable": "cream",
|
|
58
|
+
"syntaxString": "copper",
|
|
59
|
+
"syntaxNumber": "veinDim",
|
|
60
|
+
"syntaxType": "vein",
|
|
61
|
+
"syntaxOperator": "warmGray",
|
|
62
|
+
"syntaxPunctuation": "warmGray",
|
|
63
|
+
"thinkingOff": "warmGray",
|
|
64
|
+
"thinkingMinimal": "warmGray",
|
|
65
|
+
"thinkingLow": "warmGray",
|
|
66
|
+
"thinkingMedium": "veinDim",
|
|
67
|
+
"thinkingHigh": "vein",
|
|
68
|
+
"thinkingXhigh": "bronze",
|
|
69
|
+
"bashMode": "vein",
|
|
70
|
+
"statusLineBg": "band1",
|
|
71
|
+
"statusLineSep": "band3",
|
|
72
|
+
"statusLineModel": "vein",
|
|
73
|
+
"statusLinePath": "cream",
|
|
74
|
+
"statusLineGitClean": "emerald",
|
|
75
|
+
"statusLineGitDirty": "bronze",
|
|
76
|
+
"statusLineContext": "warmGray",
|
|
77
|
+
"statusLineSpend": "copper",
|
|
78
|
+
"statusLineStaged": "emerald",
|
|
79
|
+
"statusLineDirty": "bronze",
|
|
80
|
+
"statusLineUntracked": "warmGray",
|
|
81
|
+
"statusLineOutput": "cream",
|
|
82
|
+
"statusLineCost": "copper",
|
|
83
|
+
"statusLineSubagents": "vein",
|
|
84
84
|
"pythonMode": "#f0c040"
|
|
85
85
|
},
|
|
86
86
|
"export": {
|
|
87
|
-
"pageBg": "
|
|
88
|
-
"cardBg": "
|
|
89
|
-
"infoBg": "
|
|
87
|
+
"pageBg": "stone",
|
|
88
|
+
"cardBg": "band1",
|
|
89
|
+
"infoBg": "band2"
|
|
90
90
|
}
|
|
91
91
|
}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { MermaidRenderOptions } from "@oh-my-pi/pi-natives";
|
|
2
|
+
import { LRUCache } from "@oh-my-pi/pi-utils/lru";
|
|
2
3
|
import * as mermaidAscii from "@oh-my-pi/pi-utils/mermaid-ascii";
|
|
3
4
|
|
|
4
5
|
/**
|
|
@@ -19,7 +20,15 @@ export interface MermaidResolveOptions extends MermaidRenderOptions {
|
|
|
19
20
|
// Memoizes rendered ASCII (and failures) keyed on the render options + the
|
|
20
21
|
// layout-direction variant + source. Width selection happens per call against
|
|
21
22
|
// the cached renders, so a terminal resize re-decides without re-rendering.
|
|
22
|
-
|
|
23
|
+
// Bounded by entry count and by UTF-16 length of key (which embeds the whole
|
|
24
|
+
// source) plus rendered ASCII, so long sessions cannot pin every diagram.
|
|
25
|
+
const MERMAID_CACHE_MAX = 256;
|
|
26
|
+
const MERMAID_CACHE_MAX_SIZE = 4 * 1024 * 1024;
|
|
27
|
+
const cache = new LRUCache<string, string | null>({
|
|
28
|
+
max: MERMAID_CACHE_MAX,
|
|
29
|
+
maxSize: MERMAID_CACHE_MAX_SIZE,
|
|
30
|
+
sizeCalculation: (ascii, key) => key.length + (ascii?.length ?? 0),
|
|
31
|
+
});
|
|
23
32
|
|
|
24
33
|
/** Display columns, ignoring ANSI so themed diagrams are measured as drawn. */
|
|
25
34
|
const DISPLAY_WIDTH = { countAnsiEscapeCodes: false } as const;
|
package/src/theme/schema.ts
CHANGED
|
@@ -165,4 +165,19 @@ export type ThemeBg =
|
|
|
165
165
|
| "toolErrorBg"
|
|
166
166
|
| "statusLineBg";
|
|
167
167
|
|
|
168
|
+
const VALID_THEME_BGS: ReadonlySet<string> = new Set([
|
|
169
|
+
"selectedBg",
|
|
170
|
+
"userMessageBg",
|
|
171
|
+
"customMessageBg",
|
|
172
|
+
"toolPendingBg",
|
|
173
|
+
"toolSuccessBg",
|
|
174
|
+
"toolErrorBg",
|
|
175
|
+
"statusLineBg",
|
|
176
|
+
] satisfies ThemeBg[]);
|
|
177
|
+
|
|
178
|
+
/** Check if a string is a valid ThemeBg value */
|
|
179
|
+
export function isValidThemeBg(color: string): color is ThemeBg {
|
|
180
|
+
return VALID_THEME_BGS.has(color);
|
|
181
|
+
}
|
|
182
|
+
|
|
168
183
|
export type ColorMode = "truecolor" | "256color";
|
package/src/theme/shimmer.ts
CHANGED
|
@@ -1,3 +1,7 @@
|
|
|
1
|
+
import type { TspSpan } from "@oh-my-pi/pi-wire";
|
|
2
|
+
import { node } from "../native/describe";
|
|
3
|
+
import type { NativeNode } from "../native/node";
|
|
4
|
+
import { isNativeRendering } from "../native/state";
|
|
1
5
|
import type { Theme, ThemeColor } from "./theme";
|
|
2
6
|
import { FG_RESET } from "./color";
|
|
3
7
|
|
|
@@ -151,6 +155,28 @@ export function shimmerEnabled(): boolean {
|
|
|
151
155
|
return activeMode !== "disabled";
|
|
152
156
|
}
|
|
153
157
|
|
|
158
|
+
/**
|
|
159
|
+
* Describe shimmering segments for a TSP terminal, which clocks the sweep
|
|
160
|
+
* itself: a `shimmer` node in the active mode, or plain spans in the mid tier
|
|
161
|
+
* color when shimmer is disabled. Palette tiers given as theme colors travel as
|
|
162
|
+
* token names; raw-ANSI tiers are dropped (the terminal's theme decides).
|
|
163
|
+
*/
|
|
164
|
+
export function describeShimmer(segments: readonly ShimmerSegment[], key?: string): NativeNode {
|
|
165
|
+
const spans: TspSpan[] = [];
|
|
166
|
+
for (const { text: value, palette } of segments) {
|
|
167
|
+
if (value.length === 0) continue;
|
|
168
|
+
const mid = (palette ?? DEFAULT_SHIMMER_PALETTE).mid;
|
|
169
|
+
spans.push(typeof mid === "string" ? { t: value, s: mid } : { t: value });
|
|
170
|
+
}
|
|
171
|
+
if (activeMode === "disabled") return node("text", { spans }, undefined, key);
|
|
172
|
+
const palette = segments[0]?.palette ?? DEFAULT_SHIMMER_PALETTE;
|
|
173
|
+
const tokens: { low?: string; mid?: string; high?: string } = {};
|
|
174
|
+
if (typeof palette.low === "string") tokens.low = palette.low;
|
|
175
|
+
if (typeof palette.mid === "string") tokens.mid = palette.mid;
|
|
176
|
+
if (typeof palette.high === "string") tokens.high = palette.high;
|
|
177
|
+
return node("shimmer", { spans, mode: activeMode, palette: tokens }, undefined, key);
|
|
178
|
+
}
|
|
179
|
+
|
|
154
180
|
/**
|
|
155
181
|
* Apply a shimmer sweep across one or more segments, treating them as a
|
|
156
182
|
* single continuous string for band positioning. Each segment can supply
|
|
@@ -165,6 +191,13 @@ export function shimmerEnabled(): boolean {
|
|
|
165
191
|
* - No per-char allocations beyond the run buffer.
|
|
166
192
|
*/
|
|
167
193
|
export function shimmerSegments(segments: readonly ShimmerSegment[], theme: ShimmerTheme): string {
|
|
194
|
+
// A TSP terminal animates shimmer from described nodes; a frame painted
|
|
195
|
+
// here would freeze mid-sweep, so the text goes out unstyled.
|
|
196
|
+
if (isNativeRendering()) {
|
|
197
|
+
let out = "";
|
|
198
|
+
for (const { text: value } of segments) out += value;
|
|
199
|
+
return out;
|
|
200
|
+
}
|
|
168
201
|
const mode = activeMode;
|
|
169
202
|
|
|
170
203
|
// Disabled: no animation or code-point scan. Preserve the all-empty result,
|
package/src/theme/theme-class.ts
CHANGED
|
@@ -140,6 +140,26 @@ const underlineStyler = chalk.underline;
|
|
|
140
140
|
const strikethroughStyler = chalk.strikethrough;
|
|
141
141
|
const inverseStyler = chalk.inverse;
|
|
142
142
|
|
|
143
|
+
/** Theme token of a thinking/effort level name (`off`…`max`); unknown levels (`auto`) map to `thinkingOff`. */
|
|
144
|
+
export function thinkingLevelToken(level: string): ThemeColor {
|
|
145
|
+
switch (level) {
|
|
146
|
+
case "minimal":
|
|
147
|
+
return "thinkingMinimal";
|
|
148
|
+
case "low":
|
|
149
|
+
return "thinkingLow";
|
|
150
|
+
case "medium":
|
|
151
|
+
return "thinkingMedium";
|
|
152
|
+
case "high":
|
|
153
|
+
return "thinkingHigh";
|
|
154
|
+
case "xhigh":
|
|
155
|
+
return "thinkingXhigh";
|
|
156
|
+
case "max":
|
|
157
|
+
return "thinkingMax";
|
|
158
|
+
default:
|
|
159
|
+
return "thinkingOff";
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
|
|
143
163
|
export class Theme {
|
|
144
164
|
#fgColors: Record<ThemeColor, string>;
|
|
145
165
|
#bgColors: Record<ThemeBg, string>;
|
|
@@ -419,25 +439,10 @@ export class Theme {
|
|
|
419
439
|
|
|
420
440
|
/** Border color for a thinking/effort level name (`off`…`max`); unknown levels fall back to `thinkingOff`. */
|
|
421
441
|
getThinkingBorderColor(level: string): (str: string) => string {
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
return (str: string) => this.fg("thinkingMinimal", str);
|
|
427
|
-
case "low":
|
|
428
|
-
return (str: string) => this.fg("thinkingLow", str);
|
|
429
|
-
case "medium":
|
|
430
|
-
return (str: string) => this.fg("thinkingMedium", str);
|
|
431
|
-
case "high":
|
|
432
|
-
return (str: string) => this.fg("thinkingHigh", str);
|
|
433
|
-
case "xhigh":
|
|
434
|
-
return (str: string) => this.fg("thinkingXhigh", str);
|
|
435
|
-
case "max":
|
|
436
|
-
// thinkingMax is optional; themes without it resolve to the xhigh color.
|
|
437
|
-
return (str: string) => this.fg(this.#fgColors.thinkingMax ? "thinkingMax" : "thinkingXhigh", str);
|
|
438
|
-
default:
|
|
439
|
-
return (str: string) => this.fg("thinkingOff", str);
|
|
440
|
-
}
|
|
442
|
+
const token = thinkingLevelToken(level);
|
|
443
|
+
// thinkingMax is optional; themes without it resolve to the xhigh color.
|
|
444
|
+
const color = token === "thinkingMax" && !this.#fgColors.thinkingMax ? "thinkingXhigh" : token;
|
|
445
|
+
return (str: string) => this.fg(color, str);
|
|
441
446
|
}
|
|
442
447
|
|
|
443
448
|
getBashModeBorderColor(): (str: string) => string {
|
package/src/theme/theme.ts
CHANGED
|
@@ -7,8 +7,16 @@ import { getCustomThemesDir } from "@oh-my-pi/pi-utils/dirs";
|
|
|
7
7
|
import * as logger from "@oh-my-pi/pi-utils/logger";
|
|
8
8
|
import { setActiveSymbolTheme } from "./active-symbols";
|
|
9
9
|
import { ansi256ToHex, resolveThemeColors, resolveVarRefs } from "./color";
|
|
10
|
-
import {
|
|
11
|
-
|
|
10
|
+
import {
|
|
11
|
+
type CreateThemeOptions,
|
|
12
|
+
createTheme,
|
|
13
|
+
getBuiltinThemes,
|
|
14
|
+
loadTheme,
|
|
15
|
+
loadThemeJson,
|
|
16
|
+
loadThemeJsonSync,
|
|
17
|
+
loadThemeSync,
|
|
18
|
+
} from "./loader";
|
|
19
|
+
import { isValidThemeBg, isValidThemeColor, type ThemeColor, type ThemeJson } from "./schema";
|
|
12
20
|
import type { SymbolPreset } from "./symbols";
|
|
13
21
|
import type { Theme } from "./theme-class";
|
|
14
22
|
|
|
@@ -84,6 +92,8 @@ function getDefaultTheme(): string {
|
|
|
84
92
|
/** Active theme; imports remain live across initialization, previews, and theme switches. */
|
|
85
93
|
export var theme: Theme;
|
|
86
94
|
var currentThemeName: string | undefined;
|
|
95
|
+
/** Theme shown by `previewTheme` until the next non-preview assignment. */
|
|
96
|
+
var previewThemeName: string | undefined;
|
|
87
97
|
|
|
88
98
|
type ThemeBinding = (value: Theme) => void;
|
|
89
99
|
var themeBindings: Set<ThemeBinding> | undefined;
|
|
@@ -98,8 +108,10 @@ export function bindTheme(binding: ThemeBinding): () => void {
|
|
|
98
108
|
};
|
|
99
109
|
}
|
|
100
110
|
|
|
101
|
-
|
|
111
|
+
/** `previewName` marks a theme-selector preview; any other assignment ends it. */
|
|
112
|
+
function assignTheme(value: Theme, previewName?: string): void {
|
|
102
113
|
theme = value;
|
|
114
|
+
previewThemeName = previewName;
|
|
103
115
|
setActiveSymbolTheme(value);
|
|
104
116
|
if (themeBindings) {
|
|
105
117
|
for (const binding of themeBindings) binding(value);
|
|
@@ -121,6 +133,9 @@ export interface ThemeChangeEvent {
|
|
|
121
133
|
}
|
|
122
134
|
|
|
123
135
|
var currentSymbolPresetOverride: SymbolPreset | undefined;
|
|
136
|
+
// Process-local preset forced while a Tern Surface Protocol surface is live;
|
|
137
|
+
// wins over the user's preset and is never persisted.
|
|
138
|
+
var nativeSymbolPreset: SymbolPreset | undefined;
|
|
124
139
|
var currentColorBlindMode: boolean = false;
|
|
125
140
|
var themeWatcher: fs.FSWatcher | undefined;
|
|
126
141
|
var themeReloadTimer: NodeJS.Timeout | undefined;
|
|
@@ -134,7 +149,7 @@ let themeEpoch = 0;
|
|
|
134
149
|
|
|
135
150
|
function getCurrentThemeOptions(): CreateThemeOptions {
|
|
136
151
|
return {
|
|
137
|
-
symbolPresetOverride: currentSymbolPresetOverride,
|
|
152
|
+
symbolPresetOverride: nativeSymbolPreset ?? currentSymbolPresetOverride,
|
|
138
153
|
colorBlindMode: currentColorBlindMode,
|
|
139
154
|
};
|
|
140
155
|
}
|
|
@@ -162,10 +177,7 @@ export function initThemeSync(
|
|
|
162
177
|
lightTheme?: string,
|
|
163
178
|
): void {
|
|
164
179
|
const name = configureTheme(symbolPreset, colorBlindMode, darkTheme, lightTheme);
|
|
165
|
-
const options
|
|
166
|
-
symbolPresetOverride: currentSymbolPresetOverride,
|
|
167
|
-
colorBlindMode: currentColorBlindMode,
|
|
168
|
-
};
|
|
180
|
+
const options = getCurrentThemeOptions();
|
|
169
181
|
try {
|
|
170
182
|
assignTheme(loadThemeSync(name, options));
|
|
171
183
|
} catch (error) {
|
|
@@ -255,7 +267,8 @@ export async function previewTheme(
|
|
|
255
267
|
if (requestId !== themeLoadRequestId) {
|
|
256
268
|
return { success: false, error: "Theme preview superseded by a newer request" };
|
|
257
269
|
}
|
|
258
|
-
|
|
270
|
+
// Previewing the active theme again (selector cancel) ends the preview.
|
|
271
|
+
assignTheme(loadedTheme, name === currentThemeName ? undefined : name);
|
|
259
272
|
notifyThemeChange(event);
|
|
260
273
|
return { success: true };
|
|
261
274
|
} catch (error) {
|
|
@@ -337,6 +350,30 @@ export function getSymbolPresetOverride(): SymbolPreset | undefined {
|
|
|
337
350
|
return currentSymbolPresetOverride;
|
|
338
351
|
}
|
|
339
352
|
|
|
353
|
+
/**
|
|
354
|
+
* Force `preset` while a Tern Surface Protocol surface is live (the terminal's
|
|
355
|
+
* font carries every Nerd Font glyph, so icons need no Glyph Protocol
|
|
356
|
+
* registration); `undefined` restores the user's preset. Process-local and
|
|
357
|
+
* never persisted. Rebuilds the active theme synchronously so the next frame
|
|
358
|
+
* already uses it, and notifies theme listeners like a preset change. Returns
|
|
359
|
+
* whether the active theme was rebuilt (callers invalidate render caches).
|
|
360
|
+
*/
|
|
361
|
+
export function setNativeSymbolPreset(preset: SymbolPreset | undefined): boolean {
|
|
362
|
+
if (nativeSymbolPreset === preset) return false;
|
|
363
|
+
nativeSymbolPreset = preset;
|
|
364
|
+
if (!currentThemeName || typeof theme === "undefined") return false;
|
|
365
|
+
++themeLoadRequestId;
|
|
366
|
+
try {
|
|
367
|
+
assignTheme(loadThemeSync(currentThemeName, getCurrentThemeOptions()));
|
|
368
|
+
} catch (error) {
|
|
369
|
+
// In-memory themes can't be rebuilt by name; they keep their symbols.
|
|
370
|
+
logger.debug("Native symbol preset: theme rebuild skipped", { theme: currentThemeName, error: String(error) });
|
|
371
|
+
return false;
|
|
372
|
+
}
|
|
373
|
+
notifyThemeChange({ ephemeral: true });
|
|
374
|
+
return true;
|
|
375
|
+
}
|
|
376
|
+
|
|
340
377
|
/**
|
|
341
378
|
* Set color blind mode, recreating the theme with the new setting.
|
|
342
379
|
* When enabled, uses blue instead of green for diff additions.
|
|
@@ -770,6 +807,71 @@ export async function getResolvedThemeColors(themeName?: string): Promise<Record
|
|
|
770
807
|
return cssColors;
|
|
771
808
|
}
|
|
772
809
|
|
|
810
|
+
/** One appearance variant of {@link NativeThemePalette}: token name → `#rrggbb`. */
|
|
811
|
+
export type NativeThemeVariant = Record<string, string>;
|
|
812
|
+
|
|
813
|
+
/** omp's resolved theme for a Tern Surface Protocol terminal (the `t` verb body minus `sf`). */
|
|
814
|
+
export interface NativeThemePalette {
|
|
815
|
+
dark?: NativeThemeVariant;
|
|
816
|
+
light?: NativeThemeVariant;
|
|
817
|
+
name: { dark?: string; light?: string };
|
|
818
|
+
}
|
|
819
|
+
|
|
820
|
+
/**
|
|
821
|
+
* Cheap identity of everything {@link getNativeThemePalette} depends on;
|
|
822
|
+
* recompute the palette only when it changes.
|
|
823
|
+
*/
|
|
824
|
+
export function getNativeThemePaletteKey(): string {
|
|
825
|
+
return `${themeEpoch}|${autoDetectedTheme}|${autoDarkTheme}|${autoLightTheme}|${currentThemeName}|${previewThemeName}|${currentColorBlindMode}`;
|
|
826
|
+
}
|
|
827
|
+
|
|
828
|
+
/** Every token of theme `name` as hex (terminal-default tokens omitted), plus its export colours. */
|
|
829
|
+
function nativeThemeVariant(name: string): { light: boolean; colors: NativeThemeVariant } {
|
|
830
|
+
const themeJson = loadThemeJsonSync(name);
|
|
831
|
+
const built = createTheme(themeJson, getCurrentThemeOptions());
|
|
832
|
+
const raw = resolveThemeColors(themeJson.colors, themeJson.vars);
|
|
833
|
+
const colors: NativeThemeVariant = {};
|
|
834
|
+
for (const key in raw) {
|
|
835
|
+
// Terminal-default tokens stay unset; keys outside the schema are ignored like the theme does.
|
|
836
|
+
if (raw[key as keyof typeof raw] === "") continue;
|
|
837
|
+
if (isValidThemeColor(key)) colors[key] = built.getColorHex(key);
|
|
838
|
+
else if (isValidThemeBg(key)) colors[key] = built.getBgHex(key);
|
|
839
|
+
}
|
|
840
|
+
const exported = resolveThemeExportColors(themeJson);
|
|
841
|
+
for (const key of ["pageBg", "cardBg", "infoBg"] as const) {
|
|
842
|
+
const value = exported[key];
|
|
843
|
+
if (value) colors[key] = value;
|
|
844
|
+
}
|
|
845
|
+
return { light: isLightThemeJson(themeJson), colors };
|
|
846
|
+
}
|
|
847
|
+
|
|
848
|
+
/**
|
|
849
|
+
* omp's theme for a native surface: with auto theme, the configured dark and
|
|
850
|
+
* light themes; otherwise (or while the theme selector previews one) the
|
|
851
|
+
* active theme under its own appearance only. Themes without a loadable
|
|
852
|
+
* definition (in-memory instances) contribute nothing.
|
|
853
|
+
*/
|
|
854
|
+
export function getNativeThemePalette(): NativeThemePalette {
|
|
855
|
+
const palette: NativeThemePalette = { name: {} };
|
|
856
|
+
const add = (name: string, as?: "dark" | "light"): void => {
|
|
857
|
+
try {
|
|
858
|
+
const variant = nativeThemeVariant(name);
|
|
859
|
+
const slot = as ?? (variant.light ? "light" : "dark");
|
|
860
|
+
palette[slot] = variant.colors;
|
|
861
|
+
palette.name[slot] = name;
|
|
862
|
+
} catch (error) {
|
|
863
|
+
logger.debug("Native theme palette: theme not loadable", { name, error: String(error) });
|
|
864
|
+
}
|
|
865
|
+
};
|
|
866
|
+
const single = previewThemeName ?? (autoDetectedTheme ? undefined : currentThemeName);
|
|
867
|
+
if (single !== undefined) add(single);
|
|
868
|
+
else {
|
|
869
|
+
add(autoDarkTheme, "dark");
|
|
870
|
+
add(autoLightTheme, "light");
|
|
871
|
+
}
|
|
872
|
+
return palette;
|
|
873
|
+
}
|
|
874
|
+
|
|
773
875
|
/**
|
|
774
876
|
* Check if a theme is a "light" theme by analyzing its status-line background
|
|
775
877
|
* luminance. Loads theme JSON synchronously (built-in or custom file on disk)
|
|
@@ -59,7 +59,20 @@ function getHighlightColors(t: Theme): NativeHighlightColors {
|
|
|
59
59
|
* the 33ms frame budget and starving the spinner/render timers (the "TUI freeze").
|
|
60
60
|
*/
|
|
61
61
|
const HIGHLIGHT_CACHE_MAX = 256;
|
|
62
|
-
|
|
62
|
+
// Size-bound like markdown's render cache: a streaming block (bash command,
|
|
63
|
+
// eval cell) inserts one full `code + highlighted` pair per growth frame, so a
|
|
64
|
+
// count cap alone would retain 256 near-copies of a large payload. Sizes are
|
|
65
|
+
// UTF-16 code units of key + value (ANSI output runs several times the source
|
|
66
|
+
// length). The per-entry cap stays generous so a large but settled code body
|
|
67
|
+
// repainting every frame still hits; only payloads past it re-highlight.
|
|
68
|
+
const HIGHLIGHT_CACHE_MAX_SIZE = 8 * 1024 * 1024;
|
|
69
|
+
const HIGHLIGHT_CACHE_MAX_ENTRY_SIZE = 1024 * 1024;
|
|
70
|
+
const highlightCache = new LRUCache<string, string>({
|
|
71
|
+
max: HIGHLIGHT_CACHE_MAX,
|
|
72
|
+
maxSize: HIGHLIGHT_CACHE_MAX_SIZE,
|
|
73
|
+
maxEntrySize: HIGHLIGHT_CACHE_MAX_ENTRY_SIZE,
|
|
74
|
+
sizeCalculation: (value, key) => Math.max(1, key.length + value.length),
|
|
75
|
+
});
|
|
63
76
|
let highlightCacheTheme: Theme | undefined;
|
|
64
77
|
|
|
65
78
|
function highlightCached(code: string, validLang: string | undefined, highlightTheme: Theme): string | null {
|
package/src/tools/ask.ts
CHANGED
|
@@ -1,4 +1,10 @@
|
|
|
1
|
-
import type { ToolRenderer } from "./renderer";
|
|
1
|
+
import type { NativeToolHead, NativeToolView, ToolRenderer, ToolRenderResult } from "./renderer";
|
|
2
|
+
import type { TspSpan } from "@oh-my-pi/pi-wire";
|
|
3
|
+
import { compact, md, node, row, span, text } from "../native/describe";
|
|
4
|
+
import type { NativeChild, NativeNode } from "../native/node";
|
|
5
|
+
import { OwnerMemo } from "../native/memo";
|
|
6
|
+
import { plainText } from "../native/spans";
|
|
7
|
+
import { noteText, resultText } from "./native-view";
|
|
2
8
|
|
|
3
9
|
import {
|
|
4
10
|
type Component,
|
|
@@ -281,8 +287,158 @@ function renderAnswerOptionLines(
|
|
|
281
287
|
return out;
|
|
282
288
|
}
|
|
283
289
|
|
|
290
|
+
function askHead(question: string | undefined, meta?: string): NativeToolHead {
|
|
291
|
+
const first = question ? plainText(sanitizeCarriageReturns(question)).trim().split("\n")[0] : "";
|
|
292
|
+
return { title: "Ask", target: first || undefined, targetKind: "text", meta: meta ? [meta] : undefined };
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
/** One question of a multi-question result: the question as markdown over its answers. */
|
|
296
|
+
function describeQuestionSection(id: string, question: string, rest: readonly NativeChild[]): NativeNode {
|
|
297
|
+
return node("section", {}, [md(plainText(question)), ...rest], id);
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
/** An answer row: a success check before the chosen label, or a quiet unchosen label. */
|
|
301
|
+
function answerRow(key: string, label: TspSpan[], chosen: boolean): NativeNode {
|
|
302
|
+
return row(
|
|
303
|
+
compact([chosen ? node("icon", { name: "check", tone: "success" }) : undefined, text(label, { wrap: "word" })]),
|
|
304
|
+
{ gap: "sm", align: "baseline", role: chosen ? "omp.tool.answer" : "omp.tool.answer.off", key },
|
|
305
|
+
);
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
/**
|
|
309
|
+
* Answered option list: every offered option marked chosen or not, plus any
|
|
310
|
+
* quoted custom answer and a muted note. A lone "Cancelled" line when nothing was chosen.
|
|
311
|
+
*/
|
|
312
|
+
function describeAnswers(
|
|
313
|
+
options: string[] | undefined,
|
|
314
|
+
selectedOptions: string[] | undefined,
|
|
315
|
+
customInput: string | undefined,
|
|
316
|
+
note: string | undefined,
|
|
317
|
+
selectedIndices: ReadonlySet<number> | undefined,
|
|
318
|
+
): NativeChild[] {
|
|
319
|
+
const selected = new Set(selectedOptions ?? []);
|
|
320
|
+
if (selected.size === 0 && customInput === undefined && note === undefined) {
|
|
321
|
+
return [text([span("Cancelled", "warning")], { tone: "warning" })];
|
|
322
|
+
}
|
|
323
|
+
const labels = options && options.length > 0 ? options : (selectedOptions ?? []);
|
|
324
|
+
const rows = labels.map((label, index) => {
|
|
325
|
+
const isSelected = selectedIndices !== undefined ? selectedIndices.has(index) : selected.has(label);
|
|
326
|
+
return answerRow(`${index}`, [span(plainText(label), isSelected ? "toolOutput" : "muted")], isSelected);
|
|
327
|
+
});
|
|
328
|
+
if (customInput !== undefined) {
|
|
329
|
+
rows.push(answerRow("custom", [span(`\u201c${plainText(customInput)}\u201d`, "toolOutput")], true));
|
|
330
|
+
}
|
|
331
|
+
return compact([
|
|
332
|
+
...rows,
|
|
333
|
+
note !== undefined
|
|
334
|
+
? text([span(plainText(note), "muted")], { wrap: "word", role: "omp.tool.context" })
|
|
335
|
+
: undefined,
|
|
336
|
+
]);
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
/** Pending ask: an inline head naming the question; the ask dialog owns the form. */
|
|
340
|
+
function describeAskCall(args: AskRenderArgs): NativeToolView {
|
|
341
|
+
const questions = normalizeRenderQuestions(args.questions);
|
|
342
|
+
const first = questions?.[0]?.question ?? (typeof args.question === "string" ? args.question : undefined);
|
|
343
|
+
const more = questions && questions.length > 1 ? `${questions.length} questions` : undefined;
|
|
344
|
+
return {
|
|
345
|
+
tool: askHead(first, more),
|
|
346
|
+
inline: true,
|
|
347
|
+
body: [text([span("Waiting for your answer…", "muted")])],
|
|
348
|
+
};
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
function describeAskResult(result: ToolRenderResult<AskToolDetails>, args: AskRenderArgs | undefined): NativeToolView {
|
|
352
|
+
const rawDetails = result.details;
|
|
353
|
+
const fallback = plainText(sanitizeCarriageReturns(resultText(result)));
|
|
354
|
+
const argQuestion =
|
|
355
|
+
normalizeRenderQuestions(args?.questions)?.[0]?.question ??
|
|
356
|
+
(typeof args?.question === "string" ? args.question : undefined);
|
|
357
|
+
if (!rawDetails) {
|
|
358
|
+
return { tool: askHead(argQuestion), tone: "warning", body: fallback ? [noteText(fallback)] : undefined };
|
|
359
|
+
}
|
|
360
|
+
const details = sanitizeAskResultDetails(rawDetails);
|
|
361
|
+
|
|
362
|
+
if (details.chatRedirect) {
|
|
363
|
+
return {
|
|
364
|
+
tool: askHead(details.questions?.[0] ?? argQuestion, "chat redirect"),
|
|
365
|
+
tone: "info",
|
|
366
|
+
body: (details.questions ?? []).map(q => md(plainText(q))),
|
|
367
|
+
};
|
|
368
|
+
}
|
|
369
|
+
|
|
370
|
+
if (details.results && details.results.length > 0) {
|
|
371
|
+
const results = details.results;
|
|
372
|
+
const rawResults = rawDetails.results ?? [];
|
|
373
|
+
const answered = results.some(
|
|
374
|
+
r =>
|
|
375
|
+
r.customInput !== undefined || r.note !== undefined || (r.selectedOptions && r.selectedOptions.length > 0),
|
|
376
|
+
);
|
|
377
|
+
return {
|
|
378
|
+
tool: askHead(results[0]?.question, results.length > 1 ? `${results.length} questions` : undefined),
|
|
379
|
+
tone: answered ? undefined : "warning",
|
|
380
|
+
// Sanitizing preserves order and length, so raw indices align with `r`.
|
|
381
|
+
body: results.map((r, index) =>
|
|
382
|
+
describeQuestionSection(
|
|
383
|
+
r.id,
|
|
384
|
+
r.question,
|
|
385
|
+
describeAnswers(
|
|
386
|
+
r.options,
|
|
387
|
+
r.selectedOptions,
|
|
388
|
+
r.customInput,
|
|
389
|
+
r.note,
|
|
390
|
+
selectedIndicesFor(rawResults[index]?.options, rawResults[index]?.selectedOptions),
|
|
391
|
+
),
|
|
392
|
+
),
|
|
393
|
+
),
|
|
394
|
+
};
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
if (!details.question) {
|
|
398
|
+
return { tool: askHead(argQuestion), body: fallback ? [text(fallback, { wrap: "word" })] : undefined };
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
const answered =
|
|
402
|
+
details.customInput !== undefined ||
|
|
403
|
+
details.note !== undefined ||
|
|
404
|
+
(details.selectedOptions && details.selectedOptions.length > 0);
|
|
405
|
+
return {
|
|
406
|
+
tool: askHead(details.question),
|
|
407
|
+
tone: answered ? undefined : "warning",
|
|
408
|
+
body: compact([
|
|
409
|
+
md(plainText(details.question)),
|
|
410
|
+
...describeAnswers(
|
|
411
|
+
details.options,
|
|
412
|
+
details.selectedOptions,
|
|
413
|
+
details.customInput,
|
|
414
|
+
details.note,
|
|
415
|
+
selectedIndicesFor(rawDetails.options, rawDetails.selectedOptions),
|
|
416
|
+
),
|
|
417
|
+
details.timedOut
|
|
418
|
+
? text([span("auto-selected after timeout — not a user choice", "muted")], {
|
|
419
|
+
wrap: "word",
|
|
420
|
+
role: "omp.tool.notice",
|
|
421
|
+
})
|
|
422
|
+
: undefined,
|
|
423
|
+
]),
|
|
424
|
+
};
|
|
425
|
+
}
|
|
426
|
+
|
|
427
|
+
const askCallMemo = new OwnerMemo<NativeToolView | undefined>();
|
|
428
|
+
const askResultMemo = new OwnerMemo<NativeToolView | undefined>();
|
|
429
|
+
|
|
284
430
|
/** Render question forms and their recorded answers. */
|
|
285
431
|
export const askToolRenderer = {
|
|
432
|
+
describeCall(args: AskRenderArgs): NativeToolView | undefined {
|
|
433
|
+
return askCallMemo.get(args, [JSON.stringify(args)], () => describeAskCall(args));
|
|
434
|
+
},
|
|
435
|
+
describeResult(
|
|
436
|
+
result: ToolRenderResult<AskToolDetails>,
|
|
437
|
+
_options?: RenderResultOptions,
|
|
438
|
+
args?: AskRenderArgs,
|
|
439
|
+
): NativeToolView | undefined {
|
|
440
|
+
return askResultMemo.get(result, [], () => describeAskResult(result, args));
|
|
441
|
+
},
|
|
286
442
|
mergeCallAndResult: true,
|
|
287
443
|
renderCall(args: AskRenderArgs, _options: RenderResultOptions, uiTheme: Theme): Component {
|
|
288
444
|
const label = formatTitle("Ask", uiTheme);
|