—HTML Series · Post 08: Semantic HTML
🏗️ Semantic HTML (Extremely Important)
This is the single most important concept in this entire course. Semantic HTML is what separates someone who writes HTML from someone who writes it well. This is what makes you professional.
The Difference Between Writing HTML and Writing It Well
You can build an entire website using nothing but <div> tags. You can wrap every section in a <div>, every header in a <div>, every navigation menu in a <div>. It will render in the browser. It will look correct. And it will be completely wrong.
A <div> is a generic container. It means nothing. It tells the browser "here's a box," but it says nothing about what's inside that box. A screen reader hitting a wall of <div> elements is like a person walking into a building with no signs on any door — every room looks the same, and there's no way to find anything without opening every single one.
Semantic HTML solves this. Instead of generic <div> containers, you use elements that describe what the content is. A <nav> tells the browser "this is navigation." A <header> says "this is the header." A <main> says "this is the main content." The page looks the same visually, but underneath, it's organized, meaningful, and accessible.
Think of semantic HTML as the difference between a building with labeled rooms and a building where every door is blank. Both buildings are functional. But only one is usable by everyone — especially people who can't see the interior. When you write semantic HTML, you're building the labels, the signs, the wayfinding system. You're building a building that works for humans, not just browsers.
Why This Matters More Than You Think
This isn't theoretical. It's practical. Hiring managers look at your HTML source. Accessibility audits flag non-semantic markup. Google's Lighthouse tool measures it. And over one billion people worldwide use assistive technology. Semantic HTML isn't a nice-to-have — it's a professional requirement.
The <div> Soup Problem
Let's see the problem in action. Here's a page structure using nothing but <div> elements, vs. the same structure with semantic HTML:
<div class="header">
<div class="nav">
<div class="nav-links">...</div>
</div>
</div>
<div class="main">
<div class="content">
<div class="post">...</div>
</div>
<div class="sidebar">...</div>
</div>
<div class="footer">...</div><header>
<nav>
<ul>...</ul>
</nav>
</header>
<main>
<section>
<article>...</article>
</section>
<aside>...</aside>
</main>
<footer>...</footer>They render identically in the browser. But the left version is a pile of meaningless boxes. The right version is a labeled blueprint. A screen reader can jump from the nav to the main content to the footer. Google can identify your primary content vs. sidebar content. A new developer joining your project can scan the HTML and understand the page structure in seconds.
The Semantic Page Blueprint
Here's how semantic elements map to a typical page layout. This is the structure of virtually every professional website:
The Seven Semantic Elements You Need to Know
<header>
<h1>CodeHerWay</h1>
<p>Where women code, lead, and rewrite the future of tech.</p>
</header><nav>
<ul>
<li><a href="#about">About</a></li>
<li><a href="#projects">Projects</a></li>
<li><a href="#contact">Contact</a></li>
</ul>
</nav>The <main> element is the most powerful landmark for accessibility. When a screen reader user presses a shortcut key to "jump to main content," they land inside <main>. Without it, they have to tab through your entire header and navigation on every single page load. One element. Massive impact.
<section> and <article> are the pair that confuses everyone. Here's the simple rule: articles can live inside sections, and sections can live inside articles. A "Blog" section might contain multiple article elements. A single long article might be divided into sections. They're not mutually exclusive — they're complementary.
The Complete Semantic Template
Here's what a fully semantic portfolio page looks like. This is the template you should base every project on:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Jenna Torres — Frontend Developer</title>
</head>
<body>
<header>
<h1>Jenna Torres</h1>
<nav>
<ul>
<li><a href="#about">About</a></li>
<li><a href="#projects">Projects</a></li>
<li><a href="#contact">Contact</a></li>
</ul>
</nav>
</header>
<main>
<section id="about">
<h2>About Me</h2>
<p>Frontend developer who builds fast, accessible websites.</p>
</section>
<section id="projects">
<h2>Projects</h2>
<article>
<h3>Weather Dashboard</h3>
<p>Real-time weather app using API data.</p>
</article>
<article>
<h3>LUXE E-Commerce</h3>
<p>Product page with interactive shopping cart.</p>
</article>
</section>
<section id="contact">
<h2>Contact</h2>
<p><a href="mailto:[email protected]">Email me</a></p>
</section>
</main>
<aside>
<h2>Currently Learning</h2>
<p>React, TypeScript, and accessibility best practices.</p>
</aside>
<footer>
<p>© 2025 Jenna Torres. Built with love and semantic HTML.</p>
</footer>
</body>
</html>What a Screen Reader Actually Hears
This is what makes semantic HTML real instead of theoretical. Here's an approximation of what a screen reader announces when it encounters the semantic page above vs. the div-soup version:
See the difference? The semantic version gives the user a map of the page. They can jump directly to the navigation, skip to main content, or find the footer — all without scrolling through everything. The div-soup version? Every section is just "Group." No landmarks. No shortcuts. No structure. The user has to read the entire page linearly to find anything.
Accessibility isn't a charity feature you add if you have extra time. It's a quality standard. The same way you wouldn't ship a site with broken links, you shouldn't ship a site with broken semantics. Every <div> you use where a semantic element would work is a door with no label, a room with no sign. Your users — all of them — deserve better.
When <div> Is Still the Right Choice
After all of this, you might think <div> is evil. It's not. <div> still has a legitimate purpose: it's a generic container for layout and styling when no semantic element fits.
Need to wrap some elements to apply a CSS grid or flexbox layout? Use a <div>. Need a wrapper for a background color that doesn't represent a meaningful section? Use a <div>. Need a container for JavaScript to target that doesn't have semantic meaning? Use a <div>.
The rule is simple: if a semantic element fits, use it. If none fits, use <div>. The problem was never <div> existing — it was <div> being used for everything.
A quick mental checklist before writing any container element: Is this a header? Use <header>. Navigation? <nav>. The main content? <main>. A thematic section with its own heading? <section>. Self-contained content? <article>. Supplementary info? <aside>. Closing section? <footer>. None of the above? Now use <div>.
My first three portfolio projects were built entirely with <div> elements. Not some divs — all divs. <div class="header">, <div class="nav">, <div class="main">, <div class="footer">. I named them semantically in my classes but used the most meaningless element possible for every single one.
I applied to a junior developer role and the hiring manager pulled up my portfolio's source code during the interview. She said, "I see you're using class names like 'header' and 'nav' — are you aware that HTML has actual elements for those?"
I wasn't. I genuinely did not know that <header>, <nav>, <main>, and <footer> existed as real HTML elements. I'd only ever seen <div> in the tutorials I followed, so I assumed that's how you built everything.
I didn't get that job. But I went home, read the MDN docs on semantic HTML, and refactored every project I had. The HTML got shorter. The code got cleaner. And I never used a <div> where a semantic element belonged again. That interview rejection was the most valuable feedback I've ever received.
🏆 Mini Build: Semantic Portfolio Structure
Rebuild your portfolio page using zero unnecessary <div> elements. Every container must be a semantic element. Here's your checklist:
Recap
Semantic HTML means using elements that describe what the content is, not just how it looks. <header> for introductory content. <nav> for navigation. <main> for the primary content (one per page). <section> for thematic groups. <article> for self-contained content. <aside> for supplementary content. <footer> for closing content. Use <div> only when no semantic element fits.
This isn't optional knowledge. It's the line between beginner HTML and professional HTML. It impacts accessibility, SEO, code readability, and how seriously other developers take your work. Every page you build from this point forward should be semantic by default.