Why use <label for>?
Click the label, focus the input.
The for attribute on a label connects the label to a form control. When the for value matches the input's id, clicking the label focuses the input — and screen readers announce the label text when the input is focused. Without it, the input has no accessible name. Screen reader users hear "edit text" with no context. This page covers the two patterns, the common bugs, and the placeholder myth.
Short answer: Use <label for="email">Email</label><input id="email" type="email">. The for value must exactly match the input's id. Alternatively, wrap the input inside the label — no for needed. Both work. Never use placeholder as a substitute for a label. Placeholder text disappears on typing and fails screen readers.
✅ Two patterns
Both associate a label with an input. Pick one per form.
for + id (explicit)
<label for="email"> + <input id="email">. The for value matches the input's id. Works when label and input are not adjacent.
Nesting (implicit)
<label>Email <input type="email"></label>. The input is inside the label. No for or id needed. Simpler for short labels.
One label, one input
A label's for takes exactly one id. For groups of inputs, use <fieldset> + <legend>.
Placeholder is not a label
Placeholder disappears on typing and is unreliable for screen readers. Use a visible label. Always.
✅ Before and after
The same form, with and without labels.
<input type="email" placeholder="Email"> <input type="password" placeholder="Password"> <button type="submit">Sign in</button>
❌ No accessible name for either input. ❌ Screen reader: "edit text", no context. ❌ Placeholder disappears on typing — label lost. ❌ Clicking the field's surroundings does nothing.
<label for="email">Email</label> <input id="email" type="email" placeholder="you@example.com"> <label for="password">Password</label> <input id="password" type="password"> <button type="submit">Sign in</button>
✅ Each input has an accessible name. ✅ Screen reader: "Email, edit text", "Password, edit text". ✅ Label text stays visible when typing. ✅ Clicking the label focuses the input.
<label> Email <input type="email" placeholder="you@example.com"> </label> <label> Password <input type="password"> </label>
✅ Implicit association — no for, no id. ✅ Screen reader announces "Email, edit text". ✅ Clicking anywhere in the label focuses the input. ✅ Good for forms where label and input are visually adjacent.
Don't use placeholder as a label. Placeholder text vanishes the moment the user starts typing — so the field's purpose is lost. Screen readers handle placeholder inconsistently: some announce it, some don't. Lighthouse and WCAG audits flag placeholder-only fields as missing accessible names. Use a visible label with for. If the design truly forbids a visible label, use a visually-hidden <label> — not a placeholder as a substitute.
⚠️ Common mistakes
The label mistakes that cost real time.
for="email" but id="user-email". Fix: they must match exactly, case-sensitive.
<label for="x"> but the input has no id. Fix: add id.
Disappears on typing, unreliable for screen readers. Fix: visible label with for.
Redundant — both work, but pick one. Fix: for+id, or nesting, not both.
A label associates with one input. Fix: <fieldset> + <legend> for groups.
Buttons are labeled by their text content. Fix: no label element needed — use aria-label only if the button has no text.
Two inputs with the same id. Fix: unique ids per page. Labels bind to the first match only.
Fine visually — but the input must still be accessible. Fix: don't hide the input. Use position: absolute; opacity: 0; only when you provide an accessible name elsewhere.
❓ Frequently asked
What does the label for attribute do?
The for attribute on a label element matches the id of a form control. When they match, clicking the label focuses the input. Screen readers also announce the label text when the input is focused, so users know what to type. Without it, the input has no accessible name and screen reader users hear only "edit text" with no context.
Can I nest the input inside the label instead?
Yes. Wrapping the input inside the label element also associates them — no for attribute needed. Both patterns are valid. The nesting pattern is simpler for short labels. The for/id pattern is more flexible: it works when the label and input are not adjacent, and it lets you style each independently. Pick one pattern per form and stay consistent.
What happens if the for doesn't match any id?
The association silently breaks. Clicking the label does nothing. The input has no accessible name — screen readers announce it as unlabeled. The W3C validator flags it. There is no runtime error; the browser just ignores the broken for. This is one of the most common form accessibility bugs — always verify that the for value exactly matches the input's id.
Does label for work with select and textarea?
Yes. The for attribute works with any labelable element: input, select, textarea, button, meter, output, progress. As long as the element has an id and the label's for matches it, clicking the label focuses the element and screen readers announce the label. Radio buttons and checkboxes also need labels — for is the standard way to associate them.
Can a label have multiple for attributes?
No. The for attribute takes exactly one id. One label associates with one control. If you need to describe multiple inputs, use fieldset and legend to group them, and give each input its own label. Or use aria-labelledby pointing to multiple IDs on the same input, but that is a separate attribute with separate rules.
Should I use placeholder instead of label?
No. Placeholder text disappears as soon as the user types, so the field's purpose is lost. Placeholders also fail contrast requirements and are not reliably announced by screen readers as labels. Use a visible label with for. Use placeholder for an example of the expected value, not as a label. If the design forbids a visible label, use an accessible visually-hidden label — not a placeholder as a substitute.