CodeMIRAI
0 XP

Accessibility basics

2 min read 6 runnable examples Quiz included

The World Health Organization estimates that one person in six lives with a significant disability. Accessible HTML lets them use your page with a screen reader, with a keyboard alone, with zoomed text or with high contrast. Most of it comes free when you use the right elements.

HTML
<style>
  .fake { display: inline-block; padding: 6px 12px; background: #5a48f5; color: white;
          border-radius: 6px; cursor: pointer; font-family: system-ui; }
</style>
<div class="fake" onclick="alert('Clicked the div')">Fake button</div>
<button onclick="alert('Clicked the button')">Real button</button>

Click inside the preview and press Tab: focus skips the fake button entirely, and Enter can't press it. A <button> can be focused, works with Enter and Space, and is announced as a button, all with no extra code. Use <a href> to go somewhere and <button> to do something.

Label every field

HTML
<!-- poor: the placeholder vanishes as you type, and isn't a reliable label -->
<input placeholder="Email">

<!-- good -->
<label for="email">Email</label>
<input id="email" type="email" autocomplete="email">

Give images and icons a name

alt text says what an image shows or does, and decorative images get alt="" so screen readers skip them. A button that shows only an icon needs a name too, from its text or from aria-label:

HTML
<button aria-label="Close">✕</button>
<button><img src="https://picsum.photos/seed/gear/16/16" alt=""> Settings</button>

Keyboard and focus

Everything that works with a mouse must work with a keyboard, and people need to see where the focus is. Never remove the focus outline without replacing it:

HTML
<style>
  button, a { font: 16px system-ui; margin: 4px; }
  .bad:focus { outline: none; }
  .good:focus-visible { outline: 3px solid #5a48f5; outline-offset: 2px; }
</style>
<button class="bad">No focus style</button>
<button class="good">Clear focus style</button>
<a class="good" href="#">A link</a>

Press Tab to move through them. :focus-visible shows the ring to keyboard users without flashing it on every mouse click.

Contrast

Text needs enough contrast with its background. The WCAG guidelines ask for a ratio of at least 4.5:1 for normal text and 3:1 for large text:

HTML
<p style="color:#aaa; background:#fff; font: 16px system-ui">Light grey on white: hard to read (2.3:1)</p>
<p style="color:#595959; background:#fff; font: 16px system-ui">Dark grey on white: easy to read (7:1)</p>

Don't rely on colour alone, either. A form field marked only with a red border tells a colour-blind visitor nothing; add a message in words.

Language and title

HTML
<html lang="en">
<title>Python loops · CodeMIRAI</title>

lang tells screen readers which language to pronounce, and the <title> is the first thing announced when a page opens.

ARIA, the last resort

ARIA attributes (role, aria-label, aria-expanded, aria-live...) add accessibility information that plain HTML can't express. The first rule of ARIA is don't use ARIA when a native element does the job: a <button> beats <div role="button" tabindex="0"> plus all the key handling you'd have to write yourself.

One genuinely useful ARIA attribute is aria-live, which announces changes to part of the page:

HTML
<button id="add">Add to cart</button>
<p id="status" aria-live="polite"></p>
<script>
  let count = 0;
  document.querySelector("#add").addEventListener("click", () => {
    count++;
    document.querySelector("#status").textContent = `${count} item(s) in your cart`;
  });
</script>

Screen readers announce the new text without moving the person's focus away from the button.

Finished this lesson?Mark it complete to earn +20 XP and move your progress on.