Skip to content

Instantly share code, notes, and snippets.

@PhilippeVay
Created February 16, 2023 16:53
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save PhilippeVay/1e7f7a883037e5ad7113496ae4c8ea07 to your computer and use it in GitHub Desktop.
Save PhilippeVay/1e7f7a883037e5ad7113496ae4c8ea07 to your computer and use it in GitHub Desktop.
Stylus script: headings display and count
/* ==UserStyle==
@name Headings: display and count
@namespace github.com/openstyles/stylus
@version 0.1.0
@description Highlight headings h1 to h6 plus role="heading". Count total number and also each level and role.
@author Philippe Vayssière
==/UserStyle== */
/* Counting elements is adapted from a Stylus script made by Access42. Hat tip to them! */
:root {
--white: white;
--heading: green;
--error: red;
--c-msg: var(--white);
--bg-msg: var(--heading);
--bd-msg: var(--heading);
--jump: "";
}
/* Highlight headings */
:where([role="heading"], h1, h2, h3, h4, h5, h6) {
position: relative;
outline: 5px solid var(--bd-msg);
}
/* Number of headings, tag by tag (and attribute role="heading"): headingN (N=1..6) and headingRole */
/* Total number of headings: heading */
[role="heading"] { counter-increment: headingRole heading; }
h1 { counter-increment: heading1 heading; }
h2 { counter-increment: heading2 heading; }
h3 { counter-increment: heading3 heading; }
h4 { counter-increment: heading4 heading; }
h5 { counter-increment: heading5 heading; }
h6 { counter-increment: heading6 heading; }
/* Level */
:where([role="heading"], h1, h2, h3, h4, h5, h6)::before {
content: "<" var(--jump) " " var(--n) ">";
margin-right: 0.5ch;
padding-right: 0.5ch;
line-height: 1;
font-weight: normal;
color: var(--c-msg) !important;
background-color: var(--bg-msg);
outline: 3px solid var(--bd-msg);
}
/* Error: lack of content in-between headings */
/* hN + h≤N */
h6 + :where(h1, h2, h3, h4, h5, h6, [role="heading"]),
h5 + :where(h1, h2, h3, h4, h5),
h4 + :where(h1, h2, h3, h4),
h3 + :where(h1, h2, h3),
h2 + :where(h1, h2),
h1 + :where(h1),
/* hN + role≤N */
h5 + [role="heading"]:not([aria-level="6"]),
h4 + [role="heading"]:not(:where([aria-level="5"], [aria-level="6"])),
h3 + [role="heading"]:not(:where([aria-level="4"], [aria-level="5"], [aria-level="6"])),
/* h2 + [role="heading"]:not([aria-level]), /* implicit aria-level="2" */
h2 + [role="heading"]:where([aria-level="1"], [aria-level="2"], :not([aria-level])),
h1 + [role="heading"]:where([aria-level="1"]),
/* roleN + h≤N */
[role="heading"][aria-level="6"] + :where(h1, h2, h3, h4, h5, h6, [role="heading"]),
[role="heading"][aria-level="5"] + :where(h1, h2, h3, h4, h5),
[role="heading"][aria-level="4"] + :where(h1, h2, h3, h4),
[role="heading"][aria-level="3"] + :where(h1, h2, h3),
[role="heading"]:where([aria-level="2"], :not([aria-level])) + :where(h1, h2), /* equiv h2 */
[role="heading"][aria-level="1"] + :where(h1),
/* roleN + role≤N */
[role="heading"][aria-level="5"] + [role="heading"]:not([aria-level="6"]),
[role="heading"][aria-level="4"] + [role="heading"]:not(:where([aria-level="5"], [aria-level="6"])),
[role="heading"][aria-level="3"] + [role="heading"]:not(:where([aria-level="4"], [aria-level="5"], [aria-level="6"])),
[role="heading"]:where([aria-level="2"], :not([aria-level])) + [role="heading"]:where([aria-level="1"], [aria-level="2"], :not([aria-level])),
[role="heading"][aria-level="1"] + [role="heading"]:where([aria-level="1"]) {
--jump: "⚠"; /* ❌ */
--c-msg: var(--error);
--bg-msg: var(--white);
--bd-msg: var(--error);
}
html {
counter-reset: heading heading1 heading2 heading3 heading4 heading5 heading6 headingRole;
}
/* Display number of headings (total then individually with role and h1-h6) */
html::after {
content: counter(heading) " headings\A\A h1: " counter(heading1) "\A h2: " counter(heading2) "\A h3: " counter(heading3) "\A h4: " counter(heading4) "\A h5: " counter(heading5) "\A h6: " counter(heading6) "\A role=\"heading\": " counter(headingRole) "\A";
position: fixed !important;
top: 300px !important;
right: 0 !important;
z-index: 123456 !important;
width: 12em !important;
border: 5px solid #fff;
border-right: 0;
padding: 15px !important;
white-space: pre !important;
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Helvetica, Arial, sans-serif, 'Apple Color Emoji', 'Segoe UI Emoji', 'Segoe UI Symbol';
font-size: 20px !important;
font-weight: bold;
color: #fff !important;
background: #10415E !important;
}
/* tagName via Custom Property */
[role="heading"] { --n: '* role="heading" ' var(--level) }
[aria-level="1"] { --level: 'level="1"' }
[aria-level="2"] { --level: 'level="2"' }
:not([aria-level]) { --level: 'level="implicit 2"' }
[aria-level="3"] { --level: 'level="3"' }
[aria-level="4"] { --level: 'level="4"' }
[aria-level="5"] { --level: 'level="5"' }
[aria-level="6"] { --level: 'level="6"' }
h1 { --n: 'h1' }
h2 { --n: 'h2' }
h3 { --n: 'h3' }
h4 { --n: 'h4' }
h5 { --n: 'h5' }
h6 { --n: 'h6' }
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment