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

Доступные формы: 12 правил для разработчиков (с примерами кода)

12 практических правил для accessible forms: label, autocomplete, aria-describedby, валидация, focus, контраст. С примерами HTML/ARIA для login, checkout и контакт-форм.

А

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

9 мин чтения

Чому форми — критична точка

Форми — це місце, де користувач реально щось робить: реєструється, оформлює замовлення, надсилає звернення. За даними WebAIM Million 2025, 49% помилок Level A на середньому сайті — це проблеми форм (відсутні labels, неконтрастні поля, недоступні помилки). Втрата конверсії від поганої форми не помітна у Google Analytics, але вона є.

1. Кожне поле має програмний label

Скрін-рідер прочитає поле тільки якщо воно зв'язане з текстом — через елемент <label for="id"> або атрибут aria-label. Placeholder сам по собі не є label.

<!-- ❌ Погано: лише placeholder -->
<input type="email" placeholder="Email">

<!-- ✅ Добре: label прив'язаний до input -->
<label for="email">Email</label>
<input id="email" type="email">

2. Placeholder — це підказка, не заміна label

Placeholder зникає коли користувач починає вводити текст. Людина з когнітивними порушеннями може забути, що саме потрібно ввести. Використовуйте placeholder для прикладу формату (наприклад, «+380 50 123 45 67»), а не для опису поля.

3. Правильні input type для мобільних

type="email", type="tel", type="number", inputmode="numeric" — мобільна клавіатура одразу покаже потрібний набір символів. Це і UX-перемога, і доступність для людей з моторними порушеннями.

4. Атрибут autocomplete для відомих полів

WCAG 2.1 success criterion 1.3.5 вимагає вказувати autocomplete для полів зі стандартним значенням (name, email, address, tel). Це допомагає браузерам автозаповнювати форми і дозволяє людям з когнітивними порушеннями уникнути ручного введення.

<input id="name"  name="name"  autocomplete="name">
<input id="email" name="email" autocomplete="email">
<input id="tel"   name="tel"   autocomplete="tel">

5. Обов'язкові поля позначені і візуально, і програмно

Зірочка червоного кольору поряд з label — недостатньо: вона не зчитується скрін-рідером і не помітна дальтонікам. Використовуйте атрибут required та слово «обов'язкове» або символ із aria-label.

<label for="email">
  Email <span aria-label="обов'язкове" className="text-red-600">*</span>
</label>
<input id="email" type="email" required>

6. Помилки валідації прив'язані до поля через aria-describedby

Просто червоний текст під полем — невидимий для скрін-рідера. Зв'яжіть повідомлення з полем через aria-describedby, додайте aria-invalid="true" на поле з помилкою, і використайте role="alert" або aria-live="polite" для оголошення.

<input
  id="email"
  type="email"
  aria-invalid="true"
  aria-describedby="email-error"
>
<p id="email-error" role="alert" className="text-red-600 text-sm">
  Невірний формат email
</p>

7. Групи radio і checkbox — у fieldset з legend

Скрін-рідер озвучить legend перед кожною опцією: «Спосіб доставки, нова пошта», «Спосіб доставки, кур'єр». Без fieldset користувач не зрозуміє, до якого питання належать опції.

<fieldset>
  <legend>Спосіб доставки</legend>
  <label><input type="radio" name="ship" value="np"> Нова пошта</label>
  <label><input type="radio" name="ship" value="ukr"> Укрпошта</label>
  <label><input type="radio" name="ship" value="courier"> Кур'єр</label>
</fieldset>

8. Видимий focus-індикатор

outline: none без альтернативи — найгірша практика. Користувачі з клавіатурної навігацією загубляться у формі. Залишайте outline або робіть власний помітний indicator (border, ring, shadow) з контрастом 3:1.

9. Контраст тексту і полів — 4.5:1 / 3:1

Сірий текст label на білому фоні (#999 на #fff) має контраст 2.85:1 — це провал WCAG. Текст у полі: мінімум 4.5:1. Бордер поля з фоном: мінімум 3:1 за WCAG 2.1 criterion 1.4.11 Non-text Contrast.

10. Touch targets ≥ 44×44 px

Маленькі checkbox і radio на мобільних — біль для людей з тремором або великими пальцями. WCAG 2.2 criterion 2.5.8 Target Size (Minimum) вимагає 24×24 CSS-пікселів, але рекомендована практика — 44×44.

11. Не очищати поля при помилці submit

Найболючіший антипатерн: користувач заповнив 10 полів, ввів неправильний email — і всі дані зникли. Зберігайте всі введені значення, помічайте лише проблемне поле. WCAG 3.3.4 «Error Prevention» прямо цього вимагає для фінансових і юридичних форм.

12. Заголовок над формою і логічний порядок tab

<h2>Зворотний зв'язок</h2> над формою допомагає скрін-рідерам перейти прямо до неї через клавішу H. Порядок полів у HTML має відповідати візуальному — інакше клавіатурна навігація буде стрибати по сторінці. Уникайте tabindex з позитивними значеннями — це ламає природний порядок.

Швидкий тест за 60 секунд

Натисніть Tab по формі від початку до кінця. Бачите, де знаходиться focus? Чи можете заповнити форму без миші? Якщо ні — у вас порушені пункти 8, 12 і, ймовірно, 1.

Автоматизована перевірка

Lighthouse і axe DevTools знаходять близько 30% порушень — ті, що автоматично детектуються (відсутній label, недостатній контраст, дублювання id). Решту знаходить ручний прохід клавіатурою + скрін-рідер. InclusiveWeb Audit поєднує обидва підходи: автомат + перевірки шаблонів сторінок з груповою аналітикою.

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

Чи можна обійтись placeholder без label?

Ні, навіть якщо візуально красиво. Placeholder зникає при введенні, не зчитується частиною скрін-рідерів і має слабкий контраст за замовчуванням. Якщо label псує дизайн — приховайте його через .sr-only, а не приберіть взагалі. Так він залишиться для assistive tech.

Як зробити floating labels доступними?

Floating labels — це звичайний label з CSS-анімацією. Доступні, якщо: 1) HTML-структура зберігає семантику (label йде до або після input), 2) контраст плаваючого label достатній і у активному, і в неактивному стані, 3) при автозаповненні label не перекриває значення.

Чи треба показати помилки одразу при введенні (real-time)?

Найкраща UX-практика: валідація на події blur (поле втратило focus), а не change (кожна буква). Користувач не повинен бачити «Невірний email» поки він не завершив набирати. Для повторної перевірки після submit — валідуйте всю форму і знайдіть перше проблемне поле.

Чи можна використовувати CAPTCHA?

Так, але з обережністю. Класична CAPTCHA з текстом — провал для незрячих. Доступніші варіанти: hCaptcha з аудіо-альтернативою, Cloudflare Turnstile (невидимий для більшості користувачів), reCAPTCHA v3 (score-based, без challenge). Завжди надавайте альтернативний канал звернення (email, телефон), якщо CAPTCHA блокує користувача.

От чтения к действию

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

Доступные формы: 12 правил для разработчиков (с примерами кода) | InclusiveWeb