Modern CSS includes advanced techniques and tools that make websites easier to build, maintain, scale, and reuse. These features improve developer productivity and help create cleaner, more efficient code.
In this lesson, we'll cover:
CSS Variables (also called Custom Properties) allow you to store reusable values that can be used throughout your stylesheet.
Instead of repeating the same value multiple times, define it once and reuse it everywhere.
Without Variables
.button {
background: #2563EB;
}
.card {
border-color: #2563EB;
}
.link {
color: #2563EB;
}
If the primary color changes, every occurrence must be updated manually.
With Variables
:root {
--primary-color: #2563EB;
}
.button {
background: var(--primary-color);
}
.card {
border-color: var(--primary-color);
}
.link {
color: var(--primary-color);
}
Now the color only needs to be changed in one place.
:root {
--primary-color: blue;
}
h1 {
color: var(--primary-color);
}
:root {
--primary: #2563EB;
--secondary: #9333EA;
--text-color: #333333;
--radius: 12px;
}
If a variable doesn't exist, a fallback value can be used.
color: var(--primary, blue);
:root {
--bg: white;
--text: black;
}
.dark {
--bg: #111827;
--text: white;
}
Changing variables automatically updates the entire theme.
CSS Functions allow calculations and dynamic styling directly inside CSS.
Accesses a CSS Variable.
background: var(--primary);
Performs mathematical calculations.
width: calc(100% - 50px);
Example
.main {
height: calc(100vh - 80px);
}
Meaning:
Viewport Height
-
Navbar Height
Returns the smaller value.
width: min(100%, 1200px);
Returns the larger value.
width: max(300px, 50%);
The most useful modern CSS function for responsive values.
clamp(
minimum,
preferred,
maximum
)
Example
font-size: clamp(
1rem,
5vw,
3rem
);
Result:
| Function | Purpose |
|---|---|
var() |
Access CSS Variables |
calc() |
Perform calculations |
min() |
Choose smaller value |
max() |
Choose larger value |
clamp() |
Responsive values |
url() |
Load external assets |
CSS Modules solve the problem of global CSS conflicts.
They are commonly used with:
File 1
.title {
color: blue;
}
File 2
.title {
color: red;
}
Both classes share the same name, causing conflicts.
Button.module.css
.title {
color: blue;
}
React Component
import styles from "./Button.module.css";
<h1 className={styles.title}>
Hello
</h1>
The browser generates a unique class name.
Example
.title_x7a92
This prevents naming conflicts.
BEM stands for:
It is a CSS naming convention used in large projects.
Poor naming becomes difficult to maintain.
Bad examples:
.title
.button
.card
These names are too generic.
block
block__element
block--modifier
<div class="card">
<h2 class="card__title">
Product
</h2>
</div>
<button class="button button--primary">
Save
</button>
.button {
padding: 10px;
}
.button--primary {
background: blue;
}
Sass (Syntactically Awesome Style Sheets) is a CSS preprocessor that adds powerful features to CSS.
npm install sass
$primary: #2563EB;
.button {
background: $primary;
}
Regular CSS
.nav {}
.nav a {}
Sass
.nav {
a {
color: white;
}
}
Reusable groups of CSS.
@mixin center {
display: flex;
justify-content: center;
align-items: center;
}
Use
.hero {
@include center;
}
PostCSS is a tool that processes CSS using plugins.
Workflow
CSS
↓
PostCSS Plugins
↓
Optimized CSS
Automatically adds browser prefixes.
Input
.card {
display: flex;
}
Output
.card {
display: -webkit-flex;
display: flex;
}
PostCSS can also support nested CSS.
.card {
h2 {
color: blue;
}
}
Tailwind CSS uses PostCSS internally to generate optimized production CSS.
CSS-in-JS allows you to write CSS directly inside JavaScript.
It is popular in React applications.
const Button = styled.button`
background: blue;
color: white;
`;
<div
css={{
color: "blue"
}}
>
Hello
</div>
Styles can change based on JavaScript values.
const Button = styled.button`
background:
${props =>
props.primary
? "blue"
: "gray"};
`;
| Library | Common Usage |
|---|---|
| Styled Components | React |
| Emotion | React |
| Stitches | React |
| Panda CSS | Modern CSS-in-JS |
| CSS Modules | CSS-in-JS |
|---|---|
| Separate CSS File | CSS Inside JavaScript |
| Faster Runtime | More Dynamic |
| Simpler | More Powerful |
| Great for Most Apps | Great for Complex Apps |
Traditional
HTML
+
CSS
Modern
React
↓
CSS Modules
↓
PostCSS
↓
Production CSS
Enterprise Applications
React
↓
TypeScript
↓
CSS Modules
or
CSS-in-JS
↓
PostCSS
CSS Variables
:root {
--primary: #2563EB;
}
Card
.card {
background: white;
border-radius: 12px;
padding: 20px;
}
Responsive Typography
h1 {
font-size: clamp(
2rem,
5vw,
4rem
);
}
Modern Layout
.container {
display: grid;
grid-template-columns: repeat(3, 1fr);
gap: 20px;
}
| Topic | Purpose |
|---|---|
| CSS Variables | Store reusable values |
| CSS Functions | Dynamic styling and calculations |
| CSS Modules | Scoped CSS |
| BEM | Naming methodology |
| Sass | CSS Preprocessor |
| PostCSS | CSS Processing Tool |
| CSS-in-JS | Write CSS inside JavaScript |
Modern CSS development focuses on reusable, responsive, and maintainable code.
Example:
:root {
--primary: #2563EB;
}
h1 {
font-size: clamp(
2rem,
5vw,
4rem
);
}
Modern websites commonly combine:
CSS Variables
+
Flexbox
+
Grid
+
CSS Modules
+
PostCSS
↓
Scalable & Maintainable Modern CSS
While all of these tools are valuable, CSS Variables, Flexbox, Grid, and PostCSS are the most widely used in modern frontend development. Frameworks like React and Next.js often build upon these technologies to create large, maintainable applications.