SalakCode SalakCode
Accessibility

Semantic HTML

Use meaningful markup for better accessibility

Beginner
a11y html structure seo

Definition

Semantic HTML uses markup that conveys meaning about the content it contains. Instead of generic divs and spans, semantic elements like header, nav, main, article, and footer describe the structure and purpose of content, making it accessible to screen readers and search engines.

Why Semantic HTML Matters

Screen Reader Experience

<!-- Bad: Screen reader just says "div" -->
<div class="header">
  <div class="nav">...</div>
</div>

<!-- Good: Screen reader announces landmarks -->
<header>
  <nav aria-label="Main">...</nav>
</header>

Keyboard Navigation

<!-- Bad: Custom button not keyboard accessible -->
<div class="button" onclick="submit()">Submit</div>

<!-- Good: Native button with built-in accessibility -->
<button type="submit">Submit</button>

Common Semantic Elements

Document Structure

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>Page Title</title>
</head>
<body>
  <header>
    <nav>
      <a href="/">Home</a>
      <a href="/about">About</a>
    </nav>
  </header>
  
  <main>
    <article>
      <h1>Article Title</h1>
      <p>Content...</p>
    </article>
    
    <aside>
      <p>Related content</p>
    </aside>
  </main>
  
  <footer>
    <p>© 2024 Company</p>
  </footer>
</body>
</html>

Text Content

<!-- Headings (h1-h6) -->
<h1>Main Page Title</h1>
<section>
  <h2>Section Title</h2>
  <article>
    <h3>Article Title</h3>
  </article>
</section>

<!-- Lists -->
<ul>
  <li>Unordered item</li>
  <li>Another item</li>
</ul>

<ol>
  <li>First step</li>
  <li>Second step</li>
</ol>

<dl>
  <dt>Term</dt>
  <dd>Definition</dd>
</dl>

<!-- Quotes -->
<blockquote cite="https://source.com">
  <p>Long quotation here...</p>
</blockquote>

<p>She said <q>Short quote</q></p>

<!-- Time -->
<time datetime="2024-01-15">January 15, 2024</time>

Forms

<form action="/submit" method="POST">
  <fieldset>
    <legend>Personal Information</legend>
    
    <label for="name">Full Name</label>
    <input 
      type="text" 
      id="name" 
      name="name"
      required
      aria-describedby="name-help"
    >
    <span id="name-help">Enter your legal name</span>
    
    <label for="email">Email</label>
    <input type="email" id="email" name="email" required>
    
    <button type="submit">Submit</button>
  </fieldset>
</form>

HTML5 Sectioning Elements

<article>
  <!-- Self-contained content -->
  <!-- Blog post, news article, product card -->
</article>

<section>
  <!-- Thematic grouping of content -->
  <!-- Chapter, tab panel, feature section -->
</section>

<aside>
  <!-- Tangentially related content -->
  <!-- Sidebar, callout, advertising -->
</aside>

<figure>
  <img src="chart.png" alt="Sales chart showing growth">
  <figcaption>Figure 1: Q4 Sales Growth</figcaption>
</figure>

<details>
  <summary>Click to expand</summary>
  <p>Hidden content revealed</p>
</details>

<dialog id="modal">
  <form method="dialog">
    <p>Modal content</p>
    <button>Close</button>
  </form>
</dialog>

Media Elements

<!-- Images with alt text -->
<img 
  src="photo.jpg" 
  alt="Golden retriever playing in park"
  width="600" 
  height="400"
>

<!-- Decorative images (empty alt) -->
<img src="decoration.png" alt="">

<!-- Audio -->
<audio controls>
  <source src="audio.mp3" type="audio/mpeg">
  <source src="audio.ogg" type="audio/ogg">
  <p>Your browser doesn't support audio</p>
</audio>

<!-- Video -->
<video controls width="640" height="360">
  <source src="video.mp4" type="video/mp4">
  <track 
    kind="captions" 
    src="captions.vtt" 
    srclang="en" 
    label="English"
  >
  <p>Your browser doesn't support video</p>
</video>

<!-- Picture element for responsive images -->
<picture>
  <source media="(min-width: 800px)" srcset="large.jpg">
  <source media="(min-width: 400px)" srcset="medium.jpg">
  <img src="small.jpg" alt="Responsive image">
</picture>

Best Practices

Heading Hierarchy

<!-- Good: Logical hierarchy -->
<h1>Page Title</h1>
  <h2>Section 1</h2>
    <h3>Subsection</h3>
  <h2>Section 2</h2>

<!-- Bad: Skipped levels -->
<h1>Page Title</h1>
  <h3>Section (skipped h2)</h3>
<!-- Use <a> for navigation -->
<a href="/about">About Page</a>
<a href="/contact">Contact</a>

<!-- Use <button> for actions -->
<button onclick="submitForm()">Submit</button>
<button onclick="toggleMenu()">Toggle Menu</button>

Tables for Data

<!-- Good: Data table -->
<table>
  <caption>Monthly Sales</caption>
  <thead>
    <tr>
      <th scope="col">Month</th>
      <th scope="col">Sales</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <th scope="row">January</th>
      <td>$10,000</td>
    </tr>
  </tbody>
</table>

<!-- Bad: Using table for layout -->
<table>
  <tr>
    <td>Header</td>
    <td>Content</td>
  </tr>
</table>
Key Takeaway

Semantic HTML provides meaning to your content, improving accessibility for screen readers and search engine optimization. Use appropriate elements for their intended purpose, maintain logical heading hierarchies, provide meaningful alt text, and prefer native HTML elements over generic divs. Native elements come with built-in accessibility features that custom components must manually implement.

Resources

Related Topics