Token Naming Convention
Semanticus CSS uses a 4-tier token system. Each tier builds on the previous, giving you precise control over how broadly or narrowly a style change applies.
Four Token Tiers
Tier 1: System Tokens --property[-state] page-level defaults
Tier 2: Variant Tokens --{variant}-property[-state] variant definitions
Tier 3: Component Tokens --{component}-property[-state] component-scoped slots
Tier 4: Individual Tokens --_{component}-property[-state] per-instance overridesThe flow: System → Variant → Component → Individual (--_).
Tier 1: System Tokens
No scope prefix. These define the document-wide baseline and must match a CSS longhand property name whenever possible.
:root, :host {
--background-color
--color
--font-family
--font-size
--typography-margin-block
--border-color
--border-radius
--outline-width
--opacity-disabled
--transition
/* Exceptions */
--spacing
--color-hover-shade
}System Tokens affect the entire page. Setting --background-color on a modifier class changes the background of every component that reads it.
Tier 2: Variant Tokens
These provide the raw color values consumed by variant modifier classes. Users override these to define custom palettes.
--{variant}-{property}[-{state}]:root, :host {
--primary-color
--primary-color-hover
--primary-background-color
--primary-background-color-hover
--primary-outline-color
--secondary-color
--secondary-color-hover
--secondary-background-color
--secondary-background-color-hover
--secondary-outline-color
/* Also: contrast, success, info, warning, danger */
/* (each with color, background-color, outline-color, and *-hover variants) */
}Variant Tokens are referenced by variant classes but don't directly style elements — they feed into the tiers below.
Tier 3: Component Tokens
Scoped to a component type. Setting one of these changes every instance of that component (e.g., all buttons, all inputs, all dialogs).
--{component}[-{part}]-{property}[-{state}]:root, :host {
/* Building Blocks */
--focus-ring-width
--menu-box-shadow
--selection-background-color
--backdrop-background-color
/* Buttons */
--buttons-color / --buttons-color-hover
--buttons-background-color / --buttons-background-color-hover
--buttons-padding-block / --buttons-padding-inline
/* Inputs */
--inputs-background-color / --inputs-background-color-focus
--inputs-border-color / --inputs-color
--inputs-accent-color / --inputs-placeholder-color
/* Dialog */
--dialog-background-color / --dialog-border-color
/* Details */
--details-dropdown-background-color / --details-dropdown-color / --details-dropdown-border-color
--details-menu-background-color / --details-menu-color
/* Links, Headings, Lists, Code, Mark, Table, Navigation, Progress, Tooltip… */
}Tier 4: Individual Component Tokens
Private tokens prefixed with --_. Defined in each component's CSS file and initialized from the Component Token tier. These are the values the component actually consumes for its own styling.
--_{component}[-{part}]-{property}[-{state}]/* Inside _buttons.css */
button, [role="button"] {
--_buttons-background-color: var(--buttons-background-color);
--_buttons-color: var(--buttons-color);
--_buttons-border-color: var(--_buttons-background-color);
background-color: var(--_buttons-background-color);
color: var(--_buttons-color);
border-color: var(--_buttons-border-color);
}
/* Inside inputs/_common.css */
:where(input, select, textarea) {
--_inputs-background-color: var(--inputs-background-color);
--_inputs-border-color: var(--inputs-border-color);
background-color: var(--_inputs-background-color);
border-color: var(--_inputs-border-color);
}
/* Inside _dialog.css */
dialog {
--_dialog-background-color: var(--dialog-background-color);
--_dialog-border-color: var(--dialog-border-color);
background: var(--_dialog-background-color);
border-color: var(--_dialog-border-color);
}How Modifier Classes Work Across Tiers
Modifier classes (.primary, .secondary, etc.) can target any tier to control the scope of their effect:
Override System Tokens → affects all children of the element
.primary {
/* Affects all children */
--background-color: var(--primary-background-color);
}Override Component Tokens → affects all children, instances of a component
.primary {
/* Affects all children that are a Card component */
--card-background-color: var(--primary-background-color);
}Override Individual Tokens → affects the specific element itself
.primary {
/* Affects the element itself if it is a Card component */
--_card-background-color: var(--primary-background-color);
}The 4-tier cascade means no combinatorial explosion — .ghost works with any intent class without separate blocks for .ghost.primary, .ghost.secondary, etc.
Property Name Rules
Tokens at Tiers 1-3 must use CSS longhand property names:
| ✓ Do this | ✖ Not this | Because |
|---|---|---|
--background-color | --background | background resets image, position, etc. |
--border-color | --border | border resets width and style |
--border-width | --border-size | CSS property is border-width |
--outline-width | --outline-size | CSS property is outline-width |
Genuine Exceptions
| Token | Reason |
|---|---|
--spacing | Responsive value used for margins and padding throughout the page |
--color-hover-shade | Internal helper color mixed into base colors via color-mix() to derive hover-state variants — not a standalone property value |
State Ordering
State always comes last:
--buttons-background-color-hover
--details-summary-color-open
--inputs-background-color-focusSpacing Tokens
Use spacing as the property segment:
--spacing /* global density */
--typography-margin-block /* block margins */
--inputs-padding-block /* form padding */
--buttons-padding-block
--details-dropdown-padding-blockCascade-Seed Tokens
Tokens on :root that propagate via inheritance use the CSS property name:
--font-size /* seeds rem calculations */
--line-height /* inherited by all text */
--font-weight /* inherited baseline */
--text-underline-offsetMigration from v2.2.0 to v3.0.0
| Old (v2.2.0) | New (v3.0.0) | Notes |
|---|---|---|
--color-primary-fill | --primary-background-color | fill → background-color |
--color-primary-text | --primary-color | text → color |
--color-primary-focus-ring | --primary-outline-color | Property-mapped |
--color-background | --background-color | Global, no --color- wrapper |
--color-text | --color | Global text |
--color-text-muted | --color-muted | Muted variant |
--color-border | --border-color | Global border |
--dialog-fill | --dialog-background-color | Component + property |
--input-border-focus | --inputs-border-color-focus | State at end |
--switch-thumb-glow | --input-switch-thumb-box-shadow | Property name |
--loading-spinner-opacity | removed | Unused |
--shadow | --_buttons-box-shadow / --_inputs-box-shadow | Scoped private tokens |
--button-* | --buttons-* | Pluralized |
--input-* | --inputs-* | Pluralized |
--h1-gap-top | --h1-margin-top | Property-mapped |
--dialog-section-* | --dialog-marginals-* | Renamed |
--menu-* | --details-menu-* | Scoped under details |
--pane-* | --dialog-* | Consolidated |
--range-* | --input-range-* | Scoped under inputs |
--switch-* | --input-switch-* | Scoped under inputs |
--search-* | --input-search-* | Scoped under inputs |
--checkbox-* | --input-checkbox-* | Scoped under inputs |
--progress-background-color | --progress-track-background-color | Property-mapped |