{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "command",
  "type": "registry:ui",
  "title": "Command",
  "description": "Searchable command list with grouping, keyboard navigation, and selection.",
  "dependencies": [
    "clsx",
    "tailwind-merge",
    "lucide-react"
  ],
  "devDependencies": [],
  "registryDependencies": [],
  "files": [
    {
      "path": "components/ui/command.tsx",
      "content": "'use client'\n\nimport * as React from 'react'\nimport { Check, Command as CommandIcon, Search } from 'lucide-react'\nimport { cn } from '@/lib/utils'\n\nexport interface CommandItem {\n  value: string\n  label: React.ReactNode\n  keywords?: string\n  group?: string\n  icon?: React.ReactNode\n  disabled?: boolean\n}\n\nexport interface CommandProps extends Omit<React.HTMLAttributes<HTMLDivElement>, 'onSelect'> {\n  items: CommandItem[]\n  value?: string\n  defaultValue?: string\n  onValueChange?: (value: string) => void\n  onSelect?: (item: CommandItem) => void\n  placeholder?: string\n  emptyMessage?: React.ReactNode\n}\n\nconst listboxId = 'rawkitui-command-list'\n\nexport function Command({\n  items,\n  value: controlledValue,\n  defaultValue,\n  onValueChange,\n  onSelect,\n  placeholder = 'Search commands... ',\n  emptyMessage = 'No results found.',\n  className,\n  ...props\n}: CommandProps) {\n  const [query, setQuery] = React.useState('')\n  const [activeIndex, setActiveIndex] = React.useState(0)\n  const [internalValue, setInternalValue] = React.useState(defaultValue ?? '')\n  const optionRefs = React.useRef<Array<HTMLButtonElement | null>>([])\n  const currentValue = controlledValue ?? internalValue\n  const normalizedQuery = query.trim().toLowerCase()\n  const filteredItems = items.filter((item) => `${item.value} ${item.label} ${item.keywords ?? ''}`.toLowerCase().includes(normalizedQuery))\n  const groups = filteredItems.reduce<Record<string, CommandItem[]>>((result, item) => {\n    const group = item.group ?? 'Suggestions'\n    result[group] ??= []\n    result[group].push(item)\n    return result\n  }, {})\n\n  React.useEffect(() => setActiveIndex(0), [query])\n\n  const activeItem = filteredItems[activeIndex]\n  const activeId = activeItem ? `rawkitui-command-option-${activeItem.value}` : undefined\n\n  // Keep the highlighted option in view inside the scrollable listbox.\n  React.useEffect(() => {\n    optionRefs.current[activeIndex]?.scrollIntoView({ block: 'nearest' })\n  }, [activeIndex, query])\n\n  const selectItem = (item: CommandItem) => {\n    if (item.disabled) return\n    setInternalValue(item.value)\n    onValueChange?.(item.value)\n    onSelect?.(item)\n  }\n\n  const handleKeyDown = (event: React.KeyboardEvent<HTMLInputElement>) => {\n    if (event.key === 'ArrowDown') {\n      event.preventDefault()\n      setActiveIndex((index) => Math.min(index + 1, filteredItems.length - 1))\n    }\n    if (event.key === 'ArrowUp') {\n      event.preventDefault()\n      setActiveIndex((index) => Math.max(index - 1, 0))\n    }\n    if (event.key === 'Home') {\n      event.preventDefault()\n      setActiveIndex(0)\n    }\n    if (event.key === 'End') {\n      event.preventDefault()\n      setActiveIndex(filteredItems.length - 1)\n    }\n    if (event.key === 'Enter' && activeItem) {\n      event.preventDefault()\n      selectItem(activeItem)\n    }\n  }\n\n  return (\n    <div className={cn('w-full max-w-lg overflow-hidden rounded-2xl bg-rk-surface font-sans rk-border rk-shadow-md', className)} {...props}>\n      <div className=\"flex items-center gap-3 border-b-2 border-rk-ink/15 px-4\">\n        <Search className=\"h-4 w-4 shrink-0 text-black/50\" aria-hidden=\"true\" />\n        <input\n          value={query}\n          onChange={(event) => setQuery(event.target.value)}\n          onKeyDown={handleKeyDown}\n          placeholder={placeholder}\n          role=\"combobox\"\n          aria-expanded=\"true\"\n          aria-controls={listboxId}\n          aria-activedescendant={activeId}\n          aria-autocomplete=\"list\"\n          className=\"h-12 min-w-0 flex-1 bg-transparent text-sm font-bold outline-none placeholder:text-black/40\"\n        />\n        <CommandIcon className=\"h-4 w-4 shrink-0 text-black/35\" aria-hidden=\"true\" />\n      </div>\n      <div id={listboxId} role=\"listbox\" aria-label=\"Command options\" className=\"max-h-72 overflow-y-auto p-2\">\n        {filteredItems.length === 0 ? (\n          <div role=\"status\" className=\"px-3 py-8 text-center text-sm font-bold text-black/55\">{emptyMessage}</div>\n        ) : (\n          Object.entries(groups).map(([group, groupItems]) => (\n            <div key={group} role=\"group\" aria-label={group} className=\"mb-2 last:mb-0\">\n              <div className=\"px-3 py-2 font-mono text-[10px] font-black uppercase tracking-wider text-rk-secondary\">{group}</div>\n              {groupItems.map((item) => {\n                const index = filteredItems.indexOf(item)\n                const isActive = index === activeIndex\n                return (\n                  <button\n                    key={item.value}\n                    ref={(el) => {\n                      optionRefs.current[index] = el\n                    }}\n                    type=\"button\"\n                    role=\"option\"\n                    id={`rawkitui-command-option-${item.value}`}\n                    aria-selected={currentValue === item.value}\n                    disabled={item.disabled}\n                    onMouseEnter={() => setActiveIndex(index)}\n                    onClick={() => selectItem(item)}\n                    className={cn('flex min-h-10 w-full items-center gap-3 rounded-xl px-3 text-left text-sm font-extrabold transition-colors focus:outline-none disabled:pointer-events-none disabled:opacity-40', isActive ? 'bg-rk-primary' : 'hover:bg-rk-canvas')}\n                  >\n                    <span className=\"flex h-6 w-6 shrink-0 items-center justify-center\">{item.icon}</span>\n                    <span className=\"min-w-0 flex-1 truncate\">{item.label}</span>\n                    {currentValue === item.value && <Check className=\"h-4 w-4 shrink-0 stroke-[3]\" aria-hidden=\"true\" />}\n                  </button>\n                )\n              })}\n            </div>\n          ))\n        )}\n      </div>\n    </div>\n  )\n}\n",
      "type": "registry:ui",
      "target": "components/ui/command.tsx"
    }
  ]
}