Dialog is a container to display content in an overlay window.
import { Dialog } from 'primereact/dialog';
<Dialog>
<Dialog.Trigger />
<Dialog.Portal>
<Dialog.Header>
<Dialog.Title />
<Dialog.HeaderActions>
<Dialog.Maximizable />
<Dialog.Close />
</Dialog.HeaderActions>
</Dialog.Header>
<Dialog.Content />
<Dialog.Footer />
</Dialog.Portal>
</Dialog>
Dialog is defined using Dialog
, Dialog.Trigger
, Dialog.Portal
, Dialog.Header
, Dialog.Content
and Dialog.Footer
components.
import { DialogContentInstance } from '@primereact/types/shared/dialog';
import { Button } from 'primereact/button';
import { Dialog } from 'primereact/dialog';
import { InputText } from 'primereact/inputtext';
import { Label } from 'primereact/label';
export default function BasicDemo() {
return (
<div className="card flex justify-center">
<Dialog modal>
<Dialog.Trigger>Show</Dialog.Trigger>
<Dialog.Portal style={{ width: '25rem' }}>
<Dialog.Header>
<Dialog.Title>Edit Profile</Dialog.Title>
<Dialog.Close />
</Dialog.Header>
<Dialog.Content>
{(instance: DialogContentInstance) => {
const { dialog } = instance;
return (
<>
<span className="text-surface-500 dark:text-surface-400 block mb-8">Update your information.</span>
<div className="flex items-center gap-4 mb-4">
<Label htmlFor="username" className="font-semibold w-24">
Username
</Label>
<InputText id="username" className="flex-auto" autoComplete="off" />
</div>
<div className="flex items-center gap-4 mb-8">
<Label htmlFor="email" className="font-semibold w-24">
Email
</Label>
<InputText id="email" className="flex-auto" autoComplete="off" />
</div>
<div className="flex justify-end gap-2">
<Button onClick={dialog?.close} severity="secondary">
Cancel
</Button>
<Button onClick={dialog?.close}>Sign-In</Button>
</div>
</>
);
}}
</Dialog.Content>
</Dialog.Portal>
</Dialog>
</div>
);
}
The position of the dialog can be customized with the position
property. The available values are top
, top-left
, top-right
, bottom
, bottom-left
, bottom-right
, left
, right
, and center
.
import { DialogChangeEvent, DialogContentInstance, DialogProps } from '@primereact/types/shared/dialog';
import { Button } from 'primereact/button';
import { Dialog } from 'primereact/dialog';
import { InputText } from 'primereact/inputtext';
import { Label } from 'primereact/label';
import * as React from 'react';
export default function PositionDemo() {
const [open, setOpen] = React.useState<boolean>(false);
const [position, setPosition] = React.useState<DialogProps['position']>('center');
const openPosition = (position: DialogProps['position']) => {
setOpen(true);
setPosition(position);
};
return (
<div className="card">
<div className="flex flex-wrap justify-center gap-2 mb-2">
<Button onClick={() => openPosition('left')} severity="secondary" style={{ minWidth: '10rem' }}>
Left
<i className="pi pi-arrow-right" />
</Button>
<Button onClick={() => openPosition('right')} severity="secondary" style={{ minWidth: '10rem' }}>
Right
<i className="pi pi-arrow-left" />
</Button>
</div>
<div className="flex flex-wrap justify-center gap-2 mb-2">
<Button onClick={() => openPosition('topleft')} severity="secondary" style={{ minWidth: '10rem' }}>
TopLeft
<i className="pi pi-arrow-down-right" />
</Button>
<Button onClick={() => openPosition('top')} severity="secondary" style={{ minWidth: '10rem' }}>
Top
<i className="pi pi-arrow-down" />
</Button>
<Button onClick={() => openPosition('topright')} severity="secondary" style={{ minWidth: '10rem' }}>
TopRight
<i className="pi pi-arrow-down-left" />
</Button>
</div>
<div className="flex flex-wrap justify-center gap-2">
<Button onClick={() => openPosition('bottomleft')} severity="secondary" style={{ minWidth: '10rem' }}>
BottomLeft
<i className="pi pi-arrow-up-right" />
</Button>
<Button onClick={() => openPosition('bottom')} severity="secondary" style={{ minWidth: '10rem' }}>
Bottom
<i className="pi pi-arrow-up" />
</Button>
<Button onClick={() => openPosition('bottomright')} severity="secondary" style={{ minWidth: '10rem' }}>
BottomRight
<i className="pi pi-arrow-up-left" />
</Button>
</div>
<Dialog open={open} onOpenChange={(e: DialogChangeEvent) => setOpen(e.value as boolean)} modal position={position} draggable={false}>
<Dialog.Portal style={{ width: '25rem' }}>
<Dialog.Header>
<Dialog.Title>Edit Profile</Dialog.Title>
<Dialog.HeaderActions>
<Dialog.Close />
</Dialog.HeaderActions>
</Dialog.Header>
<Dialog.Content>
{(instance: DialogContentInstance) => {
const { dialog } = instance;
return (
<>
<span className="text-surface-500 dark:text-surface-400 block mb-8">Update your information.</span>
<div className="flex items-center gap-4 mb-4">
<Label htmlFor="username" className="font-semibold w-24">
Username
</Label>
<InputText id="username" className="flex-auto" autoComplete="off" />
</div>
<div className="flex items-center gap-4 mb-8">
<Label htmlFor="email" className="font-semibold w-24">
Email
</Label>
<InputText id="email" className="flex-auto" autoComplete="off" />
</div>
<div className="flex justify-end gap-2">
<Button type="button" severity="secondary" onClick={dialog?.close}>
Cancel
</Button>
<Button type="button" onClick={dialog?.close}>
Save
</Button>
</div>
</>
);
}}
</Dialog.Content>
</Dialog.Portal>
</Dialog>
</div>
);
}
A dialog can be maximized by clicking the Dialog.Maximizable button.
import { Dialog } from 'primereact/dialog';
export default function MaximizableDemo() {
return (
<div className="card flex justify-center">
<Dialog modal>
<Dialog.Trigger>Show</Dialog.Trigger>
<Dialog.Portal style={{ width: '50rem' }}>
<Dialog.Header>
<Dialog.Title>Header</Dialog.Title>
<Dialog.HeaderActions>
<Dialog.Maximizable />
<Dialog.Close />
</Dialog.HeaderActions>
</Dialog.Header>
<Dialog.Content>
<p>
Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo
consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est
laborum.
</p>
</Dialog.Content>
</Dialog.Portal>
</Dialog>
</div>
);
}
Mask layer behind the Dialog is configured with the modal property. By default, no modal layer is added.
import { DialogContentInstance } from '@primereact/types/shared/dialog';
import { Button } from 'primereact/button';
import { Dialog } from 'primereact/dialog';
import { InputText } from 'primereact/inputtext';
import { Label } from 'primereact/label';
export default function WithoutModalDemo() {
return (
<div className="card flex justify-center">
<Dialog>
<Dialog.Trigger>Show</Dialog.Trigger>
<Dialog.Portal style={{ width: '25rem' }}>
<Dialog.Header>
<Dialog.Title>Edit Profile</Dialog.Title>
<Dialog.HeaderActions>
<Dialog.Close />
</Dialog.HeaderActions>
</Dialog.Header>
<Dialog.Content>
{(instance: DialogContentInstance) => {
const { dialog } = instance;
return (
<>
<span className="text-surface-500 dark:text-surface-400 block mb-8">Update your information.</span>
<div className="flex items-center gap-4 mb-4">
<Label htmlFor="username" className="font-semibold w-24">
Username
</Label>
<InputText id="username" className="flex-auto" autoComplete="off" />
</div>
<div className="flex items-center gap-4 mb-8">
<Label htmlFor="email" className="font-semibold w-24">
Email
</Label>
<InputText id="email" className="flex-auto" autoComplete="off" />
</div>
<div className="flex justify-end gap-2">
<Button type="button" severity="secondary" onClick={dialog?.close}>
Cancel
</Button>
<Button type="button" onClick={dialog?.close}>
Save
</Button>
</div>
</>
);
}}
</Dialog.Content>
</Dialog.Portal>
</Dialog>
</div>
);
}
Dialog component uses dialog
role along with aria-labelledby
referring to the header element however any attribute is passed to the root element so you may use aria-labelledby
to override this default behavior. In addition aria-modal
is added since focus is kept within the popup.
Trigger element also has aria-expanded and aria-controls to be handled explicitly.
Key | Function |
---|---|
tab | Moves focus to the next the focusable element within the dialog if modal is true. Otherwise, the focusable element in the page tab sequence. |
shift + tab | Moves focus to the previous the focusable element within the dialog if modal is true. Otherwise, the focusable element in the page tab sequence. |
escape | Closes the dialog if closeOnEscape is true. |
Key | Function |
---|---|
enter | Closes the dialog. |
space | Closes the dialog. |