Document outlines and heading hierarchy in practice. You already know that <h1> through <h6> define headings; here we focus on using them consistently so the page makes sense to humans, browsers, and screen readers.
What the document outline is
Every HTML page has an implicit outline: a tree of sections defined by headings. Think of it like a table of contents. The <h1> is the book title. <h2> elements are chapters. <h3> elements are sections within a chapter, and so on.
Assistive technology can jump between headings. Browser extensions build page maps from them. Search engines use headings as strong signals about topic structure. Sloppy heading levels do not always break the visual design (CSS can make an <h4> look huge), but they do break the outline.
One H1 per page (usually)
As a default rule, each page gets one <h1> that names the page. On a blog post, that is the post title. On a contact page, it might be ‘Contact us’. On the home page, it is often the site name or primary value proposition.
Multiple <h1> elements are not invalid HTML, but they confuse the outline unless you have a deliberate reason (some single-page apps treat each ‘screen’ as a section – that is advanced territory). For static brochure sites and content pages, stick to one.
Do not skip levels
The most common mistake is jumping from <h2> to <h4> because the design called for a smaller font. Headings communicate structure, not appearance. Size and colour belong in CSS.
Good hierarchy:
<h1>Gardening tips</h1>
<h2>Spring planting</h2>
<h3>Vegetables</h3>
<h3>Herbs</h3>
<h2>Summer watering</h2>
<h3>Containers</h3>
Broken hierarchy (do not do this):
<h1>Gardening tips</h1>
<h4>Spring planting</h4>
<h2>Summer watering</h2>
Screen reader users who navigate by heading level will get a misleading picture of how content relates. Fix the levels; adjust the visual style with a class if needed.
Sections and headings work together
HTML5 introduced <section> and <article> for grouping content. A section should normally start with a heading. If you wrap content in <section> without a heading, ask yourself whether <div> would be clearer.
Example article with nested sections:
<article>
<h1>How to repot a houseplant</h1>
<p>Introductory paragraph…</p>
<section>
<h2>When to repot</h2>
<p>Content…</p>
</section>
<section>
<h2>What you need</h2>
<ul>
<li>Fresh compost</li>
<li>A slightly larger pot</li>
</ul>
</section>
<section>
<h2>Step by step</h2>
<ol>
<li>Water the plant the day before.</li>
<li>Loosen the root ball gently.</li>
</ol>
</section>
</article>
Each section is a meaningful chunk with its own subheading. The outline reads: H1 article title, then H2 subtopics. A reader skimming headings gets the full shape of the piece.
Headings inside landmarks
Landmark regions (<header>, <nav>, <main>, <aside>, <footer>) can contain headings. The page-level <h1> almost always lives in <main> (or inside an <article> within main).
Sidebars and footers often use <h2> for their section titles – ‘Related posts’, ‘Legal’ – even though the main content might also use H2 for its sections. That is acceptable because the landmarks create separate contexts. What you must avoid is arbitrary level choices based on font size alone.
If a sidebar heading feels ‘too prominent’ at H2, reduce it with CSS rather than demoting it to H4 and skipping H3.
Hidden headings for navigation blocks
Sometimes a region needs a heading for the outline but you do not want it visible. A footer with columns of links is a common case. You can include a heading and hide it visually while keeping it available to screen readers:
<footer>
<h2 class="visually-hidden">Site footer</h2>
<nav aria-label="Legal">
<ul>
<li><a href="/privacy/">Privacy</a></li>
<li><a href="/terms/">Terms</a></li>
</ul>
</nav>
</footer>
The class visually-hidden (or sr-only, depending on your CSS framework) removes the heading from sight but not from the accessibility tree. Do not use this trick to hide headings that sighted users need – only when the visible design already makes the purpose obvious and the heading is purely structural.
Testing your outline
You do not need special tools to sanity-check headings. Try these:
- Read headings only. Collapse or skim the page and read H1, H2, H3 in order. Does the story still make sense?
- Browser dev tools. Some browsers expose an accessibility tree where you can inspect heading levels.
- Extensions. HeadingsMap and similar extensions draw the outline as a nested list. Worth installing if you build pages regularly.
- Validators. The W3C Nu Html Checker flags some outline issues. It is not perfect, but it catches obvious problems.
Common smells
Watch for these patterns in your markup or a client’s legacy site:
- Bold paragraphs instead of headings.
<p><strong>Section title</strong></p>is not a heading. Use the correct<h*>element. - Heading levels chosen for size. If your stylesheet only styles H2 and H4, fix the CSS, not the HTML.
- Multiple H1s from CMS widgets. Page builder blocks that each output an H1 will wreck the outline. Configure widgets to use H2 or H3 when they sit inside an existing page.
- Empty sections. A
<section>with no heading and no clear purpose should probably be removed or merged.
Headings and SEO (briefly)
Search engines weight headings, but keyword stuffing in H2 tags does more harm than good. Write headings for humans first. A clear, descriptive H1 helps both accessibility and search – ‘Contact our Bristol workshop’ beats ‘Welcome’ on a contact page.
Keep heading text concise. If a heading runs to two full lines on mobile, consider shortening it or splitting the section.
Next up: landmark regions in depth – how <header>, <nav>, <main>, <aside>, and <footer> fit together in page templates you can reuse across a site.

