Toast
Toast displays transient feedback without interrupting the current workflow.
The queue, timers, pause/resume behavior, hotkey focus, and live-region
semantics come from Spar's headless toast controller; React Spar renders each
item with Takeoff Alert anatomy by default.
Use variants to show the visual tone of the toast.
Usage
import { Toaster, createToaster } from '@takeoff-ui/react-spar';
const toaster = createToaster({ placement: 'bottom-end' });
function App() {
return (
<>
<button
type="button"
onClick={() =>
toaster.success({
title: 'Booking saved',
description: 'Passenger details were updated successfully.',
})
}
>
Save
</button>
<Toaster toaster={toaster} />
</>
);
}
Playground
Type/Variants
Toast uses type for semantic intent. React Spar maps that intent to the Alert
variant internally, so consumers do not pass a separate variant prop.
Appearance
Positions
Persistent Toast
Update Toast
Promise Toasts
Overlap
Max Visible
Duration
Page Idle
External Close
Custom Rendering
API Reference
Toaster
Props
| Name | Type | Default | Description |
|---|---|---|---|
| toaster | ToasterController | - | Toast controller returned by createToaster. |
| children | React.ReactNode | - | Optional render function for custom toast item rendering. |
| appearance | ToastAppearance | 'filled' | Alert appearance used by the default toast renderer. |
| closeLabel | string | 'Dismiss notification' | Accessible label for the default close control. |
| overlap | boolean | false | Stacks visible toasts and expands the stack on hover or focus. |
| classNames | Partial<Record<"root", string>> | - | |
| slotProps | Partial<Record<"root", React.HTMLAttributes<HTMLElement>>> | - | |
| label | string | 'Notifications (F8)' | Accessible label for the toast viewport region. |
| hotkey | string[] | ['F8'] | Keyboard shortcut that focuses the toast viewport. |
| className | string | - | Appends custom classes to the root slot of this part. |
Data attributes
| Attribute | Applied when | Purpose |
|---|---|---|
| data-slot="root" | Always | Stable selector for wrapper styling on the root slot. |
| data-placement | Always | Reflects the toaster placement for viewport positioning. |
| data-overlap | When overlap is true | Enables the overlapped visual stack recipe. |
| data-expanded | When an overlapping toaster is hovered or focused | Indicates that the overlapped stack is expanded for interaction. |
Toast
Props
| Name | Type | Default | Description |
|---|---|---|---|
| toast | ToastData | - | Toast item supplied by the headless toaster controller. |
| children | React.ReactNode | - | Optional custom toast content. When omitted, Toast renders the Takeoff Alert anatomy. |
| toaster | ToasterController | - | Controller used to pause, resume, and dismiss the toast. |
| appearance | ToastAppearance | 'filled' | Alert appearance used by the default toast renderer. |
| closeLabel | string | 'Dismiss notification' | Accessible label for the default close control. |
| classNames | Partial<Record<"root", string>> | - | |
| slotProps | Partial<Record<"root", React.HTMLAttributes<HTMLElement>>> | - | |
| className | string | - | Appends custom classes to the root slot of this part. |
Data attributes
| Attribute | Applied when | Purpose |
|---|---|---|
| data-slot="root" | Always | Stable selector for wrapper styling on the root slot. |
| data-toast-id | Always | Stable toast item identifier used for layout motion. |
| data-status | Always | Reflects the toast lifecycle status. |
| data-type | Always | Reflects the headless toast type used for styling hooks. |
Type Definitions
| Name | Definition |
|---|---|
| ToasterController | { placement: ToastPlacement; maxVisibleToasts: number; create: (options: ToastOptions) => string; success: (options: ToastOptions) => string; error: (options: ToastOptions) => string; warning: (options: ToastOptions) => string; info: (options: ToastOptions) => string; loading: (options: ToastOptions) => string; update: (id: string, options: ToastUpdateOptions) => void; dismiss: (id?: string) => void; pause: (id?: string) => void; resume: (id?: string) => void; clear: () => void; destroy: () => void; promise: <TData>(promise: Promise<TData>, options: ToastPromiseOptions<TData>) => Promise<TData>; subscribe: (listener: () => void) => () => void; getSnapshot: () => ToastData[] } |
| ToastAppearance | 'filled' | 'filledLight' | 'outlined' | 'gradient' |
| ToastData | { id: string; title?: ReactNode; description?: ReactNode; type: ToastType; duration: number | null; createdAt: number; remaining: number | null; status: ToastStatus; announcement: ToastAnnouncement; action?: ToastActionOptions | undefined; dismissible: boolean; data?: unknown } |
Controller Values
| Option | Default | Behavior |
|---|---|---|
placement | 'bottom-end' | Reflected on data-placement for viewport positioning. |
duration | 5000 | Auto-dismiss duration for ordinary toasts. |
maxVisibleToasts | 24 | Maximum number of toasts to display at once. Extra items stay queued; lower this for denser product screens. |
removeDelay | 200 | Time a dismissing toast remains mounted for exit motion. |
pauseOnPageIdle | false | Timers continue unless this option is enabled. |