Informe de conformidad

Auditoría WCAG 2.2 nivel AA

Café Almendra (demo)
2026-08-13
Método: código

Target: mini sitio de una página (a11ykit-demo/index.html), maquetado con HTML y CSS propios, creado como caso de ejemplo del skill A11yKit.

Alcance: cubre únicamente este archivo. No es una auditoría del resto del sitio TOKITO.

Nivel A✕ No cumple53%
Nivel AA✕ No cumple44%
14✅ Cumple
15❌ No cumple
23N/A No aplica
3⚠️ No verificable
01

Perceivable

NivelCriterioEstadoMotivoSolución
A 1.1.1Non-text ContentAlternativa textual para toda imagen/icono con significado. ❌ No cumple Las 3 imágenes de .gallery-grid no tienen atributo alt. Los enlaces sociales del footer envuelven un SVG en <a aria-hidden="true"> sin nombre accesible. Añadir alt descriptivo a cada foto. Quitar aria-hidden del <a> y añadir aria-label="Facebook" / "Instagram".
A 1.2.1Audio/Video-only N/A No aplica No hay contenido de solo audio o solo vídeo.
A 1.2.2Captions (Prerecorded) N/A No aplica No hay vídeo.
A 1.2.3Audio Description N/A No aplica No hay vídeo.
AA 1.2.4Captions (Live) N/A No aplica No hay contenido en directo.
AA 1.2.5Audio Description (Prerecorded) N/A No aplica No hay vídeo.
A 1.3.1Info and RelationshipsEstructura semántica: headings, labels, listas, tablas. ❌ No cumple Los <h3> de sección ("La carta", "El local", "Reserva tu mesa") saltan de h1 a h3, sin h2 intermedio. Los 3 inputs del formulario no tienen <label>, solo placeholder. Las <section> no tienen aria-label, por lo que no se exponen como landmarks. Cambiar los h3 de sección a h2. Añadir <label for="..."> a cada input. Añadir aria-label a las secciones o envolver el contenido en <main>.
A 1.3.2Meaningful Sequence ✅ Cumple
A 1.3.3Sensory CharacteristicsNo depender solo de forma/posición/color para dar instrucciones. ❌ No cumple El texto "Los campos en rojo son obligatorios" identifica los campos obligatorios únicamente por su color, en la propia instrucción. Añadir un indicador no cromático junto al texto, ej. "(obligatorio)" o asterisco explicado.
AA 1.3.4Orientation ✅ Cumple
AA 1.3.5Identify Input PurposeCampos comunes (email, nombre) identificables para autocompletar. ❌ No cumple Ningún input (Nombre, Email, Personas) tiene atributo autocomplete. Añadir autocomplete="name" y autocomplete="email" a los campos correspondientes.
A 1.4.1Use of ColorEl color no es el único portador de información. ❌ No cumple La obligatoriedad de los campos se comunica solo con color rojo en el texto de ayuda; ningún campo tiene además un indicador no cromático aplicado individualmente. Añadir texto o icono junto a cada campo obligatorio, no solo una nota general en color.
A 1.4.2Audio Control N/A No aplica No hay audio autoreproducido.
AA 1.4.3Contrast (Minimum)4.5:1 texto normal, 3:1 texto grande. ❌ No cumple Texto de .btn ("Reservar mesa", "Enviar reserva"): #a89484 sobre blanco = 2.9:1. Eyebrows de sección y .dish p: #8a7a6c sobre blanco/crema = ~4.1:1 y ~3.8:1. Todos por debajo de 4.5:1. Oscurecer #a89484 y #8a7a6c hasta 4.5:1 mínimo sobre sus fondos (ej. usar --marron #6b4a3a, que sí cumple).
AA 1.4.4Resize TextTexto ampliable a 200% sin perder contenido. ⚠️ No verificable Requiere probar zoom real en navegador; no determinable solo del CSS estático.
AA 1.4.5Images of Text ✅ Cumple
AA 1.4.10ReflowSin scroll horizontal a 320px de ancho. ⚠️ No verificable No hay ninguna @media query en toda la hoja de estilos, con grids fijos de 3 columnas y padding fijo de 48–96px: riesgo real, pero confirmar el scroll exige renderizar la página a 320px.
AA 1.4.11Non-text Contrast3:1 en bordes, iconos, controles. ❌ No cumple Borde de .btn (#a89484 sobre blanco) = 2.9:1. Borde de los inputs (var(--linea) #e5ddd3 sobre blanco) = 1.35:1. Ambos muy por debajo de 3:1. Oscurecer ambos colores de borde hasta 3:1 mínimo.
AA 1.4.12Text SpacingEl layout no se rompe si se fuerza más espaciado. ⚠️ No verificable No determinable solo leyendo CSS estático; requiere inyectar el override de espaciado y observar el resultado renderizado.
AA 1.4.13Content on Hover or Focus N/A No aplica No hay tooltips ni contenido que aparezca por hover/focus.
02

Operable

NivelCriterioEstadoMotivoSolución
A 2.1.1Keyboard ✅ Cumple
A 2.1.2No Keyboard Trap ✅ Cumple
A 2.1.4Character Key Shortcuts N/A No aplica No hay atajos de teclado implementados.
A 2.2.1Timing Adjustable N/A No aplica No hay límites de tiempo.
A 2.2.2Pause, Stop, Hide N/A No aplica No hay contenido en movimiento.
A 2.3.1Three Flashes N/A No aplica No hay animaciones ni parpadeos.
A 2.4.1Bypass BlocksSkip link para saltar bloques repetidos. ❌ No cumple No hay skip link ni landmark <main> para saltar el header/nav e ir directo al contenido. Añadir un skip link ("Ir al contenido") al inicio del <body> y envolver las secciones principales en <main>.
A 2.4.2Page Titled ✅ Cumple
A 2.4.3Focus Order ✅ Cumple
A 2.4.4Link Purpose (In Context)El texto del link se entiende por sí solo. ❌ No cumple Los 2 enlaces sociales del footer no tienen texto ni nombre accesible; su propósito no es determinable. Añadir aria-label="Facebook" / "Instagram" a cada enlace.
AA 2.4.5Multiple Ways N/A No aplica Página única con navegación por anclas; no aplica el concepto de "múltiples formas de llegar a una página" dentro de este alcance.
AA 2.4.6Headings and Labels ✅ Cumple
AA 2.4.7Focus VisibleEl foco de teclado siempre es visible. ❌ No cumple .btn e input tienen outline: none sin ningún estilo de foco alternativo. Afecta a los 2 botones ("Reservar mesa", "Enviar reserva") y los 3 campos del formulario. Sustituir outline: none por un foco visible (ej. outline: 2px solid var(--marron) con offset). Nunca eliminarlo sin reemplazo.
AA 2.4.11Focus Not Obscured ✅ Cumple
A 2.5.1Pointer Gestures N/A No aplica No hay gestos multitáctiles.
A 2.5.2Pointer Cancellation ✅ Cumple
A 2.5.3Label in Name ✅ Cumple
A 2.5.4Motion Actuation N/A No aplica No hay controles activados por movimiento del dispositivo.
AA 2.5.7Dragging Movements N/A No aplica No hay interacciones de arrastre.
AA 2.5.8Target Size (Minimum)24×24px mínimo en elementos interactivos. ❌ No cumple Los iconos sociales del footer miden 18×18px explícitos (width/height), sin padding, y están próximos entre sí (gap: 10px) sin que aplique ninguna excepción. Aumentar el área clicable a mínimo 24×24px (padding en el enlace, no solo el icono visual).
03

Understandable

NivelCriterioEstadoMotivoSolución
A 3.1.1Language of Page ✅ Cumple
AA 3.1.2Language of Parts N/A No aplica No hay fragmentos en otro idioma.
A 3.2.1On Focus ✅ Cumple
A 3.2.2On Input ✅ Cumple
AA 3.2.3Consistent Navigation N/A No aplica Página única; no hay otra página con la que comparar la navegación dentro de este alcance.
AA 3.2.4Consistent Identification N/A No aplica Mismo motivo: página única, sin otra página con la que comparar.
A 3.2.6Consistent Help N/A No aplica No existe mecanismo de ayuda ni páginas múltiples que comparar.
A 3.3.1Error IdentificationLos errores se identifican y describen en texto. ❌ No cumple Pese a indicar campos obligatorios, ningún input tiene required, pattern ni ningún otro mecanismo (JS, aria-invalid) que identifique errores al enviar el formulario incompleto o mal formado. Añadir required a los campos obligatorios y validación (nativa o JS) que identifique el error en texto al enviar.
A 3.3.2Labels or InstructionsLabels o instrucciones visibles en los campos. ❌ No cumple Los 3 campos ("Nombre", "tu@email.com", "Personas") usan solo placeholder como única indicación — desaparece al escribir y no es una etiqueta persistente. Añadir <label> visible y persistente para cada campo, manteniendo el placeholder como ayuda adicional si se quiere.
AA 3.3.3Error SuggestionEl error sugiere cómo corregirse. ❌ No cumple Al no existir ningún mecanismo de identificación de errores (ver 3.3.1), tampoco existe sugerencia de corrección. Una vez implementada la validación, describir cómo corregir cada error (ej. "El email no es válido, revisa el formato").
AA 3.3.4Error Prevention (Legal/Financial/Data) N/A No aplica Una reserva de mesa no es una transacción legal, financiera ni de eliminación de datos irreversible.
A 3.3.7Redundant Entry N/A No aplica Formulario de un solo paso; no repite ningún dato ya introducido.
AA 3.3.8Accessible Authentication (Minimum) N/A No aplica No hay login en esta página.
04

Robust

NivelCriterioEstadoMotivoSolución
A 4.1.2Name, Role, ValueCada componente expone su nombre, rol y estado al software asistivo. ❌ No cumple Los enlaces sociales del footer llevan aria-hidden="true" en el propio <a> pero siguen siendo focusables (sin tabindex="-1"): quedan totalmente ocultos para tecnología asistiva pese a recibir foco por teclado — un usuario de lector de pantalla tabula hasta un elemento "fantasma" sin nombre ni rol anunciado. Quitar aria-hidden="true" del <a> y añadir un aria-label descriptivo (el aria-hidden puede quedarse en el <svg> interno, que ya es decorativo dentro del enlace).
AA 4.1.3Status Messages N/A No aplica No hay mensajes de estado dinámicos implementados: sin JS ni backend visible en este archivo estático.

Conclusión

Nivel A

✕ No cumple

9 criterios A fallan: 1.1.1, 1.3.1, 1.3.3, 1.4.1, 2.4.1, 2.4.4, 3.3.1, 3.3.2, 4.1.2.

53% de los criterios A aplicables cumplen (10/19)

Nivel AA

✕ No cumple

Al no cumplir Nivel A, Nivel AA tampoco puede cumplir (AA exige A + AA juntos).

44% de los criterios A+AA aplicables cumplen (14/32)

El porcentaje es un indicador de avance, no una certificación — WCAG es binario (cumple / no cumple), sin niveles intermedios. Esta auditoría cubre solo public/a11ykit-demo/index.html, no el resto del sitio.