Guide
React, Vue, Svelte and the rest
React
import { useCommandPalette, useCommands } from '@devix-labs/command-palette/react';
import '@devix-labs/command-palette/styles.css';
function App() {
const palette = useCommandPalette({
items: [{ id: 'go.home', title: 'Go home', perform: () => navigate('/') }],
});
return <button onClick={() => palette.open()}>Search… ⌘K</button>;
}
Register commands from wherever they belong, for as long as that screen is mounted:
function InvoiceScreen({ invoice }) {
const palette = useCommandPalette();
useCommands(palette, [
{ id: 'invoice.send', title: `Send invoice ${invoice.number}`, perform: () => send(invoice) },
{ id: 'invoice.delete', title: 'Delete invoice', perform: () => remove(invoice) },
], [invoice.id]);
}
useCommandPalette returns a no-op palette during server rendering, so a page that calls open() in
an effect still renders on the server.
Vue
<script setup>
import { onUnmounted } from 'vue';
import { useCommandPalette } from '@devix-labs/command-palette/vue';
const palette = useCommandPalette({ items: commands });
onUnmounted(() => palette.destroy());
</script>
<template>
<button @click="palette.open()">Search… ⌘K</button>
</template>
Svelte
<script>
import { onDestroy } from 'svelte';
import { createCommandPalette } from '@devix-labs/command-palette/svelte';
const palette = createCommandPalette({ items: commands });
onDestroy(() => palette.destroy());
</script>
<button on:click={() => palette.open()}>Search… ⌘K</button>
Web component
<script type="module" src="https://www.devix.pk/cdn/oss/command-palette@1.0.0/element.js"></script>
<dx-command-palette hotkey="mod+k">
<script type="application/json">
[
{ "id": "home", "title": "Go home", "href": "/" },
{ "id": "docs", "title": "Open docs", "section": "Go to", "href": "/docs" }
]
</script>
</dx-command-palette>
Commands in JSON carry href instead of perform; for anything else, reach the instance through the
element's palette property.
Laravel
Feed it your routes at build time, or from an endpoint:
<script type="module">
import { createCommandPalette } from '{{ asset('js/command-palette.js') }}';
const palette = createCommandPalette({
items: @json($commands),
search: async (query, { signal }) => {
const response = await fetch(`{{ route('search') }}?q=${encodeURIComponent(query)}`, { signal });
return (await response.json()).map((row) => ({ id: `r-${row.id}`, title: row.title, section: row.type, perform: () => (location.href = row.url) }));
},
});
window.palette = palette;
</script>
Because perform is a function, commands that come from JSON need a shape you control — href,
route, or an action name you switch on.
Updated 15 Sep 2026