ARIA: Atributy přístupnosti v HTML kódu

ARIA: Atribúty prístupnosti v HTML kóde

Co je WAI-ARIA a proč patří mezi základy moderního webu

WAI-ARIA (Accessible Rich Internet Applications) je soubor atributů HTML definovaný konsorciem W3C, který doplňuje sémantiku a interakce webových komponent tak, aby byly přístupné uživatelům asistivních technologií (čtečky obrazovky, alternativní vstupy). ARIA nevytváří vizuální prvky, ale „říká“ strojům, co prvky jsou a co právě dělají. V době aplikací SPA, vlastních komponent a indexace AI/LLM je ARIA klíčová pro přístupnost (a11y), SEO i AIO/AEO – vyhledávačům a modelům pomáhá pochopit strukturu a stavy UI.

Zásady: kdy ARIA používat a kdy ne

  • Přednost má nativní HTML. Pokud existuje sémantický prvek (button, nav, header, ul/li, table, form), použijte ho. ARIA je doplněk, nikoli náhrada.
  • ARIA by neměla měnit vizuální chování. Ovládání klávesnicí a fokus řešte v JS/CSS, ARIA pouze popisuje roli a stav.
  • „Žádná ARIA je lepší než špatná ARIA“. Špatné stavy, chybné reference nebo nesoulad rolí škodí více než žádná ARIA.
  • Konzistence stavu. Atributy jako aria-expanded, aria-selected, aria-checked musí odrážet skutečný stav komponenty.

Stavební kameny ARIA: role, properties, states

ARIA se dělí na tři hlavní skupiny:

  • Role (např. role="button", role="dialog", role="navigation") – definují typ widgetu nebo landmarku.
  • Properties (např. aria-labelledby, aria-describedby, aria-owns) – stabilní vlastnosti a vztahy.
  • States (např. aria-expanded, aria-checked, aria-busy) – stavy, které se během interakcí mění.

Role landmarků: kostra stránky pro rychlou navigaci

Landmarky umožňují rychlou navigaci pomocí čteček obrazovky a zároveň pomáhají vyhledávačům a LLM pochopit rozvržení stránky:

  • role="banner" – hlavička webu (zpravidla na <header>).
  • role="navigation" – hlavní navigace (často <nav>).
  • role="main" – hlavní obsah (obvykle <main>).
  • role="complementary" – doplňkové panely (postranní panel).
  • role="contentinfo" – zápatí (na <footer>).
  • role="search" – vyhledávací formulář.

Používejte nativní prvky (header, nav, main, aside, footer), které už implicitně mají roli landmarku. Roli ARIA přidávejte pouze tehdy, když nepoužíváte nativní element nebo potřebujete význam upřesnit.

Názvy a popisy: aria-label, aria-labelledby, aria-describedby

  • Viditelný název > aria-label. Pokud už prvek obsahuje viditelný text (např. obsah tlačítka), ten tvoří jeho přístupný název. aria-label používejte u ikon bez textu.
  • aria-labelledby přiřazuje název jinému elementu podle id a má vyšší prioritu než aria-label.
  • aria-describedby poskytuje doplňující popis (tooltip, nápovědu), který se přečte po názvu.

Příklad tlačítka s ikonou bez textu:

<button aria-label="Otevřít menu"></button>

Interaktivní widgety: chování, stavy a klávesnice

U vlastních komponent je nutné sladit roli, stav i ovládání klávesnicí:

  • Button: role="button", aktivace klávesami Enter i Space, fokus přes tabindex="0" (pokud nejde o nativní <button>).
  • Disclosure/Accordion: ovládací prvek s aria-expanded="true|false" a cílový prvek s aria-hidden nebo řízeným zobrazením; propojení přes aria-controls.
  • Tabs: role="tablist" obsahuje role="tab" s aria-selected, panely mají role="tabpanel" a jsou propojené přes aria-controls/aria-labelledby. Šipky přesouvají fokus mezi kartami.
  • Menu/menubar a listbox: dodržujte definované vzory ovládání klávesnicí (šipky, Home/End, Enter/Escape).

