Naar de inhoud
Gratis naslagwerk over HTML
HTML leren en naslaan
Naslag / Semantiek en indeling

Het element <dialog>

Het <dialog>-element van HTML vertegenwoordigt een modaal of niet-modaal dialoogvenster of een ander interactief onderdeel, zoals een sluitbare melding, inspecteur of subvenster.

Attributen

Dit element bevat de globale attributen.

Let op

Het tabindex-attribuut mag niet worden gebruikt op het <dialog>-element. Zie Aanvullende opmerkingen.

closedby

Specificeert de typen gebruikersacties die kunnen worden gebruikt om het <dialog>-element te sluiten. Dit attribuut onderscheidt drie manieren waarop een dialoogvenster kan worden gesloten:

  • Een light dismiss-gebruikersactie, waarbij de <dialog> wordt gesloten wanneer de gebruiker erbuiten klikt of tikt. Dit is gelijkwaardig aan het "light dismiss"-gedrag van popovers in de "auto"-status.
  • Een platformspecifieke gebruikersactie, zoals het indrukken van de Esc-toets op desktopplatforms, of een "terug"- of "sluiten"-gebaar op mobiele platforms.
  • Een door de ontwikkelaar opgegeven mechanisme, zoals een <button> met een click-handler die HTMLDialogElement.close() aanroept, of het indienen van een <form>.

Mogelijke waarden zijn:

  • any
    • : Het dialoogvenster kan worden gesloten met elk van de drie methoden.
  • closerequest
    • : Het dialoogvenster kan worden gesloten met een platformspecifieke gebruikersactie of een door de ontwikkelaar opgegeven mechanisme.
  • none
    • : Het dialoogvenster kan alleen worden gesloten met een door de ontwikkelaar opgegeven mechanisme.

Als voor het <dialog>-element geen geldige closedby-waarde is opgegeven, dan

  • gedraagt het zich, als het werd geopend met showModal(), alsof de waarde "closerequest" was
  • gedraagt het zich anders alsof de waarde "none" was.

open

Geeft aan dat het dialoogvenster actief is en beschikbaar is voor interactie. Als het open-attribuut niet is ingesteld, is het dialoogvenster niet zichtbaar voor de gebruiker. Het wordt aanbevolen om de methode .show() of .showModal() te gebruiken om dialoogvensters weer te geven, in plaats van het open-attribuut. Als een <dialog> wordt geopend met het open-attribuut, is deze niet-modaal.

Opmerking

Hoewel u kunt schakelen tussen de open en gesloten status van niet-modale dialoogvensters door de aanwezigheid van het open-attribuut aan of uit te zetten, wordt deze aanpak niet aanbevolen. Zie open voor meer informatie.

Beschrijving

Het HTML-element <dialog> wordt gebruikt om zowel modale als niet-modale dialoogvensters te maken. Modale dialoogvensters blokkeren interactie met andere UI-elementen, waardoor de rest van de pagina inert wordt, terwijl niet-modale dialoogvensters interactie met de rest van de pagina toestaan.

Dialoogvensters besturen met JavaScript

JavaScript kan worden gebruikt om het <dialog>-element weer te geven en te sluiten. U kunt de methode showModal() gebruiken om een modaal dialoogvenster weer te geven, en de methode show() om een niet-modaal dialoogvenster weer te geven. Het dialoogvenster kan worden gesloten met de methode close() of met de dialog-methode bij het indienen van een <form> die genest is binnen het <dialog>-element. Modale dialoogvensters kunnen ook worden gesloten door op de Esc-toets te drukken.

Modale dialoogvensters met invoker commands

Modale dialoogvensters kunnen declaratief worden geopend en gesloten met de HTML-attributen commandfor en command van de Invoker Commands API, die kunnen worden ingesteld op <button>-elementen.

Het command-attribuut stelt het specifieke commando in dat wordt verzonden wanneer op het <button>-element wordt geklikt, terwijl commandfor de id van het doeldialoogvenster instelt. De commando's die voor dialoogvensters kunnen worden verzonden zijn "show-modal", "close", en "request-close".

De onderstaande HTML laat zien hoe u de attributen kunt toepassen op een <button>-element, zodat er op kan worden gedrukt om een modale <dialog> te openen met een id van "my-dialog".

HTML
<button command="show-modal" commandfor="my-dialog">Open dialog</button>

<dialog id="my-dialog">
  <p>This dialog was opened using an invoker command.</p>
  <button commandfor="my-dialog" command="close">Close</button>
</dialog>

Niet-modale dialoogvensters met popover-commando's

Niet-modale dialoogvensters kunnen declaratief worden geopend, gesloten en omgeschakeld met de HTML-attributen popovertarget en popovertargetaction van de Popover API, die kunnen worden gedefinieerd op <button>- en <input>-elementen.

