import type { KeyEvent, ScrollBoxRenderable, TextareaRenderable } from "@opentui/core"; import { useKeyboard } from "@opentui/react"; import Fuse from "fuse.js"; /** @jsxImportSource @opentui/react */ import { useCallback, useEffect, useMemo, useRef, useState } from "react"; import { createKeyMatcher } from "../../components/keymap.js"; import { Menu } from "../../components/menu.js"; import { emitInterruptSignal, isCancelKeyboardEvent, isCtrlCKeyboardEvent, isEscapeKeyboardEvent, useCancelKey, } from "../runtime/open-tui-cancel.js"; import { OPEN_TUI_CANCEL, type OpenTuiSelectOption, type PromptResolver, } from "../runtime/open-tui-types.js"; const promptKeymap = createKeyMatcher({ up: ["up", "k"], down: ["down", "j"], toggle: ["space"], submit: ["enter"], }); interface TextPromptViewProps { message: string; placeholder?: string; defaultValue?: string; validate?: (value: string) => string | undefined; multiline?: boolean; charLimit?: number; height?: number; inline?: boolean; hint?: string; resolve: PromptResolver; } export function TextPromptView({ message, placeholder, defaultValue = "", validate, multiline = false, charLimit, height, inline = false, hint, resolve, }: TextPromptViewProps) { const [value, setValue] = useState(defaultValue); const valueRef = useRef(defaultValue); const textareaRef = useRef(null); const [error, setError] = useState(); useCancelKey(() => resolve(OPEN_TUI_CANCEL)); const onSubmit = (submitted: string | unknown) => { const submittedValue = typeof submitted === "string" ? submitted : valueRef.current; const validationError = validate?.(submittedValue); if (validationError) { setError(validationError); return; } resolve(submittedValue); }; useKeyboard((event) => { if (!multiline) return; if (isCtrlCKeyboardEvent(event)) { event.preventDefault?.(); event.stopPropagation?.(); emitInterruptSignal("textPrompt"); return; } if (event.ctrl && (event.name === "d" || event.name === "s")) { event.preventDefault?.(); event.stopPropagation?.(); onSubmit(valueRef.current); } }); const helperText = hint ?? (multiline ? "Ctrl+D submit • Esc cancel" : "Enter submit • Esc cancel"); if (multiline) { return (