csscss-counter

CSS counters for headings in divs resetting too often


I've copy-pasted what seems to be some popular code for automatically numbering headers in HTML (from here)

But this seems to fail if my headings are inside divs:

example:

<!DOCTYPE html>
<html lang="en">
<head>
    <style type="text/css">
        article {counter-reset: h2}
        h2 {counter-reset: h3}
        h3 {counter-reset: h4}
        h4 {counter-reset: h5}
        h5 {counter-reset: h6}

        h2:before {counter-increment: h2; content: counter(h2) ". "; }
        h3:before {counter-increment: h3; content: counter(h2) "." counter(h3) ". "; }
        h4:before {counter-increment: h4; content: counter(h2) "." counter(h3) "." counter(h4) ". "; }
        h5:before {counter-increment: h5; content: counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) ". "; }
        h6:before {counter-increment: h6; content: counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) "." counter(h6) ". "; }
    </style>
</head>
<body>
    <main>
        <div class="Layout">
            <div class="Layout-main">
                <article class="post h-entry" itemscope itemtype="http://schema.org/BlogPosting">
                    <div class="post-content e-content" itemprop="articleBody">
                        <div class="container" id="notebook-container">
                            <div><div><div><h2 id="Background">Background </h2></div></div></div>
                            <div><div><div><h3 id="Enzyme-Kinetics">Enzyme Kinetics </h3></div></div></div>
                            <div><div><div><h3 id="Parameter-Inference">Parameter Inference </h3></div></div></div>
                            <div><div><div><h3 id="The-Michaelis-Menten/Briggs-Haldane-Approximation">The Michaelis-Menten/Briggs-Haldane Approximation </h3></div></div></div>
                            <div><div><div><h2 id="Exploring-the-Forward-Model">Exploring the Forward Model </h2></div></div></div>
                            <div><div><div><h3 id="A-Standard-Example">A Standard Example </h3></div></div></div>
                            <div><div><div><h3 id="Breaking-the-Michaelis-Menten/Briggs-Haldane-Assumptions:-Initial-Substrate:Enzyme-Ratio">Breaking the Michaelis-Menten/Briggs-Haldane Assumptions: Initial Substrate:Enzyme Ratio </h3></div></div></div>
                            <div><div><div><h3 id="Breaking-the-Michaelis-Menten/Briggs-Haldane-Assumptions:-Fast-Enzyme-Substrate-Complex-Kinetics">Breaking the Michaelis-Menten/Briggs-Haldane Assumptions: Fast Enzyme-Substrate Complex Kinetics </h3></div></div></div>
                            <div><div><div><h3 id="Comparing-Integrators">Comparing Integrators </h3></div></div></div>
                            <div><div><div><h2 id="Inference">Inference </h2></div></div></div>
                        </div>
                    </div>
                </article>
            </div>
        </div>
    </main>
</body>
</html>

It's especially curious to me this works for the h2 but not the h3's...


Solution

  • This unexpected behavior is caused by the deeply nested subheadings inside .container. According to the W3 spec:

    Counters are "self-nesting", in the sense that resetting a counter in a descendant element or pseudo-element automatically creates a new instance of the counter. This is important for situations like lists in HTML, where elements can be nested inside themselves to arbitrary depth.

    Your CSS counter implementation works as expected for the example when the <h2>-<h6> elements are adjacent siblings in the .container. After I removed all those extra <div> tags so the subheadings were adjacent siblings, the counter() usage displays numbers for subheadings and increments them correctly.

    You first define your counters (by resetting them) with counter-reset. Then you increment and insert them with counter-increment as generated content using the :before pseudo class. The counter works smoothly after the DOM structure was updated.

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <style type="text/css">
            article {counter-reset: h2}
            h2 {counter-reset: h3}
            h3 {counter-reset: h4}
            h4 {counter-reset: h5}
            h5 {counter-reset: h6}
    
            h2:before {counter-increment: h2; content: counter(h2) ". "; }
            h3:before {counter-increment: h3; content: counter(h2) "." counter(h3) ". "; }
            h4:before {counter-increment: h4; content: counter(h2) "." counter(h3) "." counter(h4) ". "; }
            h5:before {counter-increment: h5; content: counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) ". "; }
            h6:before {counter-increment: h6; content: counter(h2) "." counter(h3) "." counter(h4) "." counter(h5) "." counter(h6) ". "; }
        </style>
    </head>
    <body>
        <main>
            <div class="Layout">
                <div class="Layout-main">
                    <article class="post h-entry" itemscope itemtype="http://schema.org/BlogPosting">
                        <div class="post-content e-content" itemprop="articleBody">
                            <div class="container" id="notebook-container">
                                <h2 id="Background">Background</h2>
                                <h3 id="Enzyme-Kinetics">Enzyme Kinetics </h3>
                                <h3 id="Parameter-Inference">Parameter Inference </h3>
                                <h3 id="The-Michaelis-Menten/Briggs-Haldane-Approximation">The Michaelis-Menten/Briggs-Haldane Approximation </h3>
                                <h2 id="Exploring-the-Forward-Model">Exploring the Forward Model </h2>
                                <h3 id="A-Standard-Example">A Standard Example </h3>
                                <h3 id="Breaking-the-Michaelis-Menten/Briggs-Haldane-Assumptions:-Initial-Substrate:Enzyme-Ratio">Breaking the Michaelis-Menten/Briggs-Haldane Assumptions: Initial Substrate:Enzyme Ratio </h3>
                                <h3 id="Breaking-the-Michaelis-Menten/Briggs-Haldane-Assumptions:-Fast-Enzyme-Substrate-Complex-Kinetics">Breaking the Michaelis-Menten/Briggs-Haldane Assumptions: Fast Enzyme-Substrate Complex Kinetics </h3>
                                <h3 id="Comparing-Integrators">Comparing Integrators </h3>
                                <h2 id="Inference">Inference </h2>
                            </div>
                        </div>
                    </article>
                </div>
            </div>
        </main>
    </body>
    </html>