|
@@ -3,15 +3,15 @@ import DynamicTextArea from "react-textarea-autosize"
|
|
|
|
|
|
|
|
interface TerminalProps {
|
|
interface TerminalProps {
|
|
|
output: string
|
|
output: string
|
|
|
- shouldAllowInput: boolean
|
|
|
|
|
handleSendStdin: (text: string) => void
|
|
handleSendStdin: (text: string) => void
|
|
|
|
|
+ shouldAllowInput: boolean
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
/*
|
|
|
Inspired by https://phuoc.ng/collection/mirror-a-text-area/create-your-own-custom-cursor-in-a-text-area/
|
|
Inspired by https://phuoc.ng/collection/mirror-a-text-area/create-your-own-custom-cursor-in-a-text-area/
|
|
|
*/
|
|
*/
|
|
|
|
|
|
|
|
-const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSendStdin }) => {
|
|
|
|
|
|
|
+const Terminal: React.FC<TerminalProps> = ({ output, handleSendStdin, shouldAllowInput }) => {
|
|
|
const [userInput, setUserInput] = useState("")
|
|
const [userInput, setUserInput] = useState("")
|
|
|
const [isFocused, setIsFocused] = useState(false) // Initially not focused
|
|
const [isFocused, setIsFocused] = useState(false) // Initially not focused
|
|
|
const textAreaRef = useRef<HTMLTextAreaElement>(null)
|
|
const textAreaRef = useRef<HTMLTextAreaElement>(null)
|
|
@@ -27,7 +27,6 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
}, [output, lastProcessedOutput])
|
|
}, [output, lastProcessedOutput])
|
|
|
|
|
|
|
|
const handleKeyPress = (e: React.KeyboardEvent<HTMLTextAreaElement>) => {
|
|
const handleKeyPress = (e: React.KeyboardEvent<HTMLTextAreaElement>) => {
|
|
|
- if (!shouldAllowInput) return
|
|
|
|
|
if (e.key === "Enter") {
|
|
if (e.key === "Enter") {
|
|
|
e.preventDefault()
|
|
e.preventDefault()
|
|
|
handleSendStdin(userInput)
|
|
handleSendStdin(userInput)
|
|
@@ -130,7 +129,7 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
|
|
|
|
|
const caretEle = document.createElement("span")
|
|
const caretEle = document.createElement("span")
|
|
|
caretEle.classList.add("terminal-cursor")
|
|
caretEle.classList.add("terminal-cursor")
|
|
|
- if (isFocused && shouldAllowInput) {
|
|
|
|
|
|
|
+ if (isFocused) {
|
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
|
}
|
|
}
|
|
|
if (!shouldAllowInput) {
|
|
if (!shouldAllowInput) {
|
|
@@ -159,7 +158,7 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
|
|
|
|
|
const caretEle = document.createElement("span")
|
|
const caretEle = document.createElement("span")
|
|
|
caretEle.classList.add("terminal-cursor")
|
|
caretEle.classList.add("terminal-cursor")
|
|
|
- if (isFocused && shouldAllowInput) {
|
|
|
|
|
|
|
+ if (isFocused) {
|
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
|
}
|
|
}
|
|
|
if (!shouldAllowInput) {
|
|
if (!shouldAllowInput) {
|
|
@@ -171,7 +170,6 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
}, [output, userInput, isFocused, shouldAllowInput])
|
|
}, [output, userInput, isFocused, shouldAllowInput])
|
|
|
|
|
|
|
|
const handleChange = (e: React.ChangeEvent<HTMLTextAreaElement>) => {
|
|
const handleChange = (e: React.ChangeEvent<HTMLTextAreaElement>) => {
|
|
|
- if (!shouldAllowInput) return
|
|
|
|
|
const newValue = e.target.value
|
|
const newValue = e.target.value
|
|
|
if (newValue.startsWith(output)) {
|
|
if (newValue.startsWith(output)) {
|
|
|
setUserInput(newValue.slice(output.length))
|
|
setUserInput(newValue.slice(output.length))
|
|
@@ -190,7 +188,6 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
const handleKeyDown = (e: React.KeyboardEvent<HTMLTextAreaElement>) => {
|
|
const handleKeyDown = (e: React.KeyboardEvent<HTMLTextAreaElement>) => {
|
|
|
- if (!shouldAllowInput) return
|
|
|
|
|
const textarea = e.target as HTMLTextAreaElement
|
|
const textarea = e.target as HTMLTextAreaElement
|
|
|
const cursorPosition = textarea.selectionStart
|
|
const cursorPosition = textarea.selectionStart
|
|
|
|
|
|
|
@@ -213,6 +210,9 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
if (isFocused) {
|
|
if (isFocused) {
|
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
caretEle.classList.add("terminal-cursor-focused")
|
|
|
}
|
|
}
|
|
|
|
|
+ if (!shouldAllowInput) {
|
|
|
|
|
+ caretEle.classList.add("terminal-cursor-hidden")
|
|
|
|
|
+ }
|
|
|
caretEle.innerHTML = " "
|
|
caretEle.innerHTML = " "
|
|
|
mirrorRef.current!.appendChild(caretEle)
|
|
mirrorRef.current!.appendChild(caretEle)
|
|
|
|
|
|
|
@@ -291,9 +291,7 @@ const Terminal: React.FC<TerminalProps> = ({ output, shouldAllowInput, handleSen
|
|
|
color: "var(--vscode-terminal-foreground)",
|
|
color: "var(--vscode-terminal-foreground)",
|
|
|
borderRadius: "3px",
|
|
borderRadius: "3px",
|
|
|
...(textAreaStyle as any),
|
|
...(textAreaStyle as any),
|
|
|
- //pointerEvents: shouldAllowInput ? "auto" : "none",
|
|
|
|
|
}}
|
|
}}
|
|
|
- readOnly={!shouldAllowInput}
|
|
|
|
|
minRows={1}
|
|
minRows={1}
|
|
|
/>
|
|
/>
|
|
|
<div ref={mirrorRef} className="terminal-mirror"></div>
|
|
<div ref={mirrorRef} className="terminal-mirror"></div>
|