K
KoreUI

Spotlight

Spotlight

Command palette activado con Cmd+K / Ctrl+K. Búsqueda fuzzy instantánea, grupos, historial y dependencias multi-paso.

Demo en vivo

El Spotlight está activo en esta página. Presiónalo con el atajo de teclado o con el botón de búsqueda de la barra superior.

o presiona
K

Incluye navegación a todas las páginas de la documentación con búsqueda fuzzy instantánea.

Qué es Spotlight

Spotlight es un command palette integrado en KoreUI que permite a los usuarios buscar y ejecutar acciones, navegar a páginas y buscar datos, todo desde el teclado.

  • Atajo de teclado Cmd+K / Ctrl+K para abrir
  • Búsqueda fuzzy instantánea sobre items locales
  • Búsqueda remota con debounce para consultas a servidor
  • Providers PHP para organizar items por grupos
  • Historial de items recientes en localStorage
  • Flujos multi-paso con dependencias (pills en el input)
  • Dark mode automático via tokens semánticos

Instalación

El Spotlight viene incluido en KoreUI. Solo necesitas agregar el componente a tu layout.

resources/views/layouts/app.blade.php
<body>
    {{ $slot }}

    {{-- Spotlight --}}
    <x-kore::spotlight />

    {{-- Otros managers --}}
    <livewire:kore-overlay-manager />
    <livewire:kore-feedback-manager />

    @livewireScripts
</body>
<body>
    {{ $slot }}

    {{-- Spotlight --}}
    <x-kore::spotlight />

    {{-- Otros managers --}}
    <livewire:kore-overlay-manager />
    <livewire:kore-feedback-manager />

    @livewireScripts
</body>

Con esto, presiona Cmd+K (Mac) o Ctrl+K (Windows/Linux) para abrir el Spotlight.

Uso mínimo

Puedes usar Spotlight sin providers, solo con búsqueda remota.

Solo búsqueda remota
<x-kore::spotlight search-url="{{ route('spotlight.search') }}" />
<x-kore::spotlight search-url="{{ route('spotlight.search') }}" />

Crear un provider

Los providers son clases PHP que generan los items del Spotlight.

app/Spotlight/NavigationProvider.php
namespace App\Spotlight;

use KoreUi\Spotlight\SpotlightItem;
use KoreUi\Spotlight\SpotlightProvider;

class NavigationProvider extends SpotlightProvider
{
    public function group(): string { return 'Navegación'; }
    public function priority(): int { return 10; }

    public function items(): array
    {
        return [
            SpotlightItem::make('Inicio')->icon('home')->route('home'),
            SpotlightItem::make('Configuración')->icon('settings')->route('settings')->shortcut('⌘,'),
        ];
    }
}
namespace App\Spotlight;

use KoreUi\Spotlight\SpotlightItem;
use KoreUi\Spotlight\SpotlightProvider;

class NavigationProvider extends SpotlightProvider
{
    public function group(): string { return 'Navegación'; }
    public function priority(): int { return 10; }

    public function items(): array
    {
        return [
            SpotlightItem::make('Inicio')->icon('home')->route('home'),
            SpotlightItem::make('Configuración')->icon('settings')->route('settings')->shortcut('⌘,'),
        ];
    }
}

Registrar providers

Registra tus providers en la configuración o directamente en el componente.

config/kore-ui.php
'spotlight' => [
    'providers' => [
        \App\Spotlight\NavigationProvider::class,
    ],
],
'spotlight' => [
    'providers' => [
        \App\Spotlight\NavigationProvider::class,
    ],
],
Override por instancia
<x-kore::spotlight :providers="[\App\Spotlight\NavigationProvider::class]" />
<x-kore::spotlight :providers="[\App\Spotlight\NavigationProvider::class]" />

API JavaScript

Controla el Spotlight programáticamente desde JavaScript.

Abrir y cerrar
// Abrir el Spotlight
window.dispatchEvent(new CustomEvent('kore:spotlight-open'));

// Abrir con query pre-llenado
window.dispatchEvent(new CustomEvent('kore:spotlight-open', {
    detail: { query: 'crear' }
}));

// Cerrar el Spotlight
window.dispatchEvent(new CustomEvent('kore:spotlight-close'));
// Abrir el Spotlight
window.dispatchEvent(new CustomEvent('kore:spotlight-open'));

// Abrir con query pre-llenado
window.dispatchEvent(new CustomEvent('kore:spotlight-open', {
    detail: { query: 'crear' }
}));

