properly labelling form controls in HTML for accessibility

Making Forms Accessible: A Developer’s Guide to Labels and Inputs

We may earn an affiliate commission through purchases made from our guides and tutorials.

Well-labeled form controls are the backbone of accessible web design. When users interact with an input, they should know exactly what information is expected—whether they rely on sight, screen readers, or voice input. Clear, consistent labeling improves usability for everyone, reduces errors, and ensures compliance with accessibility standards such as WCAG.

The challenge is that HTML offers multiple ways to “label” an input—<label>, placeholder, title, aria-label, and aria-labelledby. While they may look interchangeable, each serves a specific role, and using them incorrectly often creates redundancy or confusion. The key is knowing when to use which attribute and how they interact.

Below is a consolidated resource for web developers on properly labelling form controls in HTML for accessibility. It covers the “why”, best practices, common pitfalls, attribute hierarchy, and concrete patterns to follow.

Why labels matter

  • The Web Content Accessibility Guidelines (WCAG) require form controls to have both a label (visible) and a name (what assistive tech like screen-readers understand). These should match or at least be consistent.
  • Visible labels help all users: sighted, cognitive, motor‐impaired. They improve clarity, reduce errors, and help users know what to enter.
  • Programmatic labels (via <label>, aria-labelledby, etc.) are essential for assistive technologies to properly expose the name, role, and state of inputs. Without these, screen readers often announce something generic like “edit field” with no context.

Attribute hierarchy for accessible names

When multiple possible sources of a “name” exist (label, placeholder, title, aria-label, aria-labelledby), browsers and assistive technologies follow rules to pick one. Knowing the hierarchy helps avoid unintentional outcomes.

Rough order (from highest priority / strongest):

  • aria-labelledby — refers to visible text elsewhere in the page; best when a label or text grouping already exists.
  • aria-label — used when no visible label text is present (e.g. icon-only buttons). But if you already have a <label>, avoid overriding it.
  • <label> element (explicit for="id") or implicit wrapping of control in <label> — the normal, preferred way. It is visible and programmatically associated.
  • title attribute — weak: inconsistent support, often only visible on hover, often ignored by some assistive tech. Should rarely be relied upon for critical labeling.
  • placeholder attributenot a substitute for a label. It is transient (disappears when user types), often low contrast, and may be omitted by some screen readers. Use only for hinting input format, not for essential identity.

Best practices / patterns to follow

Here are concrete guidelines to ensure your form controls are well-labelled and accessible:

PracticeWhat to DoWhy It Helps
Always include a visible <label> for each inputUse <label for="inputID"> with a matching id on the input, or wrap the input inside <label>.Ensures the label is read by assistive tech and seen by sighted users. Improves usability by making the label clickable, which sets focus on the input.
Use aria-describedby for supplementary instructionsAdd aria-describedby="hintID" on the input and place extra guidance in an element with that id.Keeps the main label concise while still giving screen readers access to hints such as format or required rules. Maintains clarity between “what the field is” and “how to fill it.”
Reserve aria-label / aria-labelledby for when no visible label is possibleUse them only for icon-only buttons, custom widgets, or when design constraints prevent visible text. Prefer aria-labelledby if text already exists on screen.Provides an accessible name when no visible label is available. Prevents overwriting or duplicating a perfectly good <label>.
Avoid relying on the title attribute for labelsDo not use title as the only way to identify an input. If used, restrict it to supplementary, non-essential information.title is inconsistently supported by screen readers, often hidden on touch devices, and hard to discover. Not dependable for conveying critical information.
Use placeholder only for hints or examplesWrite placeholder text that shows expected format or example values (e.g., user@example.com), not the field’s name.Prevents confusion when the placeholder disappears on input. Keeps the accessible name consistent while still offering useful context.
Mark required fields clearly and handle errors accessiblyIndicate required fields with visible text (e.g., “Required”) and link error messages using aria-describedby.Helps all users understand constraints. Screen readers can announce errors when focus returns to the field, ensuring no information is lost.
Group related fields with <fieldset> and <legend>Wrap sets of related inputs (like radio buttons or checkboxes) in a <fieldset>, with a <legend> describing the group.Provides essential context so assistive tech announces the group meaningfully (e.g., “Choose a shipping option”). Improves comprehension for sighted and non-sighted users alike.

Common mistakes to avoid

  • Duplicating the same label text in <label>, aria-label, title, and placeholder. Leads to redundant reads by screen readers.
  • Letting placeholder be the only visible label. Once the user begins typing, the placeholder disappears; low contrast or tiny placeholder text compounds problems.
  • Using aria-label that contradicts or omits visible label. For example, the visible label says “First name”, aria-label says “Your name” → assistive tech only announces “Your name”, confusing users who see “First name”. Violates “Label in Name” WCAG criterion.
  • Believing title reliably substitutes for labels. Many screen readers ignore title, or it may only be read on hover/focus. On mobile, hover doesn’t exist.
  • Over-using ARIA: adding aria-label, aria-labelledby, etc., when a standard HTML <label> would suffice, complicating maintenance and possibly reducing accessibility.

Example patterns (good vs bad)

Here are side-by-side examples to illustrate the right way and wrong way.

Bad:

<label for="email">Email</label>
<input type="email" id="email"
       aria-label="Email"
       placeholder="Email"
       title="Email">

Issues:

  • Three sources of “Email” text: <label>, aria-label, placeholder, title → redundant, possible confusion.
  • placeholder disappears once input starts.
  • title not reliably read; may be inaccessible on some devices.

Good:

<label for="email">Email address</label>
<input type="email" id="email" placeholder="user@example.com">

Variations where extra hints are needed:

<label for="dob">Date of birth</label>
<input type="text" id="dob" aria-describedby="dob-format">
<span id="dob-format">Format: YYYY-MM-DD</span>

Or, for an icon-only button:

<button aria-label="Close dialog">
  <svg aria-hidden="true" focusable="false">
    <!-- icon markup -->
  </svg>
</button>

Checklist for developers

Before deploying a form control, run through this checklist:

  1. Does each input have a visible <label>?
  2. Is the for-attribute on label and id on input correctly matched?
  3. Are supplementary hints/instructions needed? If yes, are they linked with aria-describedby?
  4. Is there any aria-label, title, placeholder in place? If so, are they needed, and do they duplicate label text or conflict?
  5. Does the visible label match (or is included in) the accessible name (especially when using ARIA)?
  6. Do required fields and error messages communicate clearly (visibly and programmatically)?
  7. Test with a screen reader (e.g. NVDA, VoiceOver) and keyboard only; test on mobile.

Summary

  • Prefer visible, properly associated <label> elements for form controls.
  • Use aria-label or aria-labelledby only when no visible label is possible.
  • Use placeholder only for hints, not for essential labeling.
  • Use title very sparingly; never rely on it for critical information.
  • Always ensure that what users see visually aligns with what assistive technologies announce (accessible name).

Was this helpful?

Thanks for your feedback!
Alex is the resident editor and oversees all of the guides published. His past work and experience include Colorlib, Stack Diary, Hostvix, and working with a number of editorial publications. He has been wrangling code and publishing his findings about it since the early 2000s.

Leave a comment

Your email address will not be published. Required fields are marked *