In an attempt to keep up with the fast paced changes in CSS here are the most significant updates over the past few years. Starting with 2020.
JUMP TO:
1. CSS Grid
2. prefers-color-scheme
3. The popularity of Tailwind
1. CSS GRID

HTML
<div class="grid">
<header>Header</header>
<nav>Nav</nav>
<main>Main content</main>
<aside>Sidebar</aside>
<footer>Footer</footer>
</div>
CSS
.grid {
display: grid;
/* 1️⃣ Define columns and rows */
grid-template-columns: 200px 1fr 150px;
grid-template-rows: auto 1fr auto;
/* 2️⃣ Name layout areas */
grid-template-areas:
"header header header"
"nav main aside"
"footer footer footer";
/* 3️⃣ Spacing between items */
gap: 1rem;
min-height: 100vh;
}
/* 4️⃣ Assign elements to areas */
header { grid-area: header; }
nav { grid-area: nav; }
main { grid-area: main; }
aside { grid-area: aside; }
footer { grid-area: footer; }
/* Just styling so it’s visible */
.grid > * {
padding: 1rem;
background: #eaeaea;
border: 1px solid #ccc;
}
/* Responsive Design */
@media (max-width: 600px) {
.grid {
grid-template-areas:
"header"
"nav"
"main"
"aside"
"footer";
grid-template-columns: 1fr;
}
}
What this example shows (important features)
1️⃣ Grid container
display: grid;
Turns the .grid div into a grid layout.
2️⃣ Columns & rows
grid-template-columns: 200px 1fr 150px;
grid-template-rows: auto 1fr auto;
px→ fixed widthfr→ “take remaining space”auto→ size to content
3️⃣ Named grid areas (very powerful)
grid-template-areas:
"header header header"
"nav main aside"
"footer footer footer";
This visually describes the layout in CSS.
You can rearrange the whole layout just by changing these lines.
4️⃣ Placing items by name
header { grid-area: header; }
No row/column numbers needed — much more readable.
5️⃣ Gaps
gap: 1rem;
Replaces old hacks like margins for spacing grid items.
Why Grid is useful (vs Flexbox)
- Grid → 2-dimensional (rows and columns)
- Flexbox → 1-dimensional (row or column)
This example would be awkward in Flexbox but clean in Grid.
2. prefers-color-scheme


