🧮 CSS counter-set() — Modern Counter Control Tutorial

🌐 What Is counter-set()?

counter-set() is a modern CSS function (part of the CSS Counter Styles spec) that allows you to set a counter’s value at a specific position — similar tocounter-reset but more flexible and usable directly inside content.

>>counter-set() lets you assign counter values on the fly — no need to reset at the parent.”

Note

✔ Works inside a selector
✔ Can be used inside content
✔ Lets you override counters without resetting everything

📌 Difference Between counter-reset and counter-set()

PropertyPurpose
counter-resetInitializes a counter (usually at the container level)
counter-set()Assigns a number to a counter anywhere, anytime

Note

Think of counter-set() as “override the counter here.”

📦 Syntax

Syntax

counter-set: counterName value;

counterName → name of the counter
value → the exact value to assign

📌 1. Setting a Counter Value

Basic set example

.section-title {
  counter-set: chapter 5;
}

.section-title::before {
  content: "Chapter " counter(chapter);
}

Output: Chapter 5(No need for counter-reset anywhere above!)

📌 2. Override Counter Midway

Override example

.step {
  counter-increment: step;
}

.step.special {
  counter-set: step 10;
}

.step::before {
  content: "Step " counter(step);
}

Normal steps → 1, 2, 3… Special step → becomes Step 10Next steps continue → 11, 12, ...

📌 3. Using Multiple Counters

Multiple counter set

.item {
  counter-set: major 3 minor 7;
}

Sets major = 3 and minor = 7 instantly.

📌 4. Using counter-set() in Generated Content

Yes — counter-set() can be used directly inside content (modern browsers).

counter-set inside content

.chapter::before {
  content: counter-set(ch 4) "Chapter " counter(ch);
}

Output: Chapter 4(The counter is set and displayed in a single declaration!)

📌 5. Manual Numbering in Lists

Manual list numbering

ol {
  list-style: none;
  counter-reset: li;
}

li.start-at-5 {
  counter-set: li 5;
}

li::before {
  counter-increment: li;
  content: counter(li) ". ";
}

List jumps to 5 at the special item.

📌 6. Reset + Set Combination

Reset + set

.chapters {
  counter-reset: ch;
}

.chapter::before {
  counter-increment: ch;
  content: counter(ch) ". ";
}

.chapter.override {
  counter-set: ch 20;
}

Normal → 1, 2, 3 Override → 20 Next → 21

📌 7. Using Styles (Roman, Alpha, etc.)

Formatted counter set

.roman::before {
  counter-set: index 7;
  content: counter(index, upper-roman) ") ";
}

Output: VII)

🧪 Real-World Examples

1️⃣ Numbered Card Grid

Card grid numbering

.cards {
  counter-reset: card;
}

.card {
  counter-increment: card;
}

.card.featured {
  counter-set: card 50;
}

.card::before {
  content: "#" counter(card);
}

2️⃣ Tutorials with Manual Override

Tutorial steps

.tutorial {
  counter-reset: step;
}

.step::before {
  counter-increment: step;
  content: "Step " counter(step);
}

.step.skip {
  counter-set: step 99;
}

Output: Step 1, Step 2, Step 99, Step 100…

⚠️ Common Mistakes

  • ❌ Expecting counter-set() to increment — it only sets
  • ❌ Forgetting that counter() still requires content
  • ❌ Using counter-set() without defining the counter name first
  • ❌ Resetting when you only need setting or overriding

Note

✔ Use counter-reset to define counters
✔ Use counter-increment to increase counters
✔ Use counter-set() to override or assign exact values

🔥 Summary

The counter-set() function is a powerful addition to CSS counters, giving developers precise control over counter values at any point. Perfect for dynamic numbering, conditional numbering, manual overrides, and building highly customized UI elements.

>>counter-set() is modern CSS’s answer to precise numbering control.”

Learn more →MDN Docs 📘