// Cerrar el Spotlight
window.dispatchEvent(new CustomEvent('kore:spotlight-close'));
Escuchar eventos
// Cuando se abre
window.addEventListener('kore:spotlight:open', () => { /* ... */ });

// Cuando se cierra
window.addEventListener('kore:spotlight:close', () => { /* ... */ });

// Cuando se selecciona un item
window.addEventListener('kore:spotlight:select', (e) => {
    console.log('Item seleccionado:', e.detail.item);
});
// Cuando se abre
window.addEventListener('kore:spotlight:open', () => { /* ... */ });

// Cuando se cierra
window.addEventListener('kore:spotlight:close', () => { /* ... */ });

// Cuando se selecciona un item
window.addEventListener('kore:spotlight:select', (e) => {
    console.log('Item seleccionado:', e.detail.item);
});

Historial reciente

Los items utilizados se guardan en localStorage y aparecen al abrir el Spotlight con el input vacío.

Limpiar historial
// Limpiar programáticamente
localStorage.removeItem('kore-spotlight-history');
// Limpiar programáticamente
localStorage.removeItem('kore-spotlight-history');

Para deshabilitarlo, usa :show-recent="false" en el componente o 'show_recent' => false en la configuración.

Búsqueda fuzzy

El algoritmo de búsqueda fuzzy integrado pondera campos por peso para resultados relevantes.

Campo Peso Descripción
name3Coincidencias en el nombre tienen mayor valor
synonyms2Términos alternativos de búsqueda
description1Descripción del item

Incluye bonus por caracteres consecutivos y por coincidencia al inicio de la cadena. Para datasets grandes (>200 items), puede reemplazarse por Fuse.js.

Tokens CSS

El Spotlight usa tokens existentes de kore-theme.css. No requiere tokens adicionales.

Token Uso
--color-kore-surfaceBackground del panel
--color-kore-surface-hoverHover de items
--color-kore-borderBordes y separadores
--color-kore-primaryItem seleccionado (10% opacity)
--color-kore-muted-fgHeaders de grupo, placeholder
--color-kore-fgTexto de items
--radius-kore-lgBorder radius del panel
--shadow-kore-xlSombra del panel

Dark mode funciona automáticamente con .dark o [data-theme="dark"] en <html>.

Props

Prop Tipo Default Descripción
shortcut string k Tecla del atajo (Cmd/Ctrl + key)
placeholder string Buscar acciones, páginas... Placeholder del input de búsqueda
providers array config(...) Override de providers por instancia
search-url string|null null Endpoint para búsqueda remota
search-method string GET Método HTTP para búsqueda remota
show-recent bool true Mostrar historial de items recientes
recent-count int 5 Cantidad de items recientes a mostrar
max-results int 50 Máximo de resultados totales
debounce int 300 Milisegundos de debounce para búsqueda remota

Configuración

Configuración completa del Spotlight en config/kore-ui.php.

config/kore-ui.php
'spotlight' => [
    // Clases PHP de providers
    'providers' => [],

    // Atajo de teclado (Cmd/Ctrl + shortcut)
    'shortcut' => 'k',

    // Placeholder del input
    'placeholder' => 'Buscar acciones, páginas...',

    // Mostrar items cuando input está vacío
    'show_results_without_input' => true,

    // Historial reciente (localStorage)
    'show_recent' => true,
    'recent_count' => 5,
    'max_history' => 10,

    // Búsqueda remota global
    'search_url' => null,
    'search_method' => 'GET',
    'debounce' => 300,

    // Límite de resultados totales
    'max_results' => 50,

    // z-index (encima de overlays z-50 y feedback z-60)
    'z_index' => 'z-[70]',
],
'spotlight' => [
    // Clases PHP de providers
    'providers' => [],

    // Atajo de teclado (Cmd/Ctrl + shortcut)
    'shortcut' => 'k',

    // Placeholder del input
    'placeholder' => 'Buscar acciones, páginas...',

    // Mostrar items cuando input está vacío
    'show_results_without_input' => true,

    // Historial reciente (localStorage)
    'show_recent' => true,
    'recent_count' => 5,
    'max_history' => 10,

    // Búsqueda remota global
    'search_url' => null,
    'search_method' => 'GET',
    'debounce' => 300,

    // Límite de resultados totales
    'max_results' => 50,

    // z-index (encima de overlays z-50 y feedback z-60)
    'z_index' => 'z-[70]',
],