{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "command-palette",
  "title": "Command Palette",
  "description": "A data-driven Command+K menu with dialog and inline variants, grouped results, metadata, shortcuts, and a replaceable footer.",
  "dependencies": [
    "lucide-react"
  ],
  "registryDependencies": [
    "command"
  ],
  "files": [
    {
      "path": "registry/dashboardcn/ui/command-palette.tsx",
      "content": "\"use client\"\n\nimport * as React from \"react\"\nimport { CornerDownLeft } from \"lucide-react\"\n\nimport { cn } from \"@/lib/utils\"\nimport {\n  Command,\n  CommandDialog,\n  CommandEmpty,\n  CommandGroup,\n  CommandInput,\n  CommandItem,\n  CommandList,\n  CommandSeparator,\n  CommandShortcut,\n} from \"@/components/ui/command\"\n\nexport interface CommandPaletteItem {\n  id: string\n  label: string\n  description?: string\n  icon?: React.ReactNode\n  shortcut?: React.ReactNode\n  keywords?: string[]\n  disabled?: boolean\n  onSelect?: () => void\n}\n\nexport interface CommandPaletteGroup {\n  heading?: string\n  items: CommandPaletteItem[]\n}\n\nexport interface CommandPaletteProps {\n  groups: CommandPaletteGroup[]\n  variant?: \"dialog\" | \"inline\"\n  /** Arrange results as familiar command rows or as an app-launcher grid. */\n  layout?: \"list\" | \"grid\"\n  /** Tighten list rows for dense navigation menus. */\n  density?: \"compact\" | \"default\"\n  size?: \"compact\" | \"default\" | \"wide\"\n  open?: boolean\n  onOpenChange?: (open: boolean) => void\n  placeholder?: string\n  emptyLabel?: React.ReactNode\n  title?: string\n  description?: string\n  footer?: React.ReactNode\n  className?: string\n  onSelect?: (item: CommandPaletteItem) => void\n}\n\nconst sizeClasses = {\n  compact: \"sm:max-w-md\",\n  default: \"sm:max-w-xl\",\n  wide: \"sm:max-w-2xl\",\n}\n\n/** Bind Command/Ctrl+K to a controlled command palette without stealing input shortcuts. */\nfunction useCommandPaletteShortcut(\n  onOpenChange: React.Dispatch<React.SetStateAction<boolean>>,\n  enabled = true\n) {\n  React.useEffect(() => {\n    if (!enabled) return\n\n    const onKeyDown = (event: KeyboardEvent) => {\n      if (!(event.metaKey || event.ctrlKey) || event.key.toLowerCase() !== \"k\") return\n      const target = event.target\n      if (\n        target instanceof HTMLInputElement ||\n        target instanceof HTMLTextAreaElement ||\n        target instanceof HTMLSelectElement ||\n        (target instanceof HTMLElement && target.isContentEditable)\n      ) return\n\n      event.preventDefault()\n      onOpenChange((open) => !open)\n    }\n\n    document.addEventListener(\"keydown\", onKeyDown)\n    return () => document.removeEventListener(\"keydown\", onKeyDown)\n  }, [enabled, onOpenChange])\n}\n\nfunction CommandPaletteContent({\n  groups,\n  placeholder,\n  emptyLabel,\n  footer,\n  onSelect,\n  layout,\n  density,\n}: Pick<\n  CommandPaletteProps,\n  | \"groups\"\n  | \"placeholder\"\n  | \"emptyLabel\"\n  | \"footer\"\n  | \"onSelect\"\n  | \"layout\"\n  | \"density\"\n>) {\n  return (\n    <>\n      <CommandInput placeholder={placeholder} />\n      <CommandList className=\"max-h-[min(420px,60vh)] scroll-py-2\">\n        <CommandEmpty className=\"text-muted-foreground px-6 py-12 text-center text-sm\">\n          {emptyLabel}\n        </CommandEmpty>\n        {groups.map((group, groupIndex) => (\n          <React.Fragment key={group.heading ?? groupIndex}>\n            {groupIndex > 0 ? <CommandSeparator /> : null}\n            <CommandGroup\n              heading={group.heading}\n              className={cn(\n                layout === \"grid\" &&\n                  \"p-2 [&_[cmdk-group-items]]:grid [&_[cmdk-group-items]]:grid-cols-2 [&_[cmdk-group-items]]:gap-2 sm:[&_[cmdk-group-items]]:grid-cols-3\"\n              )}\n            >\n              {group.items.map((item) => (\n                <CommandItem\n                  key={item.id}\n                  value={[item.label, item.description, ...(item.keywords ?? [])].filter(Boolean).join(\" \")}\n                  disabled={item.disabled}\n                  onSelect={() => {\n                    item.onSelect?.()\n                    onSelect?.(item)\n                  }}\n                  className={cn(\n                    \"group/item gap-3\",\n                    density === \"compact\" ? \"py-1.5\" : \"py-2.5\",\n                    layout === \"grid\" &&\n                      \"h-auto min-h-28 flex-col items-start justify-between gap-4 rounded-lg border bg-card p-3 data-[selected=true]:border-ring data-[selected=true]:bg-accent\"\n                  )}\n                >\n                  {item.icon ? (\n                    <span\n                      className={cn(\n                        \"bg-muted group-data-[selected=true]/item:bg-background flex shrink-0 items-center justify-center rounded-md border [&>svg]:size-4\",\n                        density === \"compact\" ? \"size-7\" : \"size-8\",\n                        layout === \"grid\" && \"size-9\"\n                      )}\n                    >\n                      {item.icon}\n                    </span>\n                  ) : null}\n                  <span className=\"min-w-0 flex-1\">\n                    <span className=\"block truncate text-sm font-medium\">{item.label}</span>\n                    {item.description ? (\n                      <span className=\"text-muted-foreground block truncate text-xs\">{item.description}</span>\n                    ) : null}\n                  </span>\n                  {item.shortcut ? <CommandShortcut>{item.shortcut}</CommandShortcut> : null}\n                </CommandItem>\n              ))}\n            </CommandGroup>\n          </React.Fragment>\n        ))}\n      </CommandList>\n      {footer !== null ? (\n        <div className=\"text-muted-foreground flex min-h-10 items-center justify-between gap-3 border-t bg-muted/30 px-3 text-xs\">\n          {footer}\n        </div>\n      ) : null}\n    </>\n  )\n}\n\n/** A data-driven command menu that renders as a modal palette or an embedded search surface. */\nfunction CommandPalette({\n  groups,\n  variant = \"dialog\",\n  layout = \"list\",\n  density = \"default\",\n  size = \"default\",\n  open,\n  onOpenChange,\n  placeholder = \"Type a command or search…\",\n  emptyLabel = \"No commands found.\",\n  title = \"Command palette\",\n  description = \"Search for a command to run.\",\n  footer = (\n    <span className=\"flex items-center gap-2\">\n      <CommandPaletteKbd><CornerDownLeft /></CommandPaletteKbd>\n      Select\n    </span>\n  ),\n  className,\n  onSelect,\n}: CommandPaletteProps) {\n  const content = (\n    <CommandPaletteContent\n      groups={groups}\n      placeholder={placeholder}\n      emptyLabel={emptyLabel}\n      footer={footer}\n      onSelect={onSelect}\n      layout={layout}\n      density={density}\n    />\n  )\n\n  if (variant === \"inline\") {\n    return (\n      <Command\n        data-slot=\"command-palette\"\n        className={cn(\"h-auto rounded-xl border shadow-sm\", className)}\n      >\n        {content}\n      </Command>\n    )\n  }\n\n  return (\n    <CommandDialog\n      open={open}\n      onOpenChange={onOpenChange}\n      title={title}\n      description={description}\n      showCloseButton={false}\n      className={cn(\n        \"gap-0 overflow-hidden rounded-xl border bg-popover p-0 shadow-2xl\",\n        sizeClasses[size],\n        className\n      )}\n    >\n      {content}\n    </CommandDialog>\n  )\n}\n\nfunction CommandPaletteKbd({ className, ...props }: React.ComponentProps<\"kbd\">) {\n  return (\n    <kbd\n      className={cn(\n        \"bg-background text-muted-foreground inline-flex h-5 min-w-5 items-center justify-center rounded border px-1 font-sans text-[10px] font-medium shadow-xs [&_svg]:size-3\",\n        className\n      )}\n      {...props}\n    />\n  )\n}\n\nfunction CommandPaletteShortcutKeys({\n  keys,\n  label,\n  className,\n}: {\n  keys: string[]\n  label?: string\n  className?: string\n}) {\n  return (\n    <span\n      aria-label={label ?? keys.join(\" then \")}\n      className={cn(\"flex items-center gap-1\", className)}\n    >\n      {keys.map((key) => (\n        <CommandPaletteKbd key={key}>{key}</CommandPaletteKbd>\n      ))}\n    </span>\n  )\n}\n\nexport {\n  CommandPalette,\n  CommandPaletteKbd,\n  CommandPaletteShortcutKeys,\n  useCommandPaletteShortcut,\n}\n",
      "type": "registry:ui"
    }
  ],
  "type": "registry:ui"
}