---
title: "CommandPalette"
description: "Keyboard-first global search: type to filter, arrows to move, Enter to run and Escape to close. Focus always returns to the trigger."
kind: component
id: C-065
registry: "command-palette"
docs: "https://koten.codehive.com.co/components/command-palette"
markdown: "https://koten.codehive.com.co/md/components/command-palette.md"
install: "npx shadcn@latest add https://koten.codehive.com.co/r/command-palette.json"
language: en
---

# CommandPalette · コマンド

> Component C-065 in the Koten UI catalog.

Keyboard-first global search: type to filter, arrows to move, Enter to run and Escape to close. Focus always returns to the trigger.

> Japanese labels in this page are documentation metadata. Keep the consumer UI in the product's language and do not add Japanese decoration unless the user asks (R-031).

## Install

Install `koten-theme` first when the project does not have Koten tokens yet. Use the runner of your project.

```bash
# Node
npx shadcn@latest add https://koten.codehive.com.co/r/command-palette.json

# Bun
bunx shadcn@latest add https://koten.codehive.com.co/r/command-palette.json
```

## Files

- `@/components/ui/command-palette.tsx`
- `@/lib/koten/cn.ts`
- `@/lib/koten/format.ts`
- `@/lib/koten/intl.ts`
- `@/lib/koten/labels.ts`
- `@/lib/koten/provider.tsx`

## Requirements

- **portal** — Portaled popup: The palette mounts in BaseDialog.Portal. Do not nest it in containers with overflow or transform, because the backdrop must cover the window.
- **controlled** — Controlled state (open / onOpenChange): The palette does not open by itself: it takes open and onOpenChange, and you own the state. When it closes with Escape or on select, focus returns to the trigger.

## Reference

- Upstream primitive: https://base-ui.com/react/components/dialog

## Examples

### Opening from a button

Four grouped commands; the chosen result is announced next to the trigger.

```tsx
const [open, setOpen] = useState(false);

<Button onClick={() => setOpen(true)}>Open palette</Button>

<CommandPalette
  open={open}
  onOpenChange={setOpen}
  label="KURA commands"
  placeholder="Search orders, products or actions…"
  emptyLabel="No results."
  hint="↑↓ move · ↵ run · esc close"
  items={[
    { id: "orders", label: "View orders", description: "132 orders", group: "Navigate" },
    { id: "new", label: "New order", description: "Manual form", group: "Actions" },
  ]}
  onSelect={(item) => runCommand(item.id)}
/>
```

## Props

| Prop | Type | Default | Notes |
| --- | --- | --- | --- |
| `open` | `boolean` | `—` | Controls visibility; the palette holds no internal open state. |
| `onOpenChange` | `(open: boolean) => void` | `—` | Called on close via Escape, the backdrop or an item selection. |
| `label` | `string` | `—` | Accessible name for the dialog, the field and the list. |
| `placeholder` | `string` | `—` | Hint text inside the search field. |
| `emptyLabel` | `string` | `—` | Visible message when no item matches. |
| `items` | `readonly CommandItem[]` | `—` | id, label, description, group, keywords, icon and shortcut. |
| `onSelect` | `(item: CommandItem) => void` | `—` | Called after closing; focus has already returned to the trigger. |
| `hint` | `ReactNode` | `—` | Keyboard hint at the bottom; the component ships no internal strings. |
| `className` | `string` | `—` | Merged with the popup max width and border. |

## Accessibility

- The field is a combobox with aria-controls, aria-autocomplete and aria-activedescendant; the list is a listbox.
- The dialog traps focus and returns it to the trigger on close, including with Escape.
- Arrows, Home/End and PageUp/PageDown move; Enter runs the active command.
- The empty state and the chosen result are conveyed as text, not only with colour.

## Sources

- Catalog page: https://koten.codehive.com.co/components/command-palette
- Markdown: https://koten.codehive.com.co/md/components/command-palette.md
- Repository: https://github.com/codehive-colombia/koten