De <dialog> moet worden omgezet in een popover door het popover-attribuut toe te voegen. Vervolgens kunt u popovertarget gebruiken op een knop/invoerveld om de doelpopover aan te geven, en popovertargetaction om de actie te specificeren die op de popover moet plaatsvinden wanneer op de knop wordt geklikt. Merk op dat, omdat het dialoogvenster een popover is, het niet-modaal zal zijn, zodat u het kunt sluiten door buiten het dialoogvenster te klikken.

De onderstaande HTML laat zien hoe u de attributen kunt toepassen op een <button>-element, zodat er op kan worden gedrukt om een modale <dialog> te tonen en te verbergen met een id van "my-dialog".

HTML
<button popovertarget="my-dialog">Open dialog</button>

<dialog id="my-dialog" popover>
  <p>This dialog was opened using a popovertargetaction attribute.</p>
  <button popovertarget="my-dialog" popovertargetaction="hide">Close</button>
</dialog>

De Popover API biedt ook eigenschappen die kunnen worden gebruikt om de status in JavaScript op te vragen en in te stellen.

Dialoogvensters sluiten

Het is belangrijk om voor elk <dialog>-element een sluitmechanisme te bieden, en ervoor te zorgen dat dit werkt op apparaten die mogelijk geen fysiek toetsenbord hebben.

Er zijn talloze manieren om een dialoogvenster te sluiten:

CSS-styling

Een <dialog> kan worden geselecteerd op basis van zijn elementnaam (zoals elk ander element), en u kunt ook de status ervan matchen met pseudoklassen zoals :modal en :open.

Het CSS-pseudo-element ::backdrop kan worden gebruikt om de achtergrond van een modaal dialoogvenster te stylen, die achter het <dialog>-element wordt weergegeven wanneer het dialoogvenster wordt weergegeven met de methode HTMLDialogElement.showModal(). Dit pseudo-element kan bijvoorbeeld worden gebruikt om de inerte inhoud achter het modale dialoogvenster te vervagen, te verdonkeren of anderszins te versluieren.

Aanvullende opmerkingen

  • HTML-<form>-elementen kunnen worden gebruikt om een dialoogvenster te sluiten als ze het attribuut method="dialog" hebben, of als de knop die wordt gebruikt om het formulier in te dienen formmethod="dialog" heeft ingesteld. Wanneer een <form> binnen een <dialog> wordt ingediend via de dialog-methode, wordt het dialoogvenster gesloten, worden de statussen van de formulierbesturingselementen opgeslagen maar niet ingediend, en wordt de eigenschap returnValue ingesteld op de waarde van de knop die is geactiveerd.
  • Het autofocus-attribuut moet worden toegevoegd aan het element waarmee de gebruiker naar verwachting onmiddellijk zal interageren zodra een modaal dialoogvenster wordt geopend. Als geen ander element om meer onmiddellijke interactie vraagt, wordt aanbevolen autofocus toe te voegen aan de sluitknop binnen het dialoogvenster, of aan het dialoogvenster zelf als van de gebruiker wordt verwacht dat deze erop klikt/het activeert om het te sluiten.
  • Voeg de eigenschap tabindex niet toe aan het <dialog>-element, aangezien dit niet interactief is en geen focus ontvangt. De inhoud van het dialoogvenster, inclusief de sluitknop die erin is opgenomen, kan wel focus ontvangen en interactief zijn.

Toegankelijkheid

Bij het implementeren van een dialoogvenster is het belangrijk om na te denken over de meest geschikte plaats om de focus van de gebruiker in te stellen. Bij gebruik van HTMLDialogElement.showModal() om een <dialog> te openen, wordt de focus ingesteld op het eerste geneste focusbare element. Door de initiële focusplaatsing expliciet aan te geven met het autofocus-attribuut, wordt ervoor gezorgd dat de initiële focus wordt ingesteld op het element dat als de beste initiële focusplaatsing voor een bepaald dialoogvenster wordt beschouwd. Bij twijfel, omdat het niet altijd bekend is waar de initiële focus binnen een dialoogvenster kan worden geplaatst, vooral in gevallen waarin de inhoud van een dialoogvenster dynamisch wordt weergegeven wanneer het wordt aangeroepen, biedt het <dialog>-element zelf mogelijk de beste initiële focusplaatsing.

Zorg ervoor dat er een mechanisme aanwezig is waarmee gebruikers het dialoogvenster kunnen sluiten. De meest robuuste manier om ervoor te zorgen dat alle gebruikers het dialoogvenster kunnen sluiten, is door een expliciete knop hiervoor op te nemen, zoals een bevestigings-, annulerings- of sluitknop.

