Jump to main content

Heading levels and accessibility

Getting heading levels right is not as easy as one might think. There are several things to take into account.
Even if HTML 5 allows the use of more than one <h1> per page it is still seen as best practices to stick to only one.

Using only one <h1> will benefit SEO but more important it will be better for sreenreader users.

On most screenreading software you have a command to get a list of headings on a webpage. This list can be filtered to only show a certain level (e.g. level 1 headings). This feature helps users with screenreaders to quick find the main heading of the page.

Heading structures

The next part is how to structure the headings. A good heading structure is important for screenreader users as it helps them understand/navigate the page. Here are two examples of how a page with a main menu, sidebar and content can be structured.

Sections with visible headings

<header>
	<nav aria-labelledby="nav-heading">
		<h2 id="nav-heading">Main navigation</h2>
		<ul>
			<li><a href="#">Home</a></li>
			<li><a href="#">About</a></li>
			<li><a href="#">Contact</a></li>
		</ul>
	</nav>
</header>
<aside aria-labelledby="sidebar-heading">
	<h2 id="sidebar-heading">Sidebar</h2>
	<ol>
		<li>This is the latest news</li>
		<li>This is the next latest news</li>
		<li>This is the not-so latest news</li>
	</ol>
</aside>
<main>
	<h1>A heading example article</h1>
</main>

If the design includes visible headings for the main navigation or the sidebars these headings should semantically be "real" html-headings (not <p> or <span> or <div>). Here we use <h2> as the heading level for the main navigation and the sidebar and "saves" the <h1> to the main article heading. Because thats the most important one. This skips heading levels and most automatic validation tools will give you an error. But it is ok to do this according to W3 (you can read about it here or here).

Sections without visible headings

<header>
	<nav aria-label="Main navigation">
		<ul>
			<li><a href="#">Home</a></li>
			<li><a href="#">About</a></li>
			<li><a href="#">Contact</a></li>
		</ul>
	</nav>
</header>
<aside aria-label="Sidebar">
	<ol>
		<li>This is the latest news</li>
		<li>This is the next latest news</li>
		<li>This is the not-so latest news</li>
	</ol>
</aside>
<main>
	<h1>A heading example article</h1>
</main>

If the main navigation and sidebar doesn't have any visible headings it's still important to label these sections for screenreader users, this is done with aria-label. In this example the main article <h1> are the first heading on the page and the automatic validation tools won't complain.
(Do remember that automatic testing tools is not always right, and the only finds a part of the issues on a webpage).

Read more / sources: