Toast
FeedbackNotificaciones temporales con soporte para 6 tipos, acciones inline, agrupamiento, loading/resolve y swipe-to-dismiss.
Demo en vivo
Prueba los toasts directamente. Cada botón dispara un toast real con diferente configuración.
Tipos
Posiciones
Funcionalidades
Loading / Resolve
Introducción
Los toasts son notificaciones no intrusivas que aparecen en una esquina de la pantalla. Se despachan desde componentes Livewire usando el trait InteractsWithFeedback.
Requisito: Tu layout debe incluir <livewire:kore-feedback-manager /> para que los toasts se rendericen correctamente.
Configuración inicial
Agrega el feedback manager a tu layout y el trait a tus componentes Livewire.
<body>
{{ $slot }}
<livewire:kore-overlay-manager />
<livewire:kore-feedback-manager />
@livewireScripts
</body><body>
{{ $slot }}
<livewire:kore-overlay-manager />
<livewire:kore-feedback-manager />
@livewireScripts
</body>namespace App\Livewire;
use KoreUi\Core\Concerns\InteractsWithFeedback;
use Livewire\Component;
class MyComponent extends Component
{
use InteractsWithFeedback;
public function save(): void
{
// ... lógica de guardado ...
$this->toast()->success('Guardado correctamente')->send();
}
}namespace App\Livewire;
use KoreUi\Core\Concerns\InteractsWithFeedback;
use Livewire\Component;
class MyComponent extends Component
{
use InteractsWithFeedback;
public function save(): void
{
// ... lógica de guardado ...
$this->toast()->success('Guardado correctamente')->send();
}
}Uso básico
Los toasts se crean con el método fluent toast() y se envían con send().
$this->toast()->success('Registro guardado')->send();
$this->toast()->error('Error al guardar', 'Revisa los campos requeridos.')->send();
$this->toast()->warning('Sin conexión')->send();
$this->toast()->info('Nuevo mensaje', 'Tienes 3 mensajes sin leer.')->send();$this->toast()->success('Registro guardado')->send();
$this->toast()->error('Error al guardar', 'Revisa los campos requeridos.')->send();
$this->toast()->warning('Sin conexión')->send();
$this->toast()->info('Nuevo mensaje', 'Tienes 3 mensajes sin leer.')->send();El segundo argumento es una descripción opcional que hace el toast expandible.
Tipos
Cada tipo tiene un ícono, color y timeout predeterminado.
| Tipo | Ícono | Color | Auto-dismiss |
|---|---|---|---|
success | circle-check | kore-success | 5s |
error | circle-x | kore-destructive | No (persistente) |
warning | triangle-alert | kore-warning | 8s |
info | info | kore-info | 5s |
question | circle-help | kore-primary | No (persistente) |
loading | loader-circle (spin) | kore-muted | No (persistente) |
$this->toast()->success('Registro guardado')->send();
$this->toast()->error('Error al guardar', 'Revisa los campos requeridos.')->send();
$this->toast()->warning('Sin conexión')->send();
$this->toast()->info('Nuevo mensaje', 'Tienes 3 mensajes sin leer.')->send();
$this->toast()->question('¿Descartar cambios?')->confirm('Sí', 'discard')->cancel('No')->send();
$this->toast()->loading('Importando archivo...')->send();$this->toast()->success('Registro guardado')->send();
$this->toast()->error('Error al guardar', 'Revisa los campos requeridos.')->send();
$this->toast()->warning('Sin conexión')->send();
$this->toast()->info('Nuevo mensaje', 'Tienes 3 mensajes sin leer.')->send();
$this->toast()->question('¿Descartar cambios?')->confirm('Sí', 'discard')->cancel('No')->send();
$this->toast()->loading('Importando archivo...')->send();Timeout y persistencia
Controla cuánto tiempo permanece visible un toast.
// Timeout personalizado (en segundos)
$this->toast()->success('Listo')->timeout(10)->send();
// Persistente — permanece hasta que se cierra manualmente
$this->toast()->info('Aviso importante')->persistent()->send();// Timeout personalizado (en segundos)
$this->toast()->success('Listo')->timeout(10)->send();
// Persistente — permanece hasta que se cierra manualmente
$this->toast()->info('Aviso importante')->persistent()->send();La barra de progreso y el temporizador se pausan al hacer hover sobre el toast y continúan al salir.
Posiciones
6 posiciones disponibles. El default es top-right (configurable).
$this->toast()->success('Guardado')->position('bottom-left')->send();$this->toast()->success('Guardado')->position('bottom-left')->send();top-lefttop-centertop-rightbottom-leftbottom-centerbottom-rightVarios toasts en diferentes posiciones se renderizan en contenedores separados simultáneamente.
Acciones
Botones de acción inline que llaman métodos Livewire.
$this->toast()
->success('Elemento eliminado')
->action('Deshacer', 'undoDelete', [42])
->action('Ver papelera', 'showTrash')
->timeout(8)
->send();$this->toast()
->success('Elemento eliminado')
->action('Deshacer', 'undoDelete', [42])
->action('Ver papelera', 'showTrash')
->timeout(8)
->send();Confirm/Cancel en Toast
Para decisiones rápidas sí/no sin abrir un dialog completo.
$this->toast()
->question('¿Descartar cambios?')
->confirm('Sí, descartar', 'discard')
->cancel('No')
->send();$this->toast()
->question('¿Descartar cambios?')
->confirm('Sí, descartar', 'discard')
->cancel('No')
->send();Loading y Resolve
Un toast que representa una operación en curso y se transforma in-place cuando termina.
public function importCsv(): void
{
// 1. Crear toast de loading — retorna el ID
$toastId = $this->toast()->loading('Importando archivo...')->send();
try {
$count = $this->processFile($this->file);
// 2. Resolver con éxito — transforma el toast existente
$this->toast()->resolve($toastId)->success("{$count} registros importados")->send();
} catch (\Exception $e) {
// 2. Resolver con error
$this->toast()->resolve($toastId)->error('Importación fallida', $e->getMessage())->send();
}
}public function importCsv(): void
{
// 1. Crear toast de loading — retorna el ID
$toastId = $this->toast()->loading('Importando archivo...')->send();
try {
$count = $this->processFile($this->file);
// 2. Resolver con éxito — transforma el toast existente
$this->toast()->resolve($toastId)->success("{$count} registros importados")->send();
} catch (\Exception $e) {
// 2. Resolver con error
$this->toast()->resolve($toastId)->error('Importación fallida', $e->getMessage())->send();
}
}Los toasts de loading son persistentes, no se pueden cerrar manualmente y no se agrupan.
Agrupamiento
Toasts idénticos (mismo tipo + título) se fusionan automáticamente en uno con un badge contador.
// Click 3 veces → muestra "Registro guardado (3)" en lugar de 3 toasts separados
$this->toast()->success('Registro guardado')->send();
// Forzar individual (sin agrupamiento)
$this->toast()->success('Registro guardado')->noGroup()->send();// Click 3 veces → muestra "Registro guardado (3)" en lugar de 3 toasts separados
$this->toast()->success('Registro guardado')->send();
// Forzar individual (sin agrupamiento)
$this->toast()->success('Registro guardado')->noGroup()->send();El agrupamiento se deshabilita automáticamente cuando un toast tiene acciones, opciones de confirm/cancel o hooks.
Modo Sole
Limpia todos los toasts existentes antes de mostrar el nuevo.
$this->toast()->info('Solo este toast')->sole()->send();$this->toast()->info('Solo este toast')->sole()->send();Hooks
Ejecuta métodos Livewire cuando un toast se cierra o expira.
$this->toast()
->info('Procesando...')
->hook('close', 'onToastClosed')
->hook('timeout', 'onToastExpired', [42])
->timeout(5)
->send();$this->toast()
->info('Procesando...')
->hook('close', 'onToastClosed')
->hook('timeout', 'onToastExpired', [42])
->timeout(5)
->send();Session Flash
Fuerza la entrega vía session flash en lugar de dispatch de Livewire. Útil para redirects.
$this->toast()->success('Bienvenido de vuelta')->viaSession()->send();
return redirect()->route('dashboard');$this->toast()->success('Bienvenido de vuelta')->viaSession()->send();
return redirect()->route('dashboard');Cuando usas kore_toast() o Kore::toast() fuera de Livewire, session flash se usa automáticamente.
Uso fuera de Livewire
Desde controllers, middleware, o cualquier lugar sin componente Livewire.
// Helper function
kore_toast()->success('Creado correctamente')->send();
// Facade
use KoreUi\Facades\Kore;
Kore::toast()->success('Creado correctamente')->send();// Helper function
kore_toast()->success('Creado correctamente')->send();
// Facade
use KoreUi\Facades\Kore;
Kore::toast()->success('Creado correctamente')->send();Estos métodos usan session()->flash() automáticamente, por lo que el toast aparece después del redirect.
Accesibilidad
El sistema de toasts implementa las mejores prácticas de accesibilidad.
- Contenedor de toasts:
role="region"conaria-live="polite" - Toasts de error:
role="alert"(interrumpe el lector de pantalla) - Otros toasts:
role="status" - Botón de cerrar:
aria-label="Cerrar notificación" prefers-reduced-motion: reducedeshabilita animaciones spring y transiciones- Swipe-to-dismiss en dispositivos táctiles (dirección según el borde más cercano)
Props
| Prop | Tipo | Default | Descripción |
|---|---|---|---|
type
|
string | - | Tipo del toast: success, error, warning, info, question, loading |
title
|
string | - | Título del toast (primer argumento del tipo) |
description
|
string|null | null | Descripción opcional (segundo argumento del tipo) |
timeout
|
int | 5 | Segundos antes de auto-dismiss (0 = persistente) |
position
|
string | top-right | Posición: top-left, top-center, top-right, bottom-left, bottom-center, bottom-right |
dismissible
|
bool | true | Permite cerrar manualmente el toast |
persistent()
|
method | - | Hace el toast persistente (no auto-dismiss) |
sole()
|
method | - | Limpia todos los toasts antes de mostrar este |
noGroup()
|
method | - | Deshabilita el agrupamiento automático |
action(label, method, params)
|
method | - | Agrega un botón de acción que llama un método Livewire |
confirm(label, method)
|
method | - | Botón de confirmación en toast tipo question |
cancel(label)
|
method | - | Botón de cancelar en toast tipo question |
hook(event, method, params)
|
method | - | Ejecuta método Livewire en eventos close o timeout |
viaSession()
|
method | - | Fuerza entrega vía session flash |
resolve(toastId)
|
method | - | Transforma un toast de loading existente |
Configuración
Personaliza los defaults del sistema de toasts en config/kore-ui.php.
'feedback' => [
'toast' => [
'position' => 'top-right', // top-left|top-center|top-right|bottom-left|bottom-center|bottom-right
'timeout' => 5, // segundos, 0 = persistente
'dismissible' => true,
'max_visible' => 5,
'swipe_to_dismiss' => true,
],
],'feedback' => [
'toast' => [
'position' => 'top-right', // top-left|top-center|top-right|bottom-left|bottom-center|bottom-right
'timeout' => 5, // segundos, 0 = persistente
'dismissible' => true,
'max_visible' => 5,
'swipe_to_dismiss' => true,
],
],