Standaard kan een dialoogvenster dat wordt aangeroepen met de methode showModal() worden gesloten door op de Esc-toets te drukken. Een niet-modaal dialoogvenster wordt standaard niet gesloten via de Esc-toets, en afhankelijk van wat het niet-modale dialoogvenster vertegenwoordigt, is dit gedrag mogelijk niet gewenst. Toetsenbordgebruikers verwachten dat de Esc-toets modale dialoogvensters sluit; zorg ervoor dat dit gedrag is geïmplementeerd en behouden blijft. Als er meerdere modale dialoogvensters open zijn, moet het indrukken van de Esc-toets alleen het laatst getoonde dialoogvenster sluiten. Bij gebruik van <dialog> wordt dit gedrag door de browser geboden.

Hoewel dialoogvensters kunnen worden gemaakt met andere elementen, biedt het native <dialog>-element bruikbaarheids- en toegankelijkheidsfuncties die moeten worden gerepliceerd als u andere elementen voor een vergelijkbaar doel gebruikt. Als u een aangepaste dialoogimplementatie maakt, zorg er dan voor dat alle verwachte standaardgedragingen worden ondersteund en dat de juiste aanbevelingen voor labeling worden gevolgd.

Het <dialog>-element wordt door browsers op een vergelijkbare manier blootgesteld als aangepaste dialoogvensters die het ARIA-attribuut role="dialog" gebruiken. <dialog>-elementen die worden aangeroepen met de methode showModal() hebben impliciet aria-modal="true", terwijl <dialog>-elementen die worden aangeroepen met de methode show() of worden weergegeven met het open-attribuut of door de standaard display van een <dialog> te wijzigen, worden blootgesteld als [aria-modal="false"]. Bij het implementeren van modale dialoogvensters moet alles behalve de <dialog> en de inhoud ervan inert worden gemaakt met het inert-attribuut. Bij gebruik van <dialog> samen met de methode HTMLDialogElement.showModal() wordt dit gedrag door de browser geboden.

Voorbeelden

HTML-attributen van de Invoker Command API

Dit voorbeeld demonstreert hoe u een modaal dialoogvenster kunt openen en sluiten met de HTML-attributen commandfor en command van de Invoker Commands API.

Eerst declareren we een <button>-element, waarbij we het command-attribuut instellen op "show-modal", en het commandfor-attribuut op de id van het te openen dialoogvenster (my-dialog). Vervolgens declareren we een <dialog>-element dat een "Close"-<button> bevat. Deze knop stuurt het "close"-commando naar de (dezelfde) dialog-id.

HTML
<button command="show-modal" commandfor="my-dialog">Open dialog</button>

<dialog id="my-dialog">
  <p>This dialog was opened using an invoker command.</p>
  <button commandfor="my-dialog" command="close">Close</button>
</dialog>

Resultaat

Open het dialoogvenster door op de knop "Open dialog" te drukken. U kunt het dialoogvenster sluiten door de knop "Close" te selecteren of op de Esc-toets te drukken.

Resultaat in de browser

Popover API HTML-attributen

Dit voorbeeld demonstreert hoe u een niet-modaal dialoogvenster kunt openen en sluiten met de HTML-attributen popover, popovertarget en popovertargetaction van de Popover API.

De <dialog> wordt omgezet in een popover door het popover-attribuut toe te voegen. Aangezien we geen waarde voor het attribuut hebben opgegeven, wordt de standaardwaarde "auto" gebruikt. Dit schakelt "light dismiss"-gedrag in, waardoor het dialoogvenster kan worden gesloten door buiten het dialoogvenster te klikken of door op Esc te drukken. We hadden in plaats daarvan popover="manual" kunnen instellen om "light dismiss"-gedrag uit te schakelen, in welk geval het dialoogvenster met de knop "Close" zou moeten worden gesloten.

Merk op dat we het popovertargetaction-attribuut voor de <button> die het dialoogvenster opent, niet hebben opgegeven. Dat is in dit geval niet nodig, omdat de standaardwaarde toggle is, waardoor het dialoogvenster tussen de open en gesloten status wordt omgeschakeld wanneer op de knop wordt geklikt.

HTML
<button popovertarget="my-dialog">Open dialog</button>

<dialog id="my-dialog" popover>
  <p>This dialog was opened using a popovertargetaction attribute.</p>
  <button popovertarget="my-dialog" popovertargetaction="hide">Close</button>
</dialog>

Resultaat

Open het dialoogvenster door op de knop "Open dialog" te drukken. U kunt het dialoogvenster sluiten door de knop "Close" te selecteren of op de Esc-toets te drukken. U kunt het ook sluiten door buiten het dialoogvenster te selecteren, aangezien het niet-modaal is.

