Toast

10 parts

A single toast notification. Manages its own open state and auto-dismiss timer, and provides context to its Title, Description, Action, and Close children. Control visibility with v-model:open; rendering is gated by Presence so exit transitions can play before the element unmounts. The default slot receives { open, remaining, duration } so you can render a progress bar or countdown synced to the dismiss timer.

Demo

Loading demo…

Anatomy

Import the parts and compose them. Each part forwards attributes to its underlying element.

vue
import {
  ToastProvider,
  ToastRoot,
  ToastTitle,
  ToastDescription,
  ToastAction,
  ToastClose,
  ToastViewport,
  ToastAnnounce,
  ToastAnnounceExclude,
  ToastPortal,
} from '@robonen/primitives/feedback/toast';

<ToastRoot>
  <ToastProvider />
  <ToastTitle />
  <ToastDescription />
  <ToastAction />
  <ToastClose />
  <ToastViewport />
  <ToastAnnounce />
  <ToastAnnounceExclude />
  <ToastPortal />
</ToastRoot>

API Reference

ToastProvider

Provider

Toast — a succinct, non-disruptive notification that appears in a corner of the screen and auto-dismisses after a timeout. Use it to confirm actions or surface background events without interrupting the user's flow. `ToastProvider` is the top-level wrapper that holds shared settings (label, default duration, swipe behaviour) and coordinates timer pausing across all toasts. Wrap your app (or the region that renders toasts) in a single provider, render one `ToastViewport` for placement, and mount a `ToastRoot` per notification.

PropTypeDescription
label?stringAccessible label for the toast region.
duration?numberAuto-dismiss duration in ms. Use Infinity to disable auto-dismiss.
swipeDirection?SwipeDirectionSwipe direction that dismisses a toast.
swipeThreshold?numberMinimum swipe distance (px) before a dismiss gesture is recognised.
disableSwipe?booleanDisable swipe-to-dismiss gestures for every toast.

ToastRoot

Root

A single toast notification. Manages its own open state and auto-dismiss timer, and provides context to its `Title`, `Description`, `Action`, and `Close` children. Control visibility with `v-model:open`; rendering is gated by `Presence` so exit transitions can play before the element unmounts. The default slot receives `{ open, remaining, duration }` so you can render a progress bar or countdown synced to the dismiss timer.

PropTypeDescription
duration?numberOverride the provider's auto-dismiss duration. Use Infinity to disable.
type?'foreground' | 'background'Toast type — controls the aria-live politeness.
defaultOpen?booleanInitial open state for the uncontrolled mode (when v-model:open is not bound).
forceMount?booleanForce the toast to stay mounted regardless of open (useful with external animation libraries).
toViewport?booleanTeleport this toast into the ToastViewport and register it for keyboard focus ordering. Lets toasts be authored anywhere in the tree. When the viewport is not mounted yet, the toast renders in place as a fallback.
open?booleanTwo-way bound value (v-model:open).
Emits
EventPayload
update:open[value: boolean]

ToastTitle

Title

The toast's heading. Renders the short, prominent line that names the notification, placed inside a `ToastRoot`.

No props or events — renders its element and forwards attributes.

ToastDescription

Description

The toast's supporting text. Renders the longer description beneath the `ToastTitle`, placed inside a `ToastRoot`.

No props or events — renders its element and forwards attributes.

ToastAction

Action

An actionable control inside a toast (e.g. "Undo" or "View"). Renders a button by default and requires `altText` so the action remains understandable to assistive technology even when the toast is announced out of context — `altText` is read by the announce region in place of the button's visible label.

PropTypeDescription
altTextstringAccessible description for screen readers (required). Describes what happens when the user triggers the action.

ToastClose

Close

A button that dismisses the toast it lives in. Renders a button by default and closes the parent `ToastRoot` via toast context on click. Its visible content is excluded from the screen-reader announcement (an icon-only "×" carries no meaning out of context).

No props or events — renders its element and forwards attributes.

ToastViewport

Viewport

The fixed-position region (an `<ol>`) where toasts are rendered. Provides the accessible landmark for the toast list, pauses auto-dismiss timers on hover/focus/window-blur, can be focused via a keyboard hotkey, and manages tab order across portaled toasts (newest-first) with head/tail focus proxies. Render exactly one per provider.

PropTypeDescription
label?string | ((hotkey: string) => string)Accessible label for the toast region. Overrides the provider label. The {hotkey} placeholder is replaced with the configured hotkey, and a (hotkey) => string function form is also accepted.
hotkey?string[]Keyboard shortcut to focus the viewport.

ToastAnnounce

Announce

A visually-hidden live region that mirrors a toast's text for screen readers. The visible toast is announced via `aria-live` directly, but some screen readers (notably NVDA) only reliably announce live-region content that is injected *after* the region is already in the accessibility tree. This part therefore mounts empty and injects its text on the next frame (double `requestAnimationFrame`), with a 1s timeout fallback so the announcement still happens if frames are throttled (e.g. a background tab).

PropTypeDescription
ariaLive?'assertive' | 'polite'aria-live politeness for the announce region.

ToastAnnounceExclude

AnnounceExclude

Excludes its subtree from the screen-reader announcement harvested by `ToastAnnounce`. Use it around content whose visible text is meaningless out of context (e.g. an icon-only button) — optionally provide `altText` to be announced in its place. `ToastAction` and `ToastClose` use this internally.

PropTypeDescription
altText?stringText announced in place of the excluded subtree.

ToastPortal

Portal

Renders the toast viewport into a different part of the DOM (a portal), so it escapes parent overflow/stacking contexts. Wrap `ToastViewport` in this part to mount it at the document body (default) or a custom container via `to`.

No props or events — renders its element and forwards attributes.