Informs users while preserving the current page state.
Basic usage
Dialog pops up a dialog box, and it's quite customizable.
Set model-value / v-model attribute with a Boolean, and Dialog shows when it is true. The Dialog has two parts: body and footer, and the latter requires a slot named footer. The optional title attribute (empty by default) is for defining a title. Finally, this example demonstrates how before-close is used.
export function DialogBasicUsage() { const [visible, setVisible] = useState(false); return ( <> <ElButton plain onClick={() => setVisible(true)}> Click to open the Dialog </ElButton> <ElDialog visible={visible} onVisibleChange={setVisible} title="Tips" width={500} beforeClose={(done) => { MessageBox.confirm("Are you sure to close this dialog?") .then(() => done()) .catch(() => {}); }} footer={ <Footer cancel={() => setVisible(false)} confirm={() => setVisible(false)} /> } > <span>This is a message</span> </ElDialog> </> );}
TIP
before-close only works when user clicks the close icon or the backdrop. If you have buttons that close the Dialog in the footer named slot, you can add what you would do with before-close in the buttons' click event handler.
Customized Content
The content of Dialog can be anything, even a table or a form. This example shows how to use Element Plus Table and Form with Dialog.
The header slot can be used to customize the area where the title is displayed. In order to maintain accessibility, use the title attribute in addition to using this slot, or use the titleId slot property to specify which element should be read out as the dialog title.
export function DialogCustomizationHeader() { const [visible, setVisible] = useState(false); return ( <> <ElButton plain onClick={() => setVisible(true)}> Open Dialog with customized header </ElButton> <ElDialog visible={visible} onVisibleChange={setVisible} showClose={false} width={500} header={({ close, titleId, titleClass }) => ( <div style={{ display: "flex", flexDirection: "row", justifyContent: "space-between", gap: 16, }} > <h4 id={titleId} className={titleClass} style={{ margin: 0 }}> This is a custom header! </h4> <ElButton type="danger" onClick={close}> <CircleCloseFilled style={{ marginRight: 4 }} /> Close </ElButton> </div> )} > This is dialog content. </ElDialog> </> );}
Nested Dialog
If a Dialog is nested in another Dialog, append-to-body is required.
Normally we do not recommend using nested Dialog. If you need multiple Dialogs rendered on the page, you can simply flat them so that they're siblings to each other. If you must nest a Dialog inside another Dialog, set append-to-body of the nested Dialog to true, and it will append to body instead of its parent node, so both Dialogs can be correctly rendered.
export function DialogNestedDialog() { const [outerVisible, setOuterVisible] = useState(false); const [innerVisible, setInnerVisible] = useState(false); return ( <> <ElButton plain onClick={() => setOuterVisible(true)}> Open the outer Dialog </ElButton> <ElDialog visible={outerVisible} onVisibleChange={setOuterVisible} title="Outer Dialog" width={800} footer={ <Footer cancel={() => setOuterVisible(false)} confirm={() => setInnerVisible(true)} confirmText="Open the inner Dialog" /> } > <span>This is the outer Dialog</span> <ElDialog visible={innerVisible} onVisibleChange={setInnerVisible} width={500} title="Inner Dialog" appendToBody > <span>This is the inner Dialog</span> </ElDialog> </ElDialog> </> );}
Centered content
Dialog's content can be centered.
Setting center to true will center dialog's header and footer horizontally. center only affects Dialog's header and footer. The body of Dialog can be anything, so sometimes it may not look good when centered. You need to write some CSS if you wish to center the body as well.
export function DialogCenteredContent() { const [visible, setVisible] = useState(false); return ( <> <ElButton plain onClick={() => setVisible(true)}> Click to open the Dialog </ElButton> <ElDialog visible={visible} onVisibleChange={setVisible} title="Warning" width={500} center footer={ <Footer cancel={() => setVisible(false)} confirm={() => setVisible(false)} /> } > <span> It should be noted that the content will not be aligned in center by default </span> </ElDialog> </> );}
TIP
The content of Dialog is lazily rendered, which means the default slot is not rendered onto the DOM until it is firstly opened. Therefore, if you need to perform a DOM manipulation or access a component using ref, do it in the open event callback.
Align Center dialog
Open dialog from the center of the screen.
Setting align-center to true will center the dialog both horizontally and vertically. The prop top will not work at the same time because the dialog is vertically centered in a flexbox.
export function DialogAlignCenter() { const [visible, setVisible] = useState(false); return ( <> <ElButton plain onClick={() => setVisible(true)}> Click to open the Dialog </ElButton> <ElDialog visible={visible} onVisibleChange={setVisible} title="Warning" width={500} alignCenter footer={ <Footer cancel={() => setVisible(false)} confirm={() => setVisible(false)} /> } > <span>Open the dialog from the center from the screen</span> </ElDialog> </> );}
Destroy on Close
When this is feature is enabled, the content under default slot will be destroyed with a v-if directive. Enable this when you have perf concerns.
Note that by enabling this feature, the content will not be rendered before transition.beforeEnter dispatched, there will only be overlayheader(if any)footer(if any).
export function DialogDestroyOnClose() { const [visible, setVisible] = useState(false); return ( <> <ElButton plain onClick={() => setVisible(true)}> Click to open Dialog </ElButton> <ElDialog visible={visible} onVisibleChange={setVisible} title="Notice" width={500} destroyOnClose center footer={ <Footer cancel={() => setVisible(false)} confirm={() => setVisible(false)} /> } > <span> Notice: before the dialog is opened for the first time, this node and the one below will not be rendered. </span> <div> <strong>Extra content (Not rendered)</strong> </div> </ElDialog> </> );}
Draggable Dialog
Try to drag the header part.
Set draggable to true to drag. Set overflow2.5.4 to true can drag overflow the viewport.
export function DialogDraggableDialog() { const [visible, setVisible] = useState(false); const [overflowVisible, setOverflowVisible] = useState(false); const [customVisible, setCustomVisible] = useState(false); return ( <> <div className={styles.rowGap1}> <ElButton plain onClick={() => setVisible(true)}> Open a draggable Dialog </ElButton> <ElButton plain onClick={() => setOverflowVisible(true)}> Open a overflow draggable Dialog </ElButton> <ElButton plain onClick={() => setCustomVisible(true)}> Open a custom dragging style Dialog </ElButton> </div> <ElDialog visible={visible} onVisibleChange={setVisible} title="Tips" width={500} draggable footer={ <Footer cancel={() => setVisible(false)} confirm={() => setVisible(false)} /> } > <span>It's a draggable Dialog</span> </ElDialog> <ElDialog visible={overflowVisible} onVisibleChange={setOverflowVisible} title="Tips" width={500} draggable overflow footer={ <Footer cancel={() => setOverflowVisible(false)} confirm={() => setOverflowVisible(false)} /> } > <span>It's a overflow draggable Dialog</span> </ElDialog> <ElDialog visible={customVisible} onVisibleChange={setCustomVisible} className="custom-dragging-style" title="Custom Dragging Style" width={500} draggable footer={ <Footer cancel={() => setCustomVisible(false)} confirm={() => setCustomVisible(false)} /> } > <span> This dialog has custom dragging styles. Try dragging it to see the effects! </span> </ElDialog> </> );}
TIP
When using modal = false, please make sure that append-to-body was set to true, because Dialog was positioned by position: relative, when modal gets removed, Dialog will position itself based on the current position in the DOM, instead of Document.Body, thus the style will be messed up.
Fullscreen
Set the fullscreen attribute to open fullscreen dialog.
Animation classes are dynamically generated based on the transition name. For granular control over animation behavior, you may explicitly define these classes. Refer to custom-transition-classes for details.
Events
Open developer console (ctrl + shift + J), to see order of events.