Resultaat in de browser

Het open-attribuut van dialog gebruiken

Dit voorbeeld demonstreert hoe u het booleaanse open-attribuut op een <dialog>-element kunt instellen, om een alleen-HTML niet-modaal dialoogvenster te maken dat al open is wanneer de pagina wordt geladen.

Het dialoogvenster kan worden gesloten door op de knop "OK" te klikken, omdat het method-attribuut in het <form>-element is ingesteld op "dialog". In dit geval is er geen JavaScript nodig om het formulier te sluiten.

HTML
<dialog open>
  <p>Greetings, one and all!</p>
  <form method="dialog">
    <button>OK</button>
  </form>
</dialog>

Resultaat

Dit dialoogvenster is aanvankelijk open en niet-modaal vanwege de aanwezigheid van het open-attribuut. Na het klikken op "OK" wordt het dialoogvenster gesloten, waardoor het resultaatvenster leeg blijft.

Resultaat in de browser
Opmerking

Laad de pagina opnieuw om de uitvoer te resetten.

Wanneer het dialoogvenster wordt gesloten, is er geen methode beschikbaar om het opnieuw te openen. De voorkeursmethode om niet-modale dialoogvensters weer te geven is het gebruik van de methode HTMLDialogElement.show(). Het is mogelijk om de weergave van het dialoogvenster te schakelen door het booleaanse open-attribuut toe te voegen of te verwijderen, maar dit is niet de aanbevolen werkwijze.

Een modaal dialoogvenster maken

Dit voorbeeld demonstreert een modaal dialoogvenster met een gradient-achtergrond. De methode .showModal() opent het modale dialoogvenster wanneer de knop "Show the dialog" wordt geactiveerd. Het dialoogvenster kan worden gesloten door op de Esc-toets te drukken of via de methode close() wanneer de knop "Close" binnen het dialoogvenster wordt geactiveerd.

Wanneer een dialoogvenster wordt geopend, geeft de browser standaard focus aan het eerste element dat focus kan krijgen binnen het dialoogvenster. In dit voorbeeld wordt het autofocus-attribuut toegepast op de knop "Close", waardoor deze focus krijgt wanneer het dialoogvenster wordt geopend, aangezien dit het element is waarmee we verwachten dat de gebruiker onmiddellijk na het openen van het dialoogvenster zal interageren.

HTML

HTML
<dialog>
  <button autofocus>Close</button>
  <p>This modal dialog has a groovy backdrop!</p>
</dialog>
<button>Show the dialog</button>

CSS

We kunnen de achtergrond van het dialoogvenster stylen met behulp van het pseudo-element ::backdrop.

CSS
::backdrop {
  background-image: linear-gradient(
    45deg,
    magenta,
    rebeccapurple,
    dodgerblue,
    green
  );
  opacity: 0.75;
}

JavaScript

Het dialoogvenster wordt modaal geopend met de methode .showModal() en gesloten met de methoden .close() of .requestClose().

JS
const dialog = document.querySelector("dialog");
const showButton = document.querySelector("dialog + button");
const closeButton = document.querySelector("dialog button");

// "Show the dialog" button opens the dialog modally
showButton.addEventListener("click", () => {
  dialog.showModal();
});

// "Close" button closes the dialog
closeButton.addEventListener("click", () => {
  dialog.close();
});

Resultaat

Resultaat in de browser

Wanneer het modale dialoogvenster wordt weergegeven, verschijnt het boven alle andere dialoogvensters die mogelijk aanwezig zijn. Alles buiten het modale dialoogvenster is inert en interacties buiten het dialoogvenster worden geblokkeerd. Merk op dat wanneer het dialoogvenster open is, met uitzondering van het dialoogvenster zelf, interactie met het document niet mogelijk is; de knop "Show the dialog" wordt grotendeels versluierd door de bijna ondoorzichtige achtergrond van het dialoogvenster en is inert.

De retourwaarde van het dialoogvenster verwerken

Dit voorbeeld demonstreert de returnValue van het <dialog>-element en hoe u een modaal dialoogvenster kunt sluiten met behulp van een formulier. Standaard is de returnValue de lege string, of de waarde van de knop waarmee het formulier binnen het <dialog>-element wordt ingediend, indien aanwezig.

Dit voorbeeld opent een modaal dialoogvenster wanneer de knop "Show the dialog" wordt geactiveerd. Het dialoogvenster bevat een formulier met een <select> en twee <button>-elementen, die standaard type="submit" zijn. Een event listener werkt de waarde van de knop "Confirm" bij wanneer de selectieoptie wijzigt. Als de knop "Confirm" wordt geactiveerd om het dialoogvenster te sluiten, is de huidige waarde van de knop de retourwaarde. Als het dialoogvenster wordt gesloten door op de knop "Cancel" te drukken, is de returnValue gelijk aan cancel.

