Ever written a long blog post and thought, “Wow, even I got lost halfway through this”?
Yeah — your readers probably feel the same.
That’s where a Table of Contents (TOC) saves the day.
It helps users navigate your content, boosts SEO, and makes your article feel organized — like a clean desk after a messy project.
In this post, I’ll show you how to automatically generate a Table of Contents for single posts using a small, smart PHP snippet.
Why a TOC Helps Your SEO 🧭
Here’s why adding a TOC isn’t just for looks:
- Improved User Experience: Visitors can quickly jump to sections they care about instead of endless scrolling.
- Better Engagement: Users spend more time interacting with your content — a good signal for search engines.
- Google Featured Snippets: TOCs create anchor links, which can help Google show rich snippets directly in search results.
- Accessibility: Clear navigation helps readers using assistive technologies.
So yeah, a TOC isn’t just “nice to have.” It’s a subtle SEO and UX powerhouse. 💪
The Code: Automatically Generate a TOC in WordPress
Add the following snippet to your theme’s functions.php file or your custom plugin:
function cv_generate_toc( $content ) {
if ( is_singular( 'post' ) ) {
// Find all H2 tags in the post content
preg_match_all( '/<h2.*?>(.*?)<\/h2>/', $content, $matches );
if ( empty( $matches[1] ) ) {
return $content; // No H2 headings found
}
// Generate the TOC HTML
ob_start();
?>
<div id="toc-container" class="toc-container">
<h3>Table of Contents</h3>
<ul>
<?php foreach ( $matches[1] as $heading ) :
$clean_heading = wp_strip_all_tags( $heading );
$slug = 'toc-' . sanitize_title( $clean_heading ); ?>
<li><a href="#<?php echo esc_attr( $slug ); ?>"><?php echo esc_html( $clean_heading ); ?></a></li>
<?php endforeach; ?>
</ul>
</div>
<?php
$toc = ob_get_clean();
// Add IDs to the H2 headings in the content
foreach ( $matches[1] as $index => $heading ) {
$clean_heading = wp_strip_all_tags( $heading );
$slug = 'toc-' . sanitize_title( $clean_heading );
$content = str_replace( $matches[0][$index], '<h2 id="' . esc_attr( $slug ) . '">' . $heading . '</h2>', $content );
}
// Combine TOC and content
$content = '<div class="content-toc-wrapper">' . $toc . '<div class="post-content">' . $content . '</div></div>';
}
return $content;
}
add_filter( 'the_content', 'cv_generate_toc' );
Add Smooth Scrolling for Better UX
Because we like that fancy scrolling-into-place effect:
function cv_enqueue_custom_toc_scripts() { ?>
<script>
document.addEventListener('DOMContentLoaded', function() {
document.querySelectorAll('.toc-container a').forEach(anchor => {
anchor.addEventListener('click', function(e) {
e.preventDefault();
document.querySelector(this.getAttribute('href')).scrollIntoView({
behavior: 'smooth'
});
});
});
});
</script>
<?php }
add_action( 'wp_footer', 'cv_enqueue_custom_toc_scripts' );
How It Works 🧠
The function looks for all H2 headings in your post.
It creates a TOC at the top, linking each heading to its section.
Each H2 gets a unique id (like #toc-introduction).
JavaScript adds a smooth scrolling effect when clicking TOC links.
Example Output
Table of Contents
• Introduction
• Why SEO Matters
• How to Add TOC in WordPress
• Final Thoughts
When clicked, each link smoothly scrolls to its section — no page jumps, no drama. 🎯
Styling the TOC with CSS 🎨
Want to make your TOC look clean and elegant? Drop this CSS snippet into your theme’s stylesheet or customizer:
.toc-container {
background: #f9f9f9;
border: 1px solid #e1e1e1;
border-radius: 8px;
padding: 20px;
margin-bottom: 30px;
box-shadow: 0 2px 5px rgba(0,0,0,0.05);
}
.toc-container h3 {
font-size: 1.2rem;
margin-bottom: 10px;
border-bottom: 1px solid #ddd;
padding-bottom: 5px;
}
.toc-container ul {
list-style: none;
padding-left: 0;
margin: 0;
}
.toc-container li {
margin: 6px 0;
}
.toc-container a {
color: #0073aa;
text-decoration: none;
}
.toc-container a:hover {
text-decoration: underline;
}
This gives you a modern, clean box that fits nicely with most WordPress themes.
Feel free to tweak the colors and padding to match your design.
Final Thoughts
A Table of Contents is one of those small things that makes a big impact.
It helps readers stay oriented, encourages engagement, and even improves your Google visibility.
If you write long-form content, this is a no-brainer.
Drop it in your functions.php, add a bit of CSS, and your posts just got smarter. 🧩
💡 Bonus idea: You can make your TOC collapsible or sticky for even better usability on long posts!