Skip to content

Commit b4fd9ee

Browse files
author
Eric Wheeler
committed
feat: syntax highlighting terminal output with Shiki
Refactored CommandExecution.tsx to: - Implement CodeBlock component for terminal display - Use Shiki for syntax highlighting of shell commands and terminal output Signed-off-by: Eric Wheeler <[email protected]>
1 parent 65958d8 commit b4fd9ee

File tree

1 file changed

+36
-35
lines changed

1 file changed

+36
-35
lines changed
Lines changed: 36 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1,55 +1,56 @@
1-
import { HTMLAttributes, forwardRef, useMemo, useState } from "react"
2-
import { Virtuoso } from "react-virtuoso"
3-
import { ChevronDown } from "lucide-react"
1+
import { forwardRef, useState } from "react"
2+
import { useTranslation } from "react-i18next"
43

54
import { useExtensionState } from "@src/context/ExtensionStateContext"
6-
import { cn } from "@src/lib/utils"
5+
import CodeBlock, { CODE_BLOCK_BG_COLOR } from "../common/CodeBlock"
76

87
interface CommandExecutionProps {
98
command: string
109
output: string
1110
}
1211

1312
export const CommandExecution = forwardRef<HTMLDivElement, CommandExecutionProps>(({ command, output }, ref) => {
13+
const { t } = useTranslation()
1414
const { terminalShellIntegrationDisabled = false } = useExtensionState()
15-
16-
// If we aren't opening the VSCode terminal for this command then we default
17-
// to expanding the command execution output.
1815
const [isExpanded, setIsExpanded] = useState(terminalShellIntegrationDisabled)
1916

20-
const lines = useMemo(() => output.split("\n"), [output])
17+
const onToggleExpand = () => {
18+
setIsExpanded(!isExpanded)
19+
}
2120

2221
return (
23-
<div ref={ref} className="w-full p-2 rounded-xs bg-vscode-editor-background">
22+
<>
2423
<div
25-
className={cn("flex flex-row justify-between cursor-pointer active:opacity-75", {
26-
"opacity-50": isExpanded,
27-
})}
28-
onClick={() => setIsExpanded(!isExpanded)}>
29-
<Line>{command}</Line>
30-
<ChevronDown className={cn("size-4 transition-transform duration-300", { "rotate-180": isExpanded })} />
31-
</div>
32-
<div className={cn("h-[200px]", { hidden: !isExpanded })}>
33-
<Virtuoso
34-
className="h-full mt-2"
35-
totalCount={lines.length}
36-
itemContent={(i) => <Line>{lines[i]}</Line>}
37-
followOutput="auto"
38-
/>
24+
ref={ref}
25+
style={{
26+
borderRadius: 3,
27+
border: "1px solid var(--vscode-editorGroup-border)",
28+
overflow: "hidden",
29+
backgroundColor: CODE_BLOCK_BG_COLOR,
30+
}}>
31+
<CodeBlock source={command} language="shell" />
32+
{output.length > 0 && (
33+
<div style={{ width: "100%" }}>
34+
<div
35+
onClick={onToggleExpand}
36+
style={{
37+
display: "flex",
38+
alignItems: "center",
39+
gap: "4px",
40+
width: "100%",
41+
justifyContent: "flex-start",
42+
cursor: "pointer",
43+
padding: `2px 8px ${isExpanded ? 0 : 8}px 8px`,
44+
}}>
45+
<span className={`codicon codicon-chevron-${isExpanded ? "down" : "right"}`}></span>
46+
<span style={{ fontSize: "0.8em" }}>{t("chat:commandOutput")}</span>
47+
</div>
48+
{isExpanded && <CodeBlock source={output} language="log" />}
49+
</div>
50+
)}
3951
</div>
40-
</div>
52+
</>
4153
)
4254
})
4355

44-
type LineProps = HTMLAttributes<HTMLDivElement>
45-
46-
const Line = ({ className, ...props }: LineProps) => {
47-
return (
48-
<div
49-
className={cn("font-mono text-vscode-editor-foreground whitespace-pre-wrap break-words", className)}
50-
{...props}
51-
/>
52-
)
53-
}
54-
5556
CommandExecution.displayName = "CommandExecution"

0 commit comments

Comments
 (0)