frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Save for later?"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Save"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
    >
        You can always set up this campaign at a later time.
    </Dialog>
</div>
const Example = () => {
    const [open, setOpen] = React.useState(false);
    const toggleOpen = () => setOpen(!open);

    return (
        <div>
            <Button onClick={toggleOpen}>Live Demo</Button>

            <Dialog
                open={open}
                onClose={toggleOpen}
                title="Closable Dialog"
                onPrimaryActionClick={toggleOpen}
                primaryActionName="Save"
                onSecondaryActionClick={toggleOpen}
                secondaryActionName="Cancel"
            >
                Both buttons in this demo will close the dialog.
            </Dialog>
        </div>
    );
}
render (Example)

Negative / Destructive

The dialog's primary action can signify a destructive action. Negative dialogs contain two actions.

frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Delete email"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Delete"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
        negative
    >
        Are you sure you want to delete this email and it scheduling interval?
    </Dialog>
</div>
frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Delete email"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Delete"
        negative
    >
        Are you sure you want to delete this email and it scheduling interval?
    </Dialog>
</div>

Actions

Dialogs require at least one action, with no more than two.

  • When only one action is provided, it is an acknowledgement action.
  • When two actions are provided, the primary action is a confirming action, and the secondary a dismissing action.

Non-closable Dialog

Dialog should be closable in most cases, by clicking on the background around the dialog. For other cases, non-closable Dialog can be implemented removing onClose prop. This creates a mandatory action in a workflow.

const Example = () => {
    const [open, setOpen] = React.useState(false);
    const toggleOpen = () => setOpen(!open);

    return (
        <div>
            <Button onClick={toggleOpen}>Demo Non-closable Dialog</Button>

            <Dialog
                open={open}
                title="Closable Dialog"
                onPrimaryActionClick={toggleOpen}
                primaryActionName="I agree"
            >
                This is something of great importance.
            </Dialog>
        </div>
    );
}
render (Example);

Dialog Examples

Examples with Two Actions

frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Call Jane Doe?"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Call"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
    >
    Do you want to call Jane Doe at (123){'\u00A0'}456–7890?
    </Dialog>
</div>
frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Send to Closed?"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Send"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
    >
    Are you sure you want to send this to closed? You can’t reply to closed{'\u00A0'}messages.
    </Dialog>
</div>
frame: true
---
<div style={{ height: '350px' }}>
    <Dialog
        open={true}
        title="Confirmation"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Continue"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
    >
    <p className="m-t-0">You are about to save changes to an active template. It may take a while for the changes to take effect in Inventory.</p>
    <p>Would you like to continue?</p>
    </Dialog>
</div>
frame: true
---
<div style={{ height: '350px' }}>
    <Dialog
        open={true}
        title="Delete Report"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Delete Report"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
        negative
    >
    <p className="m-t-0">You have 3 scheduled reports for Accounts Receivable Summary by Invoice Type.</p>
    <p>Deleting this report will also delete its scheduled reports.</p>
    </Dialog>
</div>
frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Deactivation Confirmation"
        portal={false}
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
        onPrimaryActionClick={() => {}}
        primaryActionName="Deactivate"
        negative
    >
        Once deactivated, serial numbers associated with this item will be deleted and cannot be recovered.
    </Dialog>
</div>
frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        portal={false}
        title="Discard drafts from this conversation?"
        onSecondaryActionClick={() => {}}
        secondaryActionName="Cancel"
        onPrimaryActionClick={() => {}}
        primaryActionName="Discard"
    />
</div>

Examples with One Acknowledgement Action

frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Not in Stock"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Ok"
    >
        This item is no longer available.
    </Dialog>
</div>
frame: true
---
<div style={{ height: '300px' }}>
    <Dialog
        open={true}
        title="Set up Later"
        portal={false}
        onPrimaryActionClick={() => {}}
        primaryActionName="Ok"
    >
        No worries. You can always set up TitanPhone later in <Link primary>Settings > Phone</Link>.
    </Dialog>
</div>

Differences from a Modal

Dialogs are more restrictive in their options relative to modals.

  • Can only be X-Small in size.
  • Cannot have scrolling content.
  • Cannot have the close icon × in the top right.
  • Must have one or two actions.
  • The footer can only be right aligned, with only solid-filled buttons.
  • Only the primary action button can be customized: primary solid or negative solid.
  • Body content is optional.

Best Practices

  • Dialogs should only be used if they require the user to be interrupted.
  • For actions, avoid 'Yes' and 'No' responses.
  • If an action involves cancelling an operation, it should be the secondary action, usually labeled 'Cancel'.
  • Like modals, dialogs should be used sparingly. Particularly with one action dialogs.

Related Components

  • For more complex interactions that require user interruption, use a Modal.
  • To completely hide the context of the page, use a Takeover component.
  • For information that does not require user interruption, use a Toast or Banner notification.

Importing

import { Dialog } from '@servicetitan/design-system';