demo · v139

Nested Dialogs

Three dialogs, each with a commandfor="id" command="request-close" button. The inner "Confirm delete" dialog intercepts its cancel event to show a guard — demonstrating that request-close fires cancel just like the Escape key, giving dialogs a unified close-prevention hook.

Checking invoker command support…

Spec surface lab

This panel uses the same primitives the command button relies on: the reflected button.command and button.commandForElement fields, the CommandEvent interface, and the imperative dialog.requestClose() path.

Run a probe to inspect the reflected command state.
Info

This dialog closes via a commandfor + command="request-close" button. Check the event log below — a cancel event fires, then the dialog closes.

Edit profile

Press Escape or click ✕ — both fire cancel. This dialog doesn't prevent it, but you can see both paths in the log.

Delete item

Closing this dialog (Escape or ✕) is intercepted. The cancel handler calls event.preventDefault() and opens a guard dialog asking you to confirm the discard.

Discard changes?

You tried to close without confirming. Are you sure you want to discard?

requestClose() probe

This dialog is opened by JavaScript, then closed with HTMLDialogElement.requestClose(). Toggle the checkbox in the spec surface lab to prevent the next cancel event and keep this dialog open.

Event log
Events will appear here as dialogs open and close.
<!-- request-close fires the 'cancel' event before closing -->
<button commandfor="myDialog" command="request-close">✕</button>

<dialog id="myDialog">…</dialog>

<script>
  // Both ESC and request-close trigger 'cancel'
  myDialog.addEventListener('cancel', (e) => {
    if (hasUnsavedChanges) {
      e.preventDefault(); // stop the close
      showGuardDialog();  // ask the user
    }
  });
</script>

see also