Wanneer het dialoogvenster wordt gesloten, wordt de retourwaarde weergegeven onder de knop "Show the dialog". Als het dialoogvenster wordt gesloten door op de Esc-toets te drukken, wordt de returnValue niet bijgewerkt en vindt het close-event niet plaats, dus de tekst in de <output> wordt niet bijgewerkt.

HTML

HTML
<!-- A modal dialog containing a form -->
<dialog id="favDialog">
  <form>
    <p>
      <label>
        Favorite animal:
        <select>
          <option value="default">Choose…</option>
          <option>Brine shrimp</option>
          <option>Red panda</option>
          <option>Spider monkey</option>
        </select>
      </label>
    </p>
    <div>
      <button value="cancel" formmethod="dialog">Cancel</button>
      <button id="confirmBtn" value="default">Confirm</button>
    </div>
  </form>
</dialog>
<p>
  <button id="showDialog">Show the dialog</button>
</p>
<output></output>

JavaScript

Het dialoogvenster wordt geopend met een event listener op de knop "Show the dialog", die HTMLDialogElement.showModal() aanroept wanneer op de knop wordt geklikt.

Het dialoogvenster wordt gesloten wanneer op de knop "Cancel" wordt geklikt, omdat de <button> het attribuut formmethod="dialog" bevat. Wanneer de methode van een formulier dialog is, wordt de status van het formulier opgeslagen maar niet ingediend, en wordt het dialoogvenster gesloten (het attribuut overschrijft de standaard GET-methode van de <form>). Zonder een action zorgt het indienen van het formulier via de standaard GET-methode ervoor dat een pagina opnieuw wordt geladen. We gebruiken JavaScript om het indienen te voorkomen en het dialoogvenster te sluiten met respectievelijk de methoden event.preventDefault() en HTMLDialogElement.close().

JS
const showButton = document.getElementById("showDialog");
const favDialog = document.getElementById("favDialog");
const outputBox = document.querySelector("output");
const selectEl = favDialog.querySelector("select");
const confirmBtn = favDialog.querySelector("#confirmBtn");

// "Show the dialog" button opens the <dialog> modally
showButton.addEventListener("click", () => {
  favDialog.showModal();
});

// "Cancel" button closes the dialog without submitting because of [formmethod="dialog"], triggering a close event.
favDialog.addEventListener("close", (e) => {
  outputBox.value =
    favDialog.returnValue === "default"
      ? "No return value."
      : `ReturnValue: ${favDialog.returnValue}.`; // Have to check for "default" rather than empty string
});

// Prevent the "confirm" button from the default behavior of submitting the form, and close the dialog with the `close()` method, which triggers the "close" event.
confirmBtn.addEventListener("click", (event) => {
  event.preventDefault(); // We don't want to submit this fake form
  favDialog.close(selectEl.value); // Have to send the select box value here.
});

Resultaat

Resultaat in de browser

Een dialoogvenster sluiten met een verplicht formulierveld

Wanneer een formulier binnen een dialoogvenster een verplicht invoerveld heeft, laat de user agent u het dialoogvenster pas sluiten nadat u een waarde voor het verplichte veld heeft opgegeven. Om zo'n dialoogvenster te sluiten, gebruikt u ofwel het attribuut formnovalidate op de sluitknop, of roept u de methode close() aan op het dialoogobject wanneer op de sluitknop wordt geklikt.

HTML
<dialog id="dialog">
  <form method="dialog">
    <p>
      <label>
        Favorite animal:
        <input type="text" required />
      </label>
    </p>
    <div>
      <input type="submit" id="normal-close" value="Normal close" />
      <input
        type="submit"
        id="novalidate-close"
        value="Novalidate close"
        formnovalidate />
      <input type="submit" id="js-close" value="JS close" />
    </div>
  </form>
</dialog>
<p>
  <button id="show-dialog">Show the dialog</button>
</p>
<output></output>
CSS
[type="submit"] {
  margin-right: 1rem;
}

JavaScript

JS
const showBtn = document.getElementById("show-dialog");
const dialog = document.getElementById("dialog");
const jsCloseBtn = dialog.querySelector("#js-close");

showBtn.addEventListener("click", () => {
  dialog.showModal();
});

jsCloseBtn.addEventListener("click", (e) => {
  e.preventDefault();
  dialog.close();
});

Resultaat

Resultaat in de browser

Uit de uitvoer blijkt dat het onmogelijk is om het dialoogvenster te sluiten met de knop Normal close. Maar het dialoogvenster kan wel worden gesloten als we de formuliervalidatie omzeilen met behulp van het formnovalidate-attribuut op de knop Cancel. Programmatisch zal dialog.close() zo'n dialoogvenster ook sluiten.

