Markdown Table of Contents Generator
Generate a [text](#anchor) TOC from Markdown headings — bullet, numbered, or HTML output with GitHub/GitLab/simple slug styles.
TOC appears here.
How to use
- Paste your Markdown in the left panel.
- Choose style (bullet / numbered / HTML), slug rule (matching where you'll publish), and min/max heading level.
- Copy the TOC and paste it at the top of your document.
About this tool
ShowHide
Generate a table of contents from the headings in a Markdown document, as a nested list of links you can paste at the top of a README. Choose the heading depth to include, and pick the slug style your host actually uses — GitHub, GitLab and a plain simple form all build anchors differently, which is exactly why a table of contents copied from one repository quietly stops working when the file moves to another. Repeated headings are numbered the way GitHub numbers them, so a document with three sections called Usage gets links that land on the right one rather than all three pointing at the first. Everything runs locally in your browser — the document is never uploaded.
Frequently asked questions
Why three slug styles?
GitHub's slug rule keeps Unicode (한글 → 한글). GitLab strips more aggressively. 'Simple' is ASCII-only — useful for generic Markdown renderers.
How are duplicate headings handled?
Same as GitHub: the first instance gets the plain slug, later ones append -1, -2, etc. Anchors will resolve correctly.
Why is code block content ignored?
Lines starting with # inside fenced code (between lines of three backticks) are usually shell prompts or comments, not headings. The parser tracks fence state to skip them.
Does GitHub render [text](#slug) correctly?
Yes — GitHub auto-generates anchor IDs for every heading and resolves matching link slugs. Use the GitHub slug style here.
My table of contents broke after moving the file to another host. Why?
Because the anchor rules are not standardised. GitHub keeps Unicode and strips most punctuation; GitLab and other renderers differ on both counts, so a link that resolved on one produces a dead anchor on the next. Regenerate with the style matching wherever the file now lives.
Should I write the anchors by hand instead?
Only if you also stop editing headings, which nobody does. Anchors are derived from heading text, so renaming a section silently breaks any link pointing at it — including ones in other files and in issues. Regenerating the table after an edit is the cheaper habit.
Related tools
Markdown Table Generator
Paste CSV, TSV, or pipe-delimited data and get a properly aligned GitHub-flavored Markdown table.
Text
Markdown Table to CSV Converter
Convert a GitHub-flavored Markdown table into CSV, TSV or semicolon-separated rows, in your browser.
Text
Excel (XLSX) to CSV, JSON & Markdown
Open an .xlsx workbook in the browser and export any sheet as CSV, JSON or a Markdown table — the file never leaves your device.
File
CSV → HTML / Markdown / JSON Table
Convert CSV to an HTML <table>, a Markdown table, or a JSON array of objects — auto-detects the delimiter.
Convert
Markdown → HTML Converter
Convert Markdown to clean HTML — copy the source for emails, CMS pages, or anywhere a rendered preview isn't enough.
Text
Markdown Stats & Reading Time
Count words, sentences, headings, links, code blocks, and estimate reading / speaking time for any Markdown.
Text