"use client"; import { useEffect, useRef, useState } from "react"; import { Input } from "@/components/ui/input"; interface SearchInputProps { onSearch: (query: string) => void; initialValue?: string; isLoading?: boolean; debounceMs?: number; placeholder?: string; } /** * Search input component with keyboard shortcuts and debouncing * Supports Cmd+K (Mac) and Ctrl+K (Windows/Linux) to focus * Press Escape to clear input */ export function SearchInput({ onSearch, initialValue = "", isLoading = false, debounceMs = 300, placeholder = "Search knowledge entries...", }: SearchInputProps): React.JSX.Element { const [value, setValue] = useState(initialValue); const inputRef = useRef(null); const debounceTimerRef = useRef(null); // Handle keyboard shortcuts useEffect((): (() => void) => { const handleKeyDown = (e: KeyboardEvent): void => { // Cmd+K (Mac) or Ctrl+K (Windows/Linux) if (e.key === "k" && (e.metaKey || e.ctrlKey)) { e.preventDefault(); inputRef.current?.focus(); } }; document.addEventListener("keydown", handleKeyDown); return () => { document.removeEventListener("keydown", handleKeyDown); }; }, []); // Handle input changes with debouncing const handleChange = (e: React.ChangeEvent): void => { const newValue = e.target.value; setValue(newValue); // Clear existing timer if (debounceTimerRef.current) { clearTimeout(debounceTimerRef.current); } // Set new timer - only search for non-empty trimmed values debounceTimerRef.current = setTimeout(() => { const trimmed = newValue.trim(); if (trimmed) { onSearch(trimmed); } }, debounceMs); }; // Handle Escape key to clear input const handleKeyDown = (e: React.KeyboardEvent): void => { if (e.key === "Escape") { setValue(""); if (debounceTimerRef.current) { clearTimeout(debounceTimerRef.current); } } }; // Cleanup timer on unmount useEffect((): (() => void) => { return (): void => { if (debounceTimerRef.current) { clearTimeout(debounceTimerRef.current); } }; }, []); // Detect platform for keyboard hint const isMac = typeof window !== "undefined" && /Mac|iPhone|iPad|iPod/.test(navigator.userAgent); const shortcutHint = isMac ? "⌘K" : "Ctrl+K"; return (
{isLoading && (
)}
{shortcutHint}
); }