Skip to content
Component

Modal

Dialog and AlertDialog are both modal overlays, wrapping Base UI. AlertDialog is for blocking confirmations that require an explicit choice.

Dialog

Initial focus lands on the first focusable element of your content - the name field here - because the close button follows children in the DOM, even though it sits top-right.

  • Content takes mobileBehavior: dialog | sheet | fullscreen, implemented with CSS max-sm: variants

When to use

  • The user must finish or explicitly dismiss a task before returning to the page (edit forms, confirmations, focused workflows).
  • AlertDialog specifically: destructive or irreversible actions that need an explicit yes/no, not a passive notice.

When not to use

  • Non-blocking status or a short message - use Toast or Notification instead.
  • Content the user should be able to reference alongside the page - use Drawer or Popover instead.
  • A simple yes/no that isn't destructive - a plain Dialog with two buttons is lighter than AlertDialog's stricter close semantics.

Keyboard

KeyAction
EscapeCloses the dialog (AlertDialog can be configured to block this for critical flows).
Tab / Shift+TabCycles focus within the dialog only - focus is trapped while open.
Enter / SpaceActivates the focused button, including Trigger and Close.

Mobile behavior

  • mobileBehavior="dialog" (default): stays a centered card at every width - use for short content that doesn't benefit from more room.
  • mobileBehavior="sheet": centered dialog on desktop, becomes a bottom-anchored full-width sheet under 640px - use for forms and taller content on mobile.
  • mobileBehavior="fullscreen": centered dialog on desktop, becomes a fully fullscreen view under 640px - use for complex, multi-step, or scroll-heavy content on mobile.
  • All three are pure CSS (max-sm: variants), so there's no layout flash or JS viewport check on first paint.

Accessibility notes

  • Base UI applies role="dialog" (or role="alertdialog" for AlertDialog), aria-modal, and wires Dialog.Title/Dialog.Description to aria-labelledby/aria-describedby automatically.
  • Focus moves into the dialog on open - onto the first focusable element of the content, not the close button - and returns to the trigger on close.
  • The backdrop is inert to screen readers and pointer events outside the dialog while open.

Common mistakes

  • Omitting Dialog.Description for a form-heavy dialog - screen reader users get a title but no context for what they're editing.
  • Using Dialog for a destructive action instead of AlertDialog - Dialog closes on outside click/Escape by default, which is exactly wrong for "delete this forever."
  • Nesting a second modal dialog inside a dialog - stack Drawer or Popover instead if you need a secondary surface.

Known limitations

  • No built-in scroll-lock exception for iOS Safari's rubber-band scroll; verify manually on longer dialog content.

Related components

CriterionStatusNote
Keyboard supportSupportedEscape closes; Tab/Shift+Tab cycle within a focus trap.
Focus managementSupportedFocus enters on open, returns to the trigger on close.
Screen reader labelsSupportedrole="dialog"/"alertdialog", aria-modal, and Title/Description wiring via Base UI.
Reduced motionSupportedprefers-reduced-motion: reduce zeroes all Fuji transition durations globally.
Reduced transparencySupportedprefers-reduced-transparency: reduce flattens Glass to opaque surfaces (portals included).
RTL layoutPartialLogical flex/grid gap works under dir="rtl"; directional chevrons are not yet mirrored.

API reference

Also accepts everything from React.ComponentPropsWithoutRef<typeof import("@base-ui/react/dialog").Dialog.Root>.

Dialog.Content props

hideCloseButtonfalse
boolean

Hides the built-in top-right close button.

mobileBehavior"dialog"
OverlayMobileBehavior

How the dialog presents on narrow viewports. CSS-driven, no JS viewport checks.

Also accepts everything from React.ComponentPropsWithoutRef<typeof import("@base-ui/react/dialog").Dialog.Popup>.

Coding agents read this reference, with its examples, from the version your project has installed, through the Fuji UI MCP server. Set up your agent