Saltar enlaces

API emergente o API de diálogo: ¿cuál elegir?

Elegir entre Popover API y Dialog API es difícil porque parecen realizar el mismo trabajo, ¡pero en realidad no es así!

atrás un poco Después de mucha investigación, descubrí que la API Popover y la API Dialog son muy diferentes en términos de accesibilidad. Entonces, si estás tratando de decidir si usar la API Popover o la API Dialog, te recomiendo que:

  • La mayoría de las ventanas emergentes utilizan la API Popover.
  • Utilice la API de Dialog solo para cuadros de diálogo modales.

Ventanas emergentes y conversaciones

La relación entre Popovers y Dialogs confunde a la mayoría de los desarrolladores, pero en realidad es muy simple.

Los cuadros de diálogo son sólo un subconjunto de ventanas emergentes. Los cuadros de diálogo modales son un subconjunto de cuadros de diálogo. lee este artículo Si desea comprender el fundamento de esta relación.

!((popover-roles-accesibles.jpg.webp))

Por eso puedes incluso <dialog> elemento.

<!-- Using popover on a dialog element --> 
<dialog popover>...</div> 

Estilísticamente, la diferencia entre ventanas emergentes y modales es aún más obvia:

  • El modal debe mostrar el fondo.
  • Las ventanas emergentes no deberían aparecer.

Por lo tanto, nunca debes aplicar estilo a un cuadro emergente. ::backdrop elemento. Hacer esto simplemente indica que la ventana emergente es un cuadro de diálogo: crea muchas preguntas.

Sólo debes diseñar modal ::backdrop elemento.

API Popover y su accesibilidad

Es relativamente fácil crear ventanas emergentes utilizando la API de Popover. Especificas tres cosas:

  • uno popovertarget Propiedades en el disparador de la ventana emergente,
  • uno id en la ventana emergente, y
  • uno popover Propiedades en la ventana emergente.

este popovertarget debe coincidir id.

<button popovertarget="the-popover"> ... </button>
<dialog popover id="the-popover"> The Popover Content </dialog>

Tenga en cuenta que estoy usando <dialog> elemento para crear un dialog Role. Esto es opcional, pero recomendado. hago esto porque dialog es un Grandes personajes preestablecidos Porque la mayoría de las ventanas emergentes son sólo cuadros de diálogo.

Estas dos líneas de código ya tienen muchas funciones auxiliares integradas para usted:

  • Gestión de enfoque automático
    • El foco va a la ventana emergente cuando se abre.
    • Cuando se cierra, el foco vuelve al gatillo.
  • Conexión automática de aria
    • No es necesario escribir aria-expanded, aria-popup y aria-controls. El navegador los maneja de forma nativa. ¡Guau!
  • Apagado automático de luz
    • La ventana emergente se cierra cuando el usuario hace clic afuera.
    • La ventana emergente se cierra cuando hacen clic. ESC llave.

Ahora, sin un estilo adicional, la ventana emergente parece un poco aburrida. El estilo es un problema completamente diferente, por lo que lo abordaremos en un artículo futuro. Jeff tiene algunas notas. Puedes verlos simultáneamente.

API de diálogo y su accesibilidad

A diferencia de la API Popover, la API Dialog no tiene muchas funciones integradas de forma predeterminada:

  • Sin gestión de enfoque automático
  • Sin conexión ARIA automática
  • Ninguna luz se apaga automáticamente

Entonces, tenemos que construirlos nosotros mismos usando JavaScript. es por eso La API Popover es superior a la API Dialog en casi todos los sentidos, excepto en uno.: Cuando intervienen verbos modales.

La API de diálogo tiene una showModal método. cuando showModal Cuando se utiliza, la API de diálogo establece un esquema. él:

  1. automáticamente inertotros elementos,
  2. Evitar que los usuarios accedan a otros elementos, y
  3. Evita que los lectores de pantalla lleguen a otros elementos.

Lo hace con tanta eficacia, Ya no necesitamos limitar el enfoque al modal.

Sin embargo, cuando usamos la API de diálogo, tenemos que lidiar con el foco y el contenido ARIA, así que manejemos el código mínimo requerido para un cuadro de diálogo que funcione correctamente.

Comenzaremos construyendo el andamio HTML:

<button 
  class="modal-invoker" 
  data-target="the-modal" 
  aria-haspopup="dialog"
>...</button>

<dialog id="the-modal">The Popover Content</dialog>

Tenga en cuenta que no agregué ninguno aria-expanded en HTML. Hago esto por varias razones:

  1. Esto reduce la complejidad de HTML.
  2. podemos escribir aria-expanded, aria-controlsasí como contenido centrado directamente en JavaScript, porque no funcionará sin JavaScript.
  3. Hacer esto hace que el HTML sea muy reutilizable.

