Search with results
Search field with fuzzy matching, highlighted letters and a pixel highlight that springs between results; `hotkey` makes "/" focus it.
Playground
Change a prop and the component re-renders. Props marked remounts set an initial value, so the component starts over.
<PxSearch hotkey placeholder="Search settings" />
Installation
pnpm dlx shadcn@latest add @lumesec/px-searchFirst timeRegister the @lumesec registry once, or install by URL+
Adds @lumesec to your components.json:
pnpm dlx shadcn@latest registry add @lumesec=https://elements.lumesec.ai/r/{name}.jsonOr skip the setup and install by URL:
npx shadcn@latest add https://elements.lumesec.ai/r/px-search.jsonUsage
import { PxSearch } from "@/components/lumesec/px-search";
export function Example() {
return (
<PxSearch
hotkey
label="Search pages"
placeholder="Search pages"
items={["Billing", "API keys", "Webhooks", "Team members"]}
onSelect={(item) => console.log("open", item)}
/>
);
}Behaviour
Fuzzy matching with highlighted letters, a scanning line while it searches and a pixel highlight that springs between results. With hotkey, “/” focuses it from anywhere.
API reference
Props
Also accepts every prop of <div> (React.ComponentProps<"div">), spread onto the root element.
itemsTypereadonly string[]Defaultdemo listEntries to search. Defaults to a demo list of 14 settings pages.
valueTypestringControlled query. Use with onValueChange.
defaultValueTypestringDefault""Initial query when uncontrolled.
hotkeyTypebooleanDefaultfalsePressing "/" anywhere on the page focuses the field, unless focus is already in an input, textarea or editable element.
labelTypestringDefault"Search settings"Accessible name of the field.
placeholderTypestringDefault"Search settings"Placeholder of the field.
disabledTypebooleanDefaultfalseDims the component, disables the field and turns off the hotkey.
onValueChangeType(query: string) => voidCalled with the query on every edit.
onSearchType(query: string, count: number) => voidCalled after each search with the query and the total number of matches. Typing searches 280 ms after the last keystroke.
onSelectType(item: string) => voidCalled when a result is chosen with Enter or a click.
Ref
ref points at the root HTMLDivElement.
Keyboard
| Keys | Action |
|---|---|
| / | Focus the field from anywhere on the page (with hotkey). |
| ArrowDown / ArrowUp | Move the highlight, wrapping at the ends. |
| Enter | Choose the highlighted result. Pressed before the pending search ran, it searches first and chooses the best match. |
| Escape | Clear the query and show the suggestions again. |
Accessibility
- The input has
role="combobox",aria-expanded="true",aria-controlspointing at the results,aria-autocomplete="list"andaria-activedescendanton the highlighted result. - Results are a
role="listbox"labelled "Results" withrole="option"items andaria-selected; the no-match row hasaria-disabled="true". - A status line in an
aria-live="polite"region announces the result count and the chosen entry. - The highlight canvas is
aria-hidden. - Reduced motion: the search runs without the 280 ms delay and the scanning line, results appear without sliding in, and the highlight jumps instead of springing.
Theming
Styled with Tailwind classes on your shadcn theme tokens, so light and dark follow your theme. The accent comes from --lumesec. See Theming.
This component reads --foreground, --muted-foreground, --card, --border, --lumesec and --lumesec-shine.
Notes
- Ships with demo data: 14 settings entries such as "Billing and invoices" and "API keys". Pass
itemsto search your own list, andlabelandplaceholderto describe it. - An empty query shows the first five entries as suggestions; a query shows up to six matches, best first, with matched letters wrapped in
<mark>. - The result list stays visible; there is no popup to open or close.
- Not a form control: it has no
nameand submits nothing. - The "/" key hint in the field shows only with
hotkey. Changingitemssearches them again with the current query.
Related
Was this page helpful?