Overview
Dialogs are high-level components used to render modal popups such as preferences, repository settings, and error messages. They’re built on the HTML5<dialog> element and are shown as modals, constraining tab navigation within the dialog itself.
Basic Structure
A typical dialog follows this structure:Dialog Component
The mainDialog component accepts several important props:
Example Implementation
Fromapp/src/ui/dialog/dialog.tsx:252:
Dialog Footer
OkCancelButtonGroup
TheOkCancelButtonGroup component handles platform-specific button ordering automatically:
- Windows/Linux: Ok, Cancel
- macOS: Cancel, Ok
This follows platform conventions as outlined in Nielsen Norman Group’s research on button order.
Basic Usage
Customization Options
Fromapp/src/ui/dialog/ok-cancel-button-group.tsx:5:
Destructive Dialogs
destructive prop:
- Makes the Cancel button the submit button (default action)
- Prevents accidental destructive actions
- Does not change which button triggers
onSubmitvsonDismissed
Error Handling
Inline Errors
Dialogs should render errors inline using theDialogError component rather than opening new error dialogs.
From app/src/ui/dialog/error.tsx:16:
Usage Example
The
DialogError component must be the first child of the Dialog element.Error Content Guidelines
1
Use text-based content
Keep error content primarily text-based and concise.
2
Omit 'Error' prefix
Don’t include the word “Error” - the styling makes it evident.
3
Be specific
Provide actionable information about what went wrong.
Best Practices
Content Structure
DO: Let child components renderDialogContent
Layout Components
DO: UseRow components for layout
The Row component receives bottom margin when used as an immediate child of DialogContent, making it excellent for structuring content.
For primary text content, use <p> elements instead of Row.
Accessibility
Focus Management
Dialogs automatically manage focus based on this priority order:1
Preferred focus element
Element with
DialogPreferredFocusClassName class2
Lowest positive tabIndex
Element with the lowest explicit tab index
3
First tabbable element
First input, textarea, or tabIndex=0 element
4
First submit button
Default action button
5
Any button
Remaining focusable buttons
6
Close button
Dialog dismiss button
ARIA Attributes
For alert dialogs that interrupt user workflow:Dialog Lifecycle
Dismissal Grace Period
Dialogs implement a 250ms grace period after mounting before acknowledging dismissal:Form Submission
All dialogs contain a top-level form element:- Submit: Triggers
onSubmitevent (affirmative action) - Reset: Triggers
onDismissedevent (cancel action) - Keyboard shortcuts: Ctrl/Cmd+W or Escape dismisses the dialog