diff --git a/packages/frontend/src/components/terminal/CommandInput.tsx b/packages/frontend/src/components/terminal/CommandInput.tsx index dd3b34b0..56cbca11 100644 --- a/packages/frontend/src/components/terminal/CommandInput.tsx +++ b/packages/frontend/src/components/terminal/CommandInput.tsx @@ -16,9 +16,13 @@ interface CommandInputProps { handleInput: KeyboardEventHandler; } -type ForwardRefType = Pick; +export type CommandInputForwardRefType = { + focus: HTMLSpanElement["focus"]; + scrollIntoView: HTMLSpanElement["scrollIntoView"]; + clear: () => void; +}; -const CommandInput = forwardRef( +const CommandInput = forwardRef( ({ gitRef, handleInput }, ref) => { const inputRef = useRef(null); @@ -31,6 +35,14 @@ const CommandInput = forwardRef( scrollIntoView(arg) { scrollIntoViewRef(inputRef, arg); }, + clear() { + const $element = inputRef.current; + if (!$element) { + return; + } + + $element.textContent = ""; + }, }), [], ); diff --git a/packages/frontend/src/components/terminal/Terminal.tsx b/packages/frontend/src/components/terminal/Terminal.tsx index 2676df67..f1e1c8ef 100644 --- a/packages/frontend/src/components/terminal/Terminal.tsx +++ b/packages/frontend/src/components/terminal/Terminal.tsx @@ -3,7 +3,7 @@ import { type KeyboardEventHandler, forwardRef } from "react"; import { ENTER_KEY } from "../../constants/event"; import type { TerminalContentType } from "../../types/terminalType"; -import CommandInput from "./CommandInput"; +import CommandInput, { CommandInputForwardRefType } from "./CommandInput"; import * as styles from "./Terminal.css"; import TerminalContent from "./TerminalContent"; @@ -13,7 +13,7 @@ interface TerminalProps { onTerminal: (input: string) => void; } -const Terminal = forwardRef( +const Terminal = forwardRef( ({ gitRef, contentArray, onTerminal }, ref) => { const handleStandardInput: KeyboardEventHandler = async (event) => { const { diff --git a/packages/frontend/src/pages/quizzes/[id].page.tsx b/packages/frontend/src/pages/quizzes/[id].page.tsx index 7e6069fb..53b348b3 100644 --- a/packages/frontend/src/pages/quizzes/[id].page.tsx +++ b/packages/frontend/src/pages/quizzes/[id].page.tsx @@ -1,7 +1,7 @@ import axios, { isAxiosError } from "axios"; import { GetStaticPaths, GetStaticProps, GetStaticPropsContext } from "next"; import { useRouter } from "next/router"; -import { RefObject, useEffect, useReducer, useRef, useState } from "react"; +import { useEffect, useReducer, useRef, useState } from "react"; import { quizAPI } from "../../apis/quiz"; import { Editor } from "../../components/editor"; @@ -10,6 +10,7 @@ import { Graph } from "../../components/graph"; import { SolvedModal, useSolvedModal } from "../../components/quiz"; import { QuizGuide } from "../../components/quiz/QuizGuide"; import { Terminal } from "../../components/terminal"; +import { CommandInputForwardRefType } from "../../components/terminal/CommandInput"; import { BROWSWER_PATH } from "../../constants/path"; import { UserQuizStatusActionType, @@ -25,7 +26,6 @@ import { } from "../../reducers/terminalReducer"; import { Categories, Quiz, QuizGitGraphCommit } from "../../types/quiz"; import { TerminalContentType } from "../../types/terminalType"; -import { focusRef, scrollIntoViewRef } from "../../utils/refObject"; import { isString } from "../../utils/typeGuard"; import * as styles from "./quiz.css"; @@ -44,7 +44,7 @@ export default function QuizPage({ quiz }: { quiz: Quiz }) { const [{ terminalMode, editorFile, contentArray }, terminalDispatch] = useReducer(terminalReducer, initialTerminalState); - const terminalInputRef = useRef(null); + const terminalInputRef = useRef(null); const fetchGitGraphDataRef = useRef(async (curId: number) => { try { @@ -131,8 +131,8 @@ export default function QuizPage({ quiz }: { quiz: Quiz }) { await quizAPI.resetQuizById(numId); fetchGitGraphDataRef?.current(numId); terminalDispatch({ type: TerminalActionTypes.reset }); - clearTextContent(terminalInputRef); - focusRef(terminalInputRef); + terminalInputRef.current?.clear(); + terminalInputRef.current?.focus(); userQuizStatusDispatcher({ type: UserQuizStatusActionType.ResetQuizById, id: numId, @@ -150,14 +150,17 @@ export default function QuizPage({ quiz }: { quiz: Quiz }) { fetchGitGraphDataRef?.current(+id); } terminalDispatch({ type: TerminalActionTypes.reset }); - clearTextContent(terminalInputRef); - focusRef(terminalInputRef); + terminalInputRef.current?.clear(); + terminalInputRef.current?.focus(); }, [id]); useEffect(() => { - scrollIntoViewRef(terminalInputRef); - clearTextContent(terminalInputRef); - focusRef(terminalInputRef); + const $terminalInput = terminalInputRef.current; + if (!$terminalInput) return; + + $terminalInput.scrollIntoView(); + $terminalInput.clear(); + $terminalInput.focus(); }, [contentArray]); const { barRef, topRef, handleBarHover } = useResizableSplitView(); @@ -239,15 +242,6 @@ export const getStaticPaths = (async () => { return { paths, fallback: "blocking" }; }) satisfies GetStaticPaths; -function clearTextContent(ref: RefObject) { - const $element = ref.current; - if (!$element) { - return; - } - - $element.textContent = ""; -} - function isEditorMode(terminalMode: "editor" | "command") { return terminalMode === "editor"; }