Vergelijking van verschillende closedby-gedragingen

Dit voorbeeld demonstreert het verschil in gedrag tussen verschillende waarden van het closedby-attribuut.

HTML

We bieden drie <button>-elementen en drie <dialog>-elementen. Elke knop wordt geprogrammeerd om een ander dialoogvenster te openen dat het gedrag demonstreert van een van de drie waarden van het closedby-attribuut — none, closerequest en any. Merk op dat elk <dialog>-element een <button>-element bevat dat wordt gebruikt om het te sluiten.

HTML
<p>Choose a <code>&lt;dialog&gt;</code> type to show:</p>
<div id="controls">
  <button id="none-btn"><code>closedby="none"</code></button>
  <button id="closerequest-btn">
    <code>closedby="closerequest"</code>
  </button>
  <button id="any-btn"><code>closedby="any"</code></button>
</div>

<dialog closedby="none">
  <h2><code>closedby="none"</code></h2>
  <p>
    Only closable using a specific provided mechanism, which in this case is
    pressing the "Close" button below.
  </p>
  <button class="close">Close</button>
</dialog>

<dialog closedby="closerequest">
  <h2><code>closedby="closerequest"</code></h2>
  <p>Closable using the "Close" button or the Esc key.</p>
  <button class="close">Close</button>
</dialog>

<dialog closedby="any">
  <h2><code>closedby="any"</code></h2>
  <p>
    Closable using the "Close" button, the Esc key, or by clicking outside the
    dialog. "Light dismiss" behavior.
  </p>
  <button class="close">Close</button>
</dialog>
CSS
body {
  font-family: sans-serif;
}

#controls {
  display: flex;
  justify-content: space-around;
}

dialog {
  width: 480px;
  border-radius: 5px;
  border-color: rgb(0 0 0 / 0.3);
}

dialog h2 {
  margin: 0;
}

dialog p {
  line-height: 1.4;
}

JavaScript

Hier wijzen we verschillende variabelen toe om te verwijzen naar de belangrijkste <button>-besturingselementen, de <dialog>-elementen en de "Close"-<button>-elementen binnen de dialoogvensters. Eerst wijzen we een click-event listener toe aan elke besturingsknop met behulp van addEventListener, waarvan de event-handlerfunctie het bijbehorende <dialog>-element opent via showModal(). Vervolgens doorlopen we de referenties naar de "Close"-<button>-elementen, waarbij we elk een click-event-handlerfunctie toewijzen die het bijbehorende <dialog>-element sluit via close().

JS
const noneBtn = document.getElementById("none-btn");
const closerequestBtn = document.getElementById("closerequest-btn");
const anyBtn = document.getElementById("any-btn");

const noneDialog = document.querySelector("[closedby='none']");
const closerequestDialog = document.querySelector("[closedby='closerequest']");
const anyDialog = document.querySelector("[closedby='any']");

const closeBtns = document.querySelectorAll(".close");

noneBtn.addEventListener("click", () => {
  noneDialog.showModal();
});

closerequestBtn.addEventListener("click", () => {
  closerequestDialog.showModal();
});

anyBtn.addEventListener("click", () => {
  anyDialog.showModal();
});

closeBtns.forEach((btn) => {
  btn.addEventListener("click", () => {
    btn.parentElement.close();
  });
});

Resultaat

Het weergegeven resultaat is als volgt:

Resultaat in de browser

Probeer op elke knop te klikken om een dialoogvenster te openen. Het eerste kan alleen worden gesloten door op de knop "Close" te klikken. Het tweede kan ook worden gesloten via een apparaatspecifieke gebruikersactie, zoals het indrukken van de Esc-toets. Het derde heeft volledig "light-dismiss"-gedrag, zodat het ook kan worden gesloten door buiten het dialoogvenster te klikken of te tikken.

Dialoogvensters animeren

<dialog>-elementen worden ingesteld op display: none; wanneer ze verborgen zijn en display: block; wanneer ze worden getoond, en worden ook verwijderd uit / toegevoegd aan de top layer en de accessibility tree. Daarom moet, om <dialog>-elementen te kunnen animeren, de display-eigenschap animeerbaar zijn. Browsers die dit ondersteunen animeren display met een variant van het discrete animatietype. Om precies te zijn: de browser schakelt tussen none en een andere waarde van display, zodat de geanimeerde inhoud gedurende de hele animatieduur zichtbaar is.

