FSM Full Stack Masterclass
Platform under construction
CSS course badge

Cascade & Control

Intermediate

CSS Variables

CSS Variables, officially custom properties, let you store reusable values in CSS and let those values participate in the cascade.

:root { --accent: #8cffc1; }
.button { color: var(--accent); }

Cascade & Control

CSS Variables turn repeated values into a controllable design system.

A CSS custom property starts with two dashes, such as --color-accent. You read it with var(--color-accent).

Custom properties are not simple search-and-replace constants. They cascade and inherit, which means their value can change depending on where they are defined.

This makes them excellent for color systems, spacing scales, component themes and responsive adjustments. Used well, variables make CSS more coherent and easier to redesign.

Declaration

--accent: #8cffc1 defines a reusable value.

Usage

color: var(--accent) reads that value.

Fallback

var(--accent, hotpink) uses fallback if the variable is missing.

Scope

Variables can be global on :root or local inside a component.

Visual model

Control CSS by understanding the browser decision path.

The browser does not apply styles emotionally. It follows a priority system. These diagrams make that priority visible before you start changing declarations.

01

:root

Global design tokens such as colors and spacing.

02

.theme-dark

Theme overrides can redefine the same variable.

03

.card

Components consume variables without knowing the exact value.

04

var()

The browser resolves the current value at computed-value time.

Examples

Write CSS that wins for a reason.

Tokenized and themeable CSS

:root {
  --surface: #101827;
  --text: #f7f9ff;
  --accent: #8cffc1;
}

.card {
  background: var(--surface);
  color: var(--text);
}

.card a {
  color: var(--accent);
}

Repeated values with no system

.card { background: #101827; color: #f7f9ff; }
.hero { background: #101827; color: #f7f9ff; }
.button { background: #8cffc1; }
.link { color: #8cffc1; }

Rules that matter

Control comes from reducing surprise.

CSS becomes easier when every override has a reason. If a rule wins by accident, the next developer has to debug your intention instead of the code.

Use meaningful names

--color-accent is better than --green if the color may change later.

Start with :root tokens

Global brand, spacing and typography values usually belong on :root.

Scope component variables locally

A component can define --card-bg or --button-bg for easy variants.

Use fallbacks where helpful

var(--accent, #8cffc1) prevents missing variables from breaking the value.

Do not over-abstract everything

A variable for every one-off value makes CSS harder to read.

Remember cascade and inheritance

Variables can change by context, which is powerful and sometimes surprising.

Production thinking

The cascade is architecture, not trivia.

Why does this matter?

Variables make CSS feel like a design system rather than a pile of declarations. They let a redesign change a few values instead of hunting through the whole stylesheet.

Accessibility

Variables are useful for maintaining contrast pairs. Store text and background values together so themes do not accidentally become unreadable.

Production note

Production design systems often use custom properties for tokens, themes, component options and responsive values.

SEO note

Variables do not directly affect SEO, but they help keep visual quality consistent across many pages and reduce maintenance errors.

Live code lab

Change the CSS and watch the interface respond.

The preview runs in an isolated iframe. Links and forms stay inside the practice area, so you can experiment without leaving the lesson.

Mini assignment

Try this now.

  • Change --accent in .theme-premium and run the preview.
  • Remove the local --surface override and see the card inherit the root value.
  • Add a fallback to one var() call.

Practice assignment

Do this before moving to the next lesson.

  1. Create five variables for a small design system.
  2. Use at least three of them inside a component.
  3. Override one variable locally to create a variant.

Try it yourself

Build a tiny theme with CSS Variables

Live preview

Self-check

Before you continue, prove that you understand CSS Variables.

Intermediate

Answer these questions before moving on. If the answer is vague, inspect the lab example and trace which declaration wins.

  1. Can you write and use a custom property with var()?
  2. Can you explain why variables are affected by cascade and inheritance?
  3. Can you choose semantic variable names instead of color-name names?
  4. Can you use a fallback value in var()?
  5. Can you decide when a value should not become a variable?

Senior audit upgrade

Custom properties are live, scoped and inherited.

CSS variables are not preprocessor constants. They are resolved by the browser at computed-value time and can change by scope, state and media query.

Scope

A variable defined on .card is available to descendants of that card, not globally.

Fallbacks

var(--x, fallback) only helps when --x is missing or invalid at computed time.

@property

Typed custom properties can define syntax, inheritance and initial values for advanced animation and safety.

@property --angle {
  syntax: '<angle>';
  inherits: false;
  initial-value: 0deg;
}

Chapter project

Debug a cascade conflict

Trace which rule wins, reduce specificity pressure and move repeated values into custom properties.

Build

a controlled component variant system without random overrides

Deliverables

  • cascade conflict example
  • specificity cleanup
  • custom-property based variant

Quality checks

  • no ID arms race
  • no unexplained !important
  • winning rule can be explained

Review question

Can you explain exactly why the final declaration wins?