Перейти до основного контенту
Гранти до ₴500 000/рік для медіа
InclusiveWeb
Посібники

Чому семантичний HTML — це основа доступності

Покроковий гайд з семантичного HTML: як правильно використовувати теги, ієрархію заголовків та уникати div-супу.

А

Андрій Вдовин

10 хв читання

Семантичний HTML — це використання HTML-елементів відповідно до їхнього призначення: <button> для кнопок, <nav> для навігації, <article> для самостійних публікацій. На відміну від суто презентаційних елементів (як-от <div> і <span>), семантичні елементи несуть змістове навантаження, зрозуміле не лише людям, а й браузерам, пошуковим роботам та асистивним технологіям. Зв'язок із доступністю тут прямий: коли розмітка передає структуру і призначення контенту, скрінрідери можуть правильно оголосити цей контент, а користувачі клавіатури — ефективно ним керувати. Це фундамент, на якому будується будь-яка доступна веб-сторінка.

Div soup vs семантичний HTML

«Div soup» — це жаргонний термін для сторінок, де весь контент загорнутий у безліч вкладених <div>, без жодної структурної розмітки. Такий підхід може виглядати ідентично для зрячого користувача, але для скрінрідера це суцільний потік тексту без орієнтирів.

❌ Неправильно — «div soup»

div-soup.html
<div class="header">
  <div class="logo">InclusiveWeb</div>
  <div class="nav">
    <div class="nav-item">Продукт</div>
    <div class="nav-item">Ціни</div>
  </div>
</div>
<div class="main">
  <div class="hero">
    <div class="title">Зробіть сайт доступним</div>
    <div class="btn" onclick="signup()">Почати</div>
  </div>
  <div class="content">
    <div class="post">
      <div class="post-title">ARIA помилки</div>
      <div class="post-text">Стаття...</div>
    </div>
  </div>
</div>
<div class="footer">© 2025 InclusiveWeb</div>

✅ Правильно — семантичні landmarks

semantic.html
<header>
  <a href="/" aria-label="InclusiveWeb — головна">
    <img src="/logo.svg" alt="InclusiveWeb" />
  </a>
  <nav aria-label="Головна навігація">
    <ul>
      <li><a href="/product">Продукт</a></li>
      <li><a href="/pricing">Ціни</a></li>
    </ul>
  </nav>
</header>
<main>
  <section aria-labelledby="hero-heading">
    <h1 id="hero-heading">Зробіть сайт доступним</h1>
    <button type="button" onclick="signup()">Почати</button>
  </section>
  <section aria-labelledby="posts-heading">
    <h2 id="posts-heading">Останні статті</h2>
    <article>
      <h3>ARIA помилки</h3>
      <p>Стаття...</p>
    </article>
  </section>
</main>
<footer>
  <p>© 2025 InclusiveWeb</p>
</footer>

Коли скрінрідер потрапляє на семантичну сторінку, користувач може одразу перейти до <main>, перелистати заголовки або перейти по landmark-регіонах. У «div soup» нічого цього немає.

Semantic HTML та Accessibility Tree

Браузер будує дві паралельні структури з HTML-коду: DOM-дерево (Document Object Model) для рендерингу та дерево доступності (Accessibility Tree) для асистивних технологій. Дерево доступності — це спрощена версія DOM, де кожен вузол описується чотирма властивостями: роль (що це за елемент), ім'я (як він називається), стан (наприклад, checked, expanded) та значення.

Семантичні елементи автоматично отримують правильні ролі в дереві доступності: <button> отримує роль button, <nav> — роль navigation, <input type="checkbox"> — роль checkbox з відповідним станом checked. Натомість <div> потрапляє в дерево доступності без ролі — просто як безіменний блок, якщо не додати ARIA вручну.

Як переглянути Accessibility Tree

У Chrome DevTools відкрийте вкладку Elements, потім у правій панелі знайдіть вкладку «Accessibility». Там ви побачите, як браузер інтерпретує кожен елемент: його роль, ім'я та стан. Це незамінний інструмент для діагностики проблем доступності.

Ключові семантичні елементи

Нижче — огляд найважливіших семантичних елементів HTML, їхніх ARIA-ролей у дереві доступності та рекомендацій щодо використання.