Bijvoorbeeld:

  • Bij het animeren van display van none naar block (of een andere zichtbare display-waarde), schakelt de waarde bij 0% van de animatieduur om naar block, zodat deze gedurende de hele animatie zichtbaar is.
  • Bij het animeren van display van block (of een andere zichtbare display-waarde) naar none, schakelt de waarde bij 100% van de animatieduur om naar none, zodat deze gedurende de hele animatie zichtbaar is.
Opmerking

Bij het animeren met CSS-transitions moet transition-behavior: allow-discrete worden ingesteld om het bovenstaande gedrag mogelijk te maken. Dit gedrag is standaard beschikbaar bij het animeren met CSS-animaties; een equivalente stap is dan niet nodig.

Overgangen voor dialog-elementen

Bij het animeren van <dialog>-elementen met CSS-transitions zijn de volgende functies vereist:

@starting-style-at-ruleBiedt een set startwaarden voor eigenschappen die zijn ingesteld op de <dialog>, waarnaar u elke keer dat deze wordt geopend een overgang wilt maken. Dit is nodig om onverwacht gedrag te voorkomen. Standaard vinden CSS-transitions alleen plaats wanneer een eigenschap verandert van de ene waarde naar de andere op een zichtbaar element; ze worden niet geactiveerd bij de eerste stijlupdate van elementen, of wanneer het display-type verandert van none naar een ander type.
display-eigenschapVoeg display toe aan de lijst met transitions, zodat de <dialog> gedurende de transitieduur display: block blijft (of een andere zichtbare display-waarde die is ingesteld voor de open status van het dialoogvenster), zodat de overige transities zichtbaar blijven.
overlay-eigenschapNeem overlay op in de lijst met transitions om ervoor te zorgen dat het verwijderen van de <dialog> uit de top layer wordt uitgesteld totdat de transitie is voltooid, zodat de transitie opnieuw zichtbaar blijft.
transition-behavior-eigenschapStel transition-behavior: allow-discrete in voor de display- en overlay-transities (of voor de transition-shorthand) om discrete transities voor deze twee eigenschappen, die standaard niet animeerbaar zijn, mogelijk te maken.

Hier is een kort voorbeeld om te laten zien hoe dit eruit kan zien.

HTML

De HTML bevat een <dialog>-element, plus een knop om het dialoogvenster te tonen. Bovendien bevat het <dialog>-element nog een knop om zichzelf te sluiten.

HTML
<dialog id="dialog">
  Content here
  <button class="close">close</button>
</dialog>

<button class="show">Show Modal</button>
CSS

In de CSS nemen we een @starting-style-blok op dat de startstijlen voor de transitie definieert voor de eigenschappen opacity en transform, de eindstijlen van de transitie in de status dialog:open, en de standaardstijlen in de standaard dialog-status waarnaar wordt teruggekeerd zodra de <dialog> is verschenen. Merk op dat de transition-lijst van de <dialog> niet alleen deze eigenschappen bevat, maar ook de eigenschappen display en overlay, elk met allow-discrete ingesteld.

We stellen ook een startstijlwaarde in voor de eigenschap background-color op de ::backdrop die achter de <dialog> verschijnt wanneer deze wordt geopend, om een mooie verdonkeringsanimatie te bieden. De selector dialog:open::backdrop selecteert alleen de achtergronden van <dialog>-elementen wanneer het dialoogvenster open is.

CSS
/* Open state of the dialog  */
dialog:open {
  opacity: 1;
  transform: scaleY(1);
}

/* Closed state of the dialog   */
dialog {
  opacity: 0;
  transform: scaleY(0);
  transition:
    opacity 0.7s ease-out,
    transform 0.7s ease-out,
    overlay 0.7s ease-out allow-discrete,
    display 0.7s ease-out allow-discrete;
  /* Equivalent to
  transition: all 0.7s allow-discrete; */
}

/* Before open state  */
/* Needs to be after the previous dialog:open rule to take effect,
    as the specificity is the same */
@starting-style {
  dialog:open {
    opacity: 0;
    transform: scaleY(0);
  }
}

/* Transition the :backdrop when the dialog modal is promoted to the top layer */
dialog::backdrop {
  background-color: transparent;
  transition:
    display 0.7s allow-discrete,
    overlay 0.7s allow-discrete,
    background-color 0.7s;
  /* Equivalent to
  transition: all 0.7s allow-discrete; */
}

dialog:open::backdrop {
  background-color: rgb(0 0 0 / 25%);
}

/* This starting-style rule cannot be nested inside the above selector
because the nesting selector cannot represent pseudo-elements. */

@starting-style {
  dialog:open::backdrop {
    background-color: transparent;
  }
}
Opmerking

In browsers die de pseudoklasse :open niet ondersteunen, kunt u de attribuutselector dialog[open] gebruiken om het <dialog>-element te stylen wanneer het zich in de open status bevindt.