prefers-color-scheme is a media query that lets your CSS respond to the user’s OS or browser theme preference:
lightdark
The browser decides this based on system settings (macOS, Windows, iOS, Android).
HTML (unchanged for both themes)
<div class="card">
<h1>Hello</h1>
<p>This page adapts to your system theme.</p>
<button>Click me</button>
</div>
CSS
/* 1️⃣ Default (light theme fallback) */
:root {
--bg: #ffffff;
--text: #222222;
--card: #f4f4f4;
--accent: #0066cc;
}
body {
background: var(--bg);
color: var(--text);
font-family: system-ui, sans-serif;
padding: 2rem;
}
.card {
background: var(--card);
padding: 2rem;
border-radius: 8px;
max-width: 400px;
}
button {
background: var(--accent);
color: white;
border: none;
padding: 0.6rem 1rem;
border-radius: 4px;
}
/* 2️⃣ Dark mode overrides */
@media (prefers-color-scheme: dark) {
:root {
--bg: #0f172a;
--text: #e5e7eb;
--card: #1e293b;
--accent: #60a5fa;
}
}
What this example demonstrates
1️⃣ Media query, not a class
@media (prefers-color-scheme: dark)
- No JavaScript
- No
.darkclass - Automatically responds to system setting changes
2️⃣ CSS variables (best practice)
:root {
--bg: #ffffff;
}
Instead of duplicating all styles, we:
- define variables once
- override them in dark mode
This keeps CSS clean and scalable.
3️⃣ Light mode as a fallback
/* default styles first */
If a browser doesn’t support prefers-color-scheme, users still get light mode.
4️⃣ Instant theme switching
Try changing:
- macOS → System Settings → Appearance
- Windows → Personalization → Colors
The page updates without reload.
Common patterns in real projects
Combine with color-scheme
html {
color-scheme: light dark;
}
This tells the browser to:
- theme form controls
- scrollbars
- built-in UI correctly
Support only dark mode users
@media (prefers-color-scheme: dark) {
body {
background: black;
}
}
Force a theme (overrides system)
body.force-light {
--bg: white;
}
Useful if you later add a user toggle.
Other user-preference media queries.
All of these belong to the same family:
| Media query | What it respects |
|---|---|
prefers-color-scheme | Light / dark theme |
prefers-reduced-motion | Less animation |
prefers-contrast | More / less contrast |
prefers-reduced-transparency | Less transparency |
They:
- read OS / browser accessibility settings
- require no JavaScript
- update live when the system setting changes
3. The popularity of Tailwind
Tailwind CSS is a utility-first CSS framework.
Instead of writing custom CSS classes, you compose your UI directly in HTML using small, single-purpose classes.
<button class="bg-blue-600 text-white px-4 py-2 rounded">
Save
</button>
Each class maps to one CSS rule:
bg-blue-600→ background colorpx-4→ horizontal paddingrounded→ border radius
You rarely write traditional CSS at all.
How does this differ from the BEM approach?
What BEM is:
BEM (Block-Element-Modifier) is not a framework.
It’s a naming convention and architecture for writing CSS.
<button class="button button--primary">
Save
</button>
.button {
padding: 1rem;
border-radius: 6px;
}
.button--primary {
background: blue;
color: white;
}
BEM helps you:
- structure large CSS codebases
- avoid selector conflicts
- understand relationships between components
Core difference
Tailwind replaces most custom CSS.
BEM organizes custom CSS.
They’re solving different layers of the problem.
Side-by-side comparison
| Aspect | Tailwind CSS | BEM |
|---|---|---|
| Type | CSS framework | Naming methodology |
| Where styles live | Mostly in HTML | Mostly in CSS |
| CSS you write | Minimal | Primary |
| Naming responsibility | Tailwind handles naming | You design names |
| Learning curve | Medium (many utilities) | Low–medium |
| File size | Generated & purged | Grows with project |
| Best for | Rapid UI development | Long-term CSS architecture |
Example: same button, different approach
Tailwind
<button class="bg-blue-600 hover:bg-blue-700 text-white px-4 py-2 rounded transition">
Save
</button>
No CSS file needed.
BEM
<button class="btn btn--primary">
Save
</button>
.btn {
padding: 0.5rem 1rem;
border-radius: 0.5rem;
transition: background 200ms;
}
.btn--primary {
background: blue;
color: white;
}
.btn--primary:hover {
background: darkblue;
}
How they scale
Tailwind scaling model
- Reuse comes from copying patterns
- Consistency comes from design tokens
- Changes are fast and local
<div class="max-w-md mx-auto p-6 bg-white shadow-lg rounded-lg">
BEM scaling model
- Reuse comes from shared components
- Consistency comes from discipline
- Changes are centralized but slower
.card {}
.card__header {}
.card__body {}
.card--featured {}
Mental model difference
Tailwind
“Describe how it looks, right here, right now.”
BEM
“Describe what this thing is, and style it elsewhere.”
Common criticisms
Tailwind critics say:
- HTML becomes cluttered
- Harder to read at first
- Requires a build step
BEM critics say:
- Boilerplate-heavy
- Lots of class names
- CSS files grow large over time
Both are valid — it depends on context.
Can they be used together?
Yes — and often they are.
Example:
<button class="btn bg-blue-600 text-white px-4 py-2">
btn→ semantic hook (BEM-ish)- Tailwind → actual styling
This is common in WordPress and React projects.
When Tailwind is a good fit
- Component-based apps (React, Vue)
- Design systems
- Teams that want speed + consistency
- You want fewer CSS files
When BEM is a good fit
- Traditional multi-page sites
- CMS-driven sites (WordPress, Drupal)
- Teams that prefer semantic HTML
- Long-lived projects with lots of CSS

Leave a Reply