Živé oblasti a dynamický obsah: aria-live, aria-busy

U asynchronních akcí oznamujte změny:

  • aria-live="polite|assertive" – čtečky oznámí novinky v oblasti; polite počká na vhodný okamžik, assertive přeruší čtení.
  • aria-busy="true" – signalizuje načítání; po dokončení přípravy obsahu nastavte zpět na false.
  • role="status" nebo role="alert" – krátká oznámení o úspěchu/chybě.

Skrývání a prezentace: aria-hidden, inert a správa fokusu

  • aria-hidden="true" odstraní prvek ze stromu přístupnosti, ale neblokuje fokus. U modálních oken upřednostněte použití inert na okolním obsahu, aby se zablokovala interakce i fokus.
  • Při otevření dialogu přesuňte fokus dovnitř a po zavření ho vraťte na spouštěcí prvek.
  • Skryté dekorativní prvky (SVG, ikonová písma) označte aria-hidden="true" nebo role="img" aria-label="..." s odpovídajícím významem.

Obrázky a grafika: role=“img“, alt a komplexní vizualizace

  • U prvku <img> používejte alt. U dekorativní grafiky zvolte prázdný alt="" a zvažte aria-hidden="true".
  • U nestandardní grafiky (SVG, canvas) použijte role="img" a název přidejte přes aria-label nebo aria-labelledby.
  • Komplexní grafy zpřístupněte krátkým názvem a delším popisem propojeným přes aria-describedby, případně nabídněte datovou tabulku.

Formuláře: chyby, nápovědy a povinná pole

  • Propojte popisek s polem přes <label for="id"> a id. Pokud popisek chybí, použijte aria-label.
  • Nápovědu propojte přes aria-describedby="id-popisu".
  • Chyby signalizujte pomocí aria-invalid="true" a dynamického chybového hlášení v oblasti s role="alert" nebo aria-live.
  • Povinnost pole indikujte vizuálně i programově pomocí aria-required="true" (u vlastních widgetů).

Dialogy a upozornění: role=“dialog“ a role=“alertdialog“

  • Kontejner má role="dialog" a název přiřazený přes aria-labelledby (nebo aria-label).
  • U kritických potvrzení použijte role="alertdialog" (výraznější upozornění).
  • Zamkněte pozadí (inert nebo „focus trap“) a zajistěte zavírání klávesou Escape.

Navigační prvky: drobečková navigace, stránkování, odkazy pro přeskočení obsahu

  • Drobečkovou navigaci označte pomocí nav s aria-label="Označení navigace" nebo "Drobečková navigace" podle jazyka; odkazy umístěte do seznamu.
  • Stránkování označte pomocí nav s aria-label="Stránkování"; aktuální stránka má aria-current="page".
  • Odkaz „Přejít na obsah“ umístěte na začátek a cílový prvek označte pomocí id; hlavní obsah by měl mít role="main" nebo být uvnitř <main>.

Tabulky, seznamy a struktury: respektujte nativní sémantiku

Pro datové tabulky používejte <table> s prvky <thead>, <tbody>, <th scope="col|row">. Vyhýbejte se ručnímu sestavování tabulek z prvků div s rolemi ARIA, pokud to není nezbytné.

ARIA a výkon LLM/SEO: proč prospívá AIO/AEO

  • Jednoznačná struktura. Landmarky a správné názvy prvků zlepšují porozumění informační architektuře modely a crawlery.
  • Přesné vztahy. Vztahy aria-labelledby/aria-describedby doplňují kontext (např. k tlačítkům, panelům, kartám), což pomáhá extrahovat smysluplné odpovědi.
  • Bohaté stavy UI. Správně aktualizované stavy (aria-expanded, aria-selected) vedou k lepšímu pochopení interaktivity a viditelnosti obsahu.
  • Nižší chybovost parsování. Konzistentní ARIA omezuje šum a anomálie v datech používaných pro indexaci a trénování.