configuración

Voy a escribir un artículo aquí sobre la implementación simple de JavaScript. Si estás utilizando un marco como React o Svelte, tendrás que hacer algunos cambios, pero espero que sea sencillo para ti.

Lo primero que debe hacer es recorrer todos dialog-invokery establecer aria-expanded llegar false. Esto establecerá el estado inicial.

También estableceremos aria-controls llegar <dialog> elemento. aun asi lo haremos aria-controls es cacaporque hasta donde yo sé no hay mejor manera de conectar estos elementos (y no hay nada de malo en conectarlos).

const modalInvokers = Array.from(document.querySelectorAll('.modal-invoker'))

modalInvokers.forEach(invoker => {
  const dialogId = invoker.dataset.target
  const dialog = document.querySelector(`#${dialogId}`)
  invoker.setAttribute('aria-expanded', false)
  invoker.setAttribute('aria-controls', dialogId)
})

En modo

Cuando se hace clic en la persona que llama/disparador tenemos que:

  1. Cambiar aria-expanded de false llegar true llegar show Patrones de usuarios de tecnología de asistencia, y
  2. usar showModal La función activa el modal.

No tenemos que escribir ningún código para ocultar este modo. click controlador, porque el usuario nunca podrá hacer clic en la persona que llama cuando se abre el cuadro de diálogo.

modalInvokers.forEach(invoker => {
  // ... 

  // Opens the modal
  invoker.addEventListener('click', event => {
    invoker.setAttribute('aria-expanded', true)
    dialog.showModal()
  })
})

Excelente. El modo está activado. Ahora tenemos que escribir código para desactivar el modal.

Modo apagado

Por defecto, showModal No hay una función de apagado automático de la luz, por lo que los usuarios no pueden hacer clic en la superposición ni hacer clic en ESC llave. Esto significa que tenemos que agregar otro botón que desactive el modal. Esto debe colocarse dentro del contenido modal.

<dialog id="the-modal"> 
  <button class="modal-closer">X</button>
  <!-- Other modal content -->
</dialog>

Cuando el usuario hace clic en el botón cerrar, debemos:

  1. poner aria-expanded en llamada abierta false,
  2. Modo apagado close métodos, y
  3. Devuelve el foco al elemento de llamada abierto.
modalInvokers.forEach(invoker => {
  // ... 

  // Opens the modal
  invoker.addEventListener('click', event => {
    invoker.setAttribute('aria-expanded', true)
    dialog.showModal()
  })
})

const modalClosers = Array.from(document.querySelectorAll('.modal-closer'))

modalClosers.forEach(closer => {
  const dialog = closer.closest('dialog')
  const dialogId = dialog.id
  const invoker = document.querySelector(`(data-target="${dialogId}")`)
  
  closer.addEventListener('click', event => {
    dialog.close()
    invoker.setAttribute('aria-expanded', false)
    invoker.focus()
  })
})

Uf, eso es todo, hemos terminado. básico implementar.

Por supuesto, hay algunos trabajos avanzados como la eliminación de la luz y el peinado… que podremos abordar en un próximo artículo.

¿Puedes usar la API de Popover para crear modales?

Sí puedes.

Pero tienes que encargarte de esto tú mismo:

  1. Otros elementos inertes.
  2. capturar el enfoque

Creo que lo que hicimos antes (establecer aria-expanded, aria-controlsy focus) es más fácil que inertizar elementos y capturar el foco.

La API de diálogo puede ser más fácil de usar en el futuro

un artículo sobre comando de llamada ya Creado para que la API de diálogo pueda contener popovertarget Al igual que la API Popover.

Este es un trabajo en progreso, por lo que es posible que podamos simplificar aún más los modales usando la API de diálogo en el futuro. Al mismo tiempo, tenemos que hacer el trabajo necesario para parchear los aspectos de accesibilidad.

Sumérgete en la creación de ventanas emergentes y modales viables

Acabamos de comenzar a usar el código anterior para crear ventanas emergentes funcionales y superficies modales: son versiones básicas a las que se puede acceder, pero definitivamente no se ven bien y aún no están listas para fines profesionales.

Para facilitar el proceso de creación de ventanas emergentes y modales, profundizaremos en los detalles de implementación de ventanas emergentes y modales profesionales en artículos futuros.

Mientras tanto, espero que esto le brinde algunas ideas sobre cuándo elegir la API Popover versus la API Dialog.

Recuerda, no es necesario utilizar ambos al mismo tiempo. Uno servirá.

Home
Account
Cart
Search
¡Hola! ¡Pregúntame lo que quieras!
Explore
Drag