Просмотр исходного кода

tui: add expandable bash output for long commands to improve readability

Dax Raad 1 месяц назад
Родитель
Сommit
b3a2f9fb4e
1 измененных файлов с 18 добавлено и 3 удалено
  1. 18 3
      packages/opencode/src/cli/cmd/tui/routes/session/index.tsx

+ 18 - 3
packages/opencode/src/cli/cmd/tui/routes/session/index.tsx

@@ -1518,15 +1518,30 @@ function BlockTool(props: { title: string; children: JSX.Element; onClick?: () =
 }
 }
 
 
 function Bash(props: ToolProps<typeof BashTool>) {
 function Bash(props: ToolProps<typeof BashTool>) {
-  const output = createMemo(() => stripAnsi(props.metadata.output?.trim() ?? ""))
   const { theme } = useTheme()
   const { theme } = useTheme()
+  const output = createMemo(() => stripAnsi(props.metadata.output?.trim() ?? ""))
+  const [expanded, setExpanded] = createSignal(false)
+  const lines = createMemo(() => output().split("\n"))
+  const overflow = createMemo(() => lines().length > 10)
+  const limited = createMemo(() => {
+    if (expanded() || !overflow()) return output()
+    return [...lines().slice(0, 10), "…"].join("\n")
+  })
+
   return (
   return (
     <Switch>
     <Switch>
       <Match when={props.metadata.output !== undefined}>
       <Match when={props.metadata.output !== undefined}>
-        <BlockTool title={"# " + (props.input.description ?? "Shell")} part={props.part}>
+        <BlockTool
+          title={"# " + (props.input.description ?? "Shell")}
+          part={props.part}
+          onClick={overflow() ? () => setExpanded((prev) => !prev) : undefined}
+        >
           <box gap={1}>
           <box gap={1}>
             <text fg={theme.text}>$ {props.input.command}</text>
             <text fg={theme.text}>$ {props.input.command}</text>
-            <text fg={theme.text}>{output()}</text>
+            <text fg={theme.text}>{limited()}</text>
+            <Show when={overflow()}>
+              <text fg={theme.textMuted}>{expanded() ? "Click to collapse" : "Click to expand"}</text>
+            </Show>
           </box>
           </box>
         </BlockTool>
         </BlockTool>
       </Match>
       </Match>