Antivzory: čemu se vyhnout

  • Falešné tlačítko z div s role="button" bez podpory kláves Enter/Space a bez tabindex.
  • Konflikt role a elementu. Např. <button role="link"> mate čtečky; použijte správný element.
  • Nesprávné živé oblasti. Zbytečné aria-live="assertive" uživatele ruší.
  • Skrytí obsahu pouze vizuálně. display:none bez ohledu na stav ARIA může čtečku zmást; slaďte vizuální stav se stavem přístupnosti.
  • Neplatné reference. aria-labelledby="neexistuje" nebo duplicitní id.

Testování a validace: praktický postup

  1. Rychlý audit klávesnicí. Projděte celé UI pouze pomocí Tab/Shift+Tab, Enter, Space a šipek. Fokus musí být viditelný.
  2. Sémantická kontrola. Ověřte landmarky (banner, navigation, main, complementary, contentinfo, search).
  3. Stavy v akci. Sledujte, zda se při interakci mění hodnoty aria-expanded, aria-selected, aria-busy.
  4. Automatizované nástroje. Spusťte lintery a audity (např. axe, Lighthouse, HTML validator) a opravte chyby s vysokou prioritou.
  5. Čtečka obrazovky. Otestujte základní scénáře alespoň v jednom prostředí (NVDA/JAWS/VoiceOver).

Mini-vzory: stručné příklady

Rozbalovací nabídka (disclosure):

<button aria-expanded="false" aria-controls="sekcia-menu" id="tlacitko-menu">Menu</button>

<div id="sekcia-menu" role="region" aria-labelledby="tlacitko-menu" hidden>...navigace...</div>

Při otevření odstraňte hidden a nastavte aria-expanded="true".

Karty (tabs):

<div role="tablist" aria-label="Sekce">
  <button role="tab" id="tab-1" aria-controls="panel-1" aria-selected="true">Přehled</button>
  <button role="tab" id="tab-2" aria-controls="panel-2" aria-selected="false">Podrobnosti</button>
</div>

<section role="tabpanel" id="panel-1" aria-labelledby="tab-1">...</section>
<section role="tabpanel" id="panel-2" aria-labelledby="tab-2" hidden>...</section>

Vícejazyčnost a lokalizace

  • Jazyk dokumentu nastavte pomocí <html lang="sk">; čtečky podle toho volí syntézu řeči.
  • Popisky ARIA pište v jazyce obsahu. U vícejazyčných sekcí používejte lang na vnořených prvcích.

ARIA a designový systém: udržitelná implementace

  • Zaveďte knihovnu komponent s jednotnou sémantikou (role, stavy, názvy, klávesnice).
  • Každou komponentu dokumentujte: jaké atributy ARIA používá, kdy a jak se mění a jaké má klávesové zkratky.
  • Přidejte unit/e2e testy stavů a přístupnosti (fokus, pořadí tabulátoru, živé oblasti).

Checklist před vydáním

  • Nativní HTML všude tam, kde je to možné; ARIA pouze doplňuje.
  • Viditelný fokus a plná ovladatelnost klávesnicí.
  • Správné landmarky a hierarchie nadpisů.
  • Jednoznačné názvy prvků (aria-label vs. aria-labelledby), popisy přes aria-describedby.
  • Aktualizované stavy (aria-expanded, aria-selected, aria-checked, aria-busy).
  • Živé oblasti pouze tam, kde dávají smysl; bez zbytečných oznámení assertive.
  • Žádné neplatné reference ani duplicitní id.
  • Automatizovaný audit prošel bez kritických chyb.

ARIA jako společný jazyk lidí, strojů a modelů

Správné používání ARIA sjednocuje sémantiku a interakce napříč prohlížeči, čtečkami, crawlery a LLM. Jde o nízkonákladovou investici s vysokou návratností: zlepšuje přístupnost, použitelnost, konverze i porozumění obsahu v rámci SEO/AIO/AEO. Dodržujte zásadu „nejprve HTML, potom ARIA“ a vytvářejte komponenty, které jsou přístupné už od návrhu.