ЕлементARIA рольКоли використовувати
<button>buttonБудь-яка інтерактивна дія (без навігації)
<nav>navigationНабори навігаційних посилань (меню, хлібні крихти)
<main>mainОсновний унікальний контент сторінки (один на сторінку)
<header>banner (якщо в body)Шапка сайту або секції: логотип, заголовок, навігація
<footer>contentinfo (якщо в body)Підвал сайту: копірайт, контакти, додаткові посилання
<article>articleСамостійний контент: пост, стаття, коментар, картка товару
<section>region (з aria-label)Тематична секція документа з заголовком
<aside>complementaryБічна панель, додатковий контент, пов'язані матеріали
<figure>figureЗображення, діаграми, код з підписом figcaption
<time>timeДати і часові відмітки з атрибутом datetime

Ієрархія заголовків

Заголовки <h1><h6> — це не просто великий або жирний текст. Вони створюють ієрархічну структуру документа — як зміст книги. Для користувачів скрінрідерів заголовки є основним засобом навігації: більшість з них переміщуються сторінкою, натискаючи клавішу H (наступний заголовок) або 16 (заголовок певного рівня).

Правило просте: ніколи не пропускайте рівні заголовків. Після <h1> може йти лише <h2>, після <h2> <h3> або наступний <h2>. Вибір розміру шрифта — завдання CSS, а не рівня заголовка.

❌ Неправильно

wrong.html
<h1>InclusiveWeb</h1>
<!-- Пропущено h2 — стрибок на h4! -->
<h4>Наші послуги</h4>
<!-- h3 використовується для стилізації, не структури -->
<h3>Детальніше</h3>
<!-- Кілька h1 на сторінці -->
<h1>Контакти</h1>

✅ Правильно

correct.html
<h1>InclusiveWeb — доступність для всіх</h1>
  <h2>Наші послуги</h2>
    <h3>Аудит доступності</h3>
    <h3>Автоматичне тестування</h3>
  <h2>Чому це важливо</h2>
    <h3>Юридичні вимоги</h3>
    <h3>Бізнес-переваги</h3>
  <h2>Контакти</h2>

Landmark Navigation

Landmarks (орієнтири) — це ключові регіони сторінки, між якими користувачі скрінрідерів можуть переміщуватись напряму. В NVDA і JAWS це клавіша D, у VoiceOver — W. Це схоже на «швидкі посилання» для навігації сторінкою без необхідності прослуховувати весь вміст зверху донизу.

Основні landmark-елементи:

  • <header> — шапка сайту, оголошується як «banner»
  • <nav> — навігаційний регіон, оголошується як «navigation»; якщо на сторінці кілька <nav> — кожен має унікальний aria-label
  • <main> — основний контент сторінки, оголошується як «main»; має бути лише один
  • <aside> — допоміжний контент, оголошується як «complementary»
  • <footer> — підвал сторінки, оголошується як «contentinfo»
landmarks.html
<body>
  <header>                         <!-- landmark: banner -->
    <nav aria-label="Головна">     <!-- landmark: navigation -->
      <ul>...</ul>
    </nav>
  </header>

  <main>                           <!-- landmark: main -->
    <nav aria-label="Хлібні крихти">  <!-- landmark: navigation -->
      <ol>...</ol>
    </nav>

    <article>
      <h1>Назва статті</h1>
      <aside aria-label="Авторська нотатка"> <!-- landmark: complementary -->
        <p>Примітка автора...</p>
      </aside>
    </article>
  </main>

  <aside aria-label="Схожі статті"> <!-- landmark: complementary -->
    <h2>Читайте також</h2>
  </aside>

  <footer>                         <!-- landmark: contentinfo -->
    <p>© 2025 InclusiveWeb</p>
  </footer>
</body>

<button> vs <div onClick>

Це одна з найчастіших помилок у сучасних JavaScript-застосунках: використання <div> або <span> з обробником onClick замість нативного <button>. Подивімось на детальну різницю:

Властивість<button><div onClick>
Клавіатурний фокус✓ Автоматично✗ Потрібен tabindex="0"
Enter / Space✓ Вбудовано✗ Потрібен keydown
ARIA роль✓ button (автоматично)✗ Потрібен role="button"
Стан disabled✓ Атрибут disabled✗ Потрібен aria-disabled + логіка
Стилі :focus-visible✓ Підтримується браузером✗ Без tabindex не працює
type="submit" у формі✓ Надсилає форму✗ Не надсилає форму

