Cuándo un SVG es decorativo
El criterio para decidir si un gráfico aporta información, cómo ocultarlo correctamente, la diferencia entre las cuatro formas de ocultar, y el fallo de anunciar dos veces lo mismo.
La pregunta
Si borraras el SVG y en su lugar no hubiera nada, ¿perdería el usuario información?
Si la respuesta es no, es decorativo. Y la respuesta es no mucho más a menudo de lo que parece:
- Un icono de sobre junto al texto «Enviar mensaje»: decorativo. El texto ya lo dice.
- El mismo icono solo, en un botón sin texto: no decorativo, pero el nombre va en el botón.
- Una ilustración de fondo en una sección: decorativa.
- Un gráfico de barras con datos: no decorativo, y hace falta bastante más que un nombre.
- Una flecha en un enlace «Ver más»: decorativa.
- Un icono de estado en una fila de tabla, sin texto: no decorativo, es el único portador del dato.
- El logotipo en la cabecera, dentro de un enlace a la portada: no decorativo, es el nombre del enlace.
- El mismo logotipo repetido en el pie: decorativo, si ya está anunciado arriba.
El caso del icono de estado merece un comentario porque es el que más se falla. Una tabla donde una columna muestra un tic verde o una cruz roja sin texto: quien usa un lector de pantalla no percibe el color ni la forma. Ese icono tiene que llevar nombre, o mejor, tiene que ir acompañado de texto oculto visualmente.
Cómo ocultarlo
La forma correcta:
<svg aria-hidden="true" viewBox="0 0 24 24" width="20" height="20"> <path d="..." /></svg>aria-hidden="true" elimina el elemento y todo su subárbol del árbol de accesibilidad, sin afectar a la presentación visual. Es exactamente lo que se necesita.
Y ahora las cuatro maneras de ocultar algo, que no son intercambiables:
| Mecanismo | Visible | En el árbol de accesibilidad | Enfocable |
|---|---|---|---|
aria-hidden="true" |
Sí | No | Sí, y eso es un problema |
display: none |
No | No | No |
visibility: hidden |
No | No | No |
| Clase de ocultación visual | No | Sí | Sí |
Dos filas merecen explicación.
La primera fila tiene una trampa: aria-hidden no impide el foco. Si dentro del SVG oculto hay algo enfocable, el usuario del teclado llegará a un elemento que existe para el foco y no existe para el lector de pantalla. Eso es una violación directa de las pautas y produce un foco que «desaparece». En SVG decorativo no suele haber nada enfocable, pero si el SVG está dentro de un enlace o un botón, asegúrate de que el propio SVG no tiene tabindex.
La última fila es la técnica opuesta y también necesaria: el texto oculto visualmente pero presente para el lector de pantalla.
.solo-lector { position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px; overflow: hidden; clip-path: inset(50%); white-space: nowrap; border: 0;}Esa combinación exacta es la que funciona: reduce el elemento a un píxel, lo recorta y evita que el texto largo provoque scroll. Las variantes con display: none o visibility: hidden no sirven, porque también lo ocultan al lector.
Con ella, el icono de estado de una tabla se resuelve así:
<td> <svg aria-hidden="true" width="16" height="16"><use href="#i-check" /></svg> <span class="solo-lector">Completado</span></td>El icono se oculta y el texto lo sustituye. Es más robusto que poner un aria-label en el SVG porque el texto se traduce como contenido y porque no depende del mapeo de accesibilidad de SVG.
Los SVG que se anuncian solos sin que lo sepas
Tres sitios donde aparece contenido accesible sin que nadie lo haya puesto a propósito.
El title de un sprite. Si el símbolo lleva title, cada instancia lo hereda. Un botón con texto y un icono cuyo símbolo tiene title anuncia doble aunque el use no diga nada. Es la razón, otra vez, de no poner title en los símbolos.
El texto dentro de un SVG decorativo. Una ilustración de fondo que incluye un text con una palabra suelta. Sin aria-hidden, ese texto se anuncia sin contexto. Es especialmente frecuente con ilustraciones exportadas de una herramienta de diseño, donde las capas conservan sus nombres como texto.
El SVG dentro de un img con alt vacío. Ese caso está bien: <img src="adorno.svg" alt=""> es decorativo y correcto. El error es olvidar el alt, porque entonces el lector anuncia el nombre del fichero.