JavaScript

De JavaScript voegt event handlers toe aan de knoppen voor tonen en sluiten, zodat deze de <dialog> tonen en sluiten wanneer erop wordt geklikt:

JS
const dialogElem = document.getElementById("dialog");
const showBtn = document.querySelector(".show");
const closeBtn = document.querySelector(".close");

showBtn.addEventListener("click", () => {
  dialogElem.showModal();
});

closeBtn.addEventListener("click", () => {
  dialogElem.close();
});
Resultaat

De code wordt als volgt weergegeven:

Resultaat in de browser
Opmerking

Omdat <dialog>-elementen elke keer dat ze worden getoond veranderen van display: none naar display: block, maakt de <dialog> elke keer dat de entree-transitie plaatsvindt een overgang van de @starting-style-stijlen naar de dialog:open-stijlen. Wanneer de <dialog> wordt gesloten, maakt deze een overgang van de dialog:open-status naar de standaard dialog-status.

Het is mogelijk dat de stijltransitie bij binnenkomst en vertrek in dergelijke gevallen verschillend is. Zie ons voorbeeld Demonstratie van wanneer starting styles worden gebruikt voor een bewijs hiervan.

Keyframe-animaties voor dialog

Bij het animeren van een <dialog> met CSS-keyframe-animaties zijn er enkele verschillen ten opzichte van transities om op te merken:

  • U geeft geen @starting-style op.
  • U neemt de display-waarde op in een keyframe; dit wordt de display-waarde voor de hele duur van de animatie, of totdat er een andere display-waarde dan none wordt tegengekomen.
  • U hoeft discrete animaties niet expliciet in te schakelen; er is geen equivalent van allow-discrete binnen keyframes.
  • U hoeft overlay ook niet in te stellen binnen keyframes; de display-animatie behandelt de animatie van de <dialog> van getoond naar verborgen.

Laten we een voorbeeld bekijken, zodat u kunt zien hoe dit eruitziet.

HTML

Eerst bevat de HTML een <dialog>-element, plus een knop om het dialoogvenster te tonen. Bovendien bevat het <dialog>-element nog een knop om zichzelf te sluiten.

HTML
<dialog id="dialog">
  Content here
  <button class="close">close</button>
</dialog>

<button class="show">Show Modal</button>
CSS

De CSS definieert keyframes om te animeren tussen de gesloten en geopende status van de <dialog>, plus de fade-in-animatie voor de achtergrond van de <dialog>. De <dialog>-animaties bevatten het animeren van display, om ervoor te zorgen dat de daadwerkelijk zichtbare animatie-effecten gedurende de hele duur zichtbaar blijven. Merk op dat het niet mogelijk was om de fade-out van de achtergrond te animeren — de achtergrond wordt onmiddellijk uit de DOM verwijderd wanneer de <dialog> wordt gesloten, dus er is niets om te animeren.

CSS
dialog {
  animation: fade-out 0.7s ease-out;
}

dialog:open {
  animation: fade-in 0.7s ease-out;
}

dialog:open::backdrop {
  background-color: black;
  animation: backdrop-fade-in 0.7s ease-out forwards;
}

/* Animation keyframes */

@keyframes fade-in {
  0% {
    opacity: 0;
    transform: scaleY(0);
    display: none;
  }

  100% {
    opacity: 1;
    transform: scaleY(1);
    display: block;
  }
}

@keyframes fade-out {
  0% {
    opacity: 1;
    transform: scaleY(1);
    display: block;
  }

  100% {
    opacity: 0;
    transform: scaleY(0);
    display: none;
  }
}

@keyframes backdrop-fade-in {
  0% {
    opacity: 0;
  }

  100% {
    opacity: 0.25;
  }
}

body,
button {
  font-family: system-ui;
}
JavaScript

Ten slotte voegt de JavaScript event handlers toe aan de knoppen om het tonen en sluiten van de <dialog> mogelijk te maken:

JS
const dialogElem = document.getElementById("dialog");
const showBtn = document.querySelector(".show");
const closeBtn = document.querySelector(".close");

showBtn.addEventListener("click", () => {
  dialogElem.showModal();
});

closeBtn.addEventListener("click", () => {
  dialogElem.close();
});
Resultaat

De code wordt als volgt weergegeven:

Resultaat in de browser

Technische samenvatting

Contentcategorieën Flow content, sectioning root
Toegestane content Flow content
Weglaten van tag Geen, zowel de begin- als de eindtag zijn verplicht.
Toegestane ouders Elk element dat flow content accepteert
Impliciete ARIA-rol dialog
Toegestane ARIA-rollen alertdialog
DOM-interface HTMLDialogElement

Verwante elementen