Semantic forms: label, fieldset, legend

Форми є одним із найскладніших для доступності компонентів. Три семантичні елементи вирішують більшість проблем:

<label> — мітка для поля вводу

Кожне поле форми повинно мати <label>. Це забезпечує три переваги: скрінрідер оголошує мітку при фокусі, область кліку збільшується (клік на текст мітки фокусує поле), а тип поля зрозумілий без візуального контексту.

<fieldset> і <legend> — групування полів

Для групп пов'язаних полів (радіо-кнопки, чекбокси) використовуйте <fieldset> з <legend>. Скрінрідер оголошує текст legend перед кожним полем групи, надаючи контекст.

semantic-form.html
<form>
  <!-- Явна мітка через for/id -->
  <div>
    <label for="full-name">Повне ім'я</label>
    <input type="text" id="full-name" name="name"
           autocomplete="name" required />
  </div>

  <!-- Прихована мітка (видима лише для скрінрідерів) -->
  <div>
    <label for="search" class="sr-only">Пошук</label>
    <input type="search" id="search" placeholder="Пошук..." />
  </div>

  <!-- Групування радіо-кнопок -->
  <fieldset>
    <legend>Оберіть план підписки</legend>
    <label>
      <input type="radio" name="plan" value="free" /> Безкоштовний
    </label>
    <label>
      <input type="radio" name="plan" value="pro" /> Професійний
    </label>
    <label>
      <input type="radio" name="plan" value="enterprise" /> Enterprise
    </label>
  </fieldset>

  <!-- Поле з підказкою через aria-describedby -->
  <div>
    <label for="password">Пароль</label>
    <input type="password" id="password"
           aria-describedby="password-hint" required />
    <p id="password-hint" class="hint">
      Мінімум 8 символів, одна велика літера та цифра
    </p>
  </div>

  <button type="submit">Зареєструватись</button>
</form>

Ключовий принцип

Якщо елемент є кнопкою — використовуй <button>. Завжди. Якщо елемент є посиланням — використовуй <a href>. Якщо елемент є навігацією — використовуй <nav>. Нативна семантика безкоштовна, надійна і не потребує ARIA.

Часті питання

Чи впливає семантичний HTML на SEO?

Так, і досить суттєво. Google використовує HTML-структуру для розуміння контенту сторінки. Правильна ієрархія заголовків допомагає визначити головну тему (h1) і підтеми (h2, h3). Елементи <article> і <section> допомагають Google зрозуміти межі контентних блоків. Крім того, семантичний HTML часто дозволяє отримувати розширені сніпети в пошуку (featured snippets).

Чи потрібно переписувати весь старий код, щоб зробити сайт доступним?

Не обов'язково. Почніть з найбільш критичних змін: додайте <main>, <nav> і <header>, виправте ієрархію заголовків, замініть <div onClick> на <button>, додайте мітки до форм. Ці зміни забезпечать 80% покращень при 20% зусиль. Повний рефакторинг можна робити поступово — компонент за компонентом.

Яка різниця між <section> і <article>?

<article> — це самостійний, незалежний контент, який має сенс сам по собі навіть поза контекстом сторінки: пост блогу, новинна стаття, коментар, картка продукту. <section> — це тематична частина документа, яка є частиною більшого цілого і зазвичай має заголовок. Простий тест: чи має сенс цей контент, якщо вирвати його з контексту сторінки? Якщо так — це <article>.

Як перевірити семантичну структуру сторінки?

Декілька ефективних методів: 1) Перевірте сторінку у скрінрідері (NVDA безкоштовний для Windows, VoiceOver вбудований у macOS/iOS) — спробуйте навігацію по заголовках і landmarks. 2) Використайте розширення HeadingsMap або Accessibility Insights для Chrome, щоб побачити структуру заголовків. 3) Запустіть axe DevTools для автоматичного виявлення проблем. 4) Перегляньте дерево доступності у Chrome DevTools (Elements → Accessibility). 5) Спробуйте відключити CSS — добре структурований семантичний HTML має мати логічний порядок і без стилів.

Джерела

Від читання до дії

InclusiveWeb сканує ваш сайт і виправляє помилки доступності за 3 хвилини. 7 днів безкоштовно, без кредитної картки.

Чому семантичний HTML — це основа доступності | InclusiveWeb