theming
Tailwind CSS v4 introduces a CSS-first theming model. Design tokens live in your CSS file, not a JavaScript config. This makes customisation faster, more explicit, and aligned with the CSS custom properties ecosystem.
How Tailwind v4 theming works
In Tailwind v4, the @theme directive defines your design
tokens as CSS custom properties. Tailwind reads these properties and automatically generates
the corresponding utility classes. No JavaScript configuration is needed.
Tailwind v3 (old way)
// tailwind.config.js
module.exports = {
theme: {
extend: {
colors: {
brand: '#6366F1',
},
},
},
}Tailwind v4 (new way)
/* global.css */
@import "tailwindcss";
@theme {
--color-brand: #6366F1;
}
/* bg-brand, text-brand, etc.
are now available! */Customising your colour palette
Replace or extend the default Tailwind palette by defining colour tokens in the @theme block. Use any valid CSS colour format —
hex, RGB, HSL, or the modern oklch() space for
perceptually uniform colours.
@import "tailwindcss";
@theme {
/* Override a default colour */
--color-indigo-500: #6366F1;
/* Add entirely new colours */
--color-brand-50: oklch(97% 0.02 250);
--color-brand-500: oklch(60% 0.20 250);
--color-brand-900: oklch(30% 0.15 250);
/* Semantic colours */
--color-success: oklch(65% 0.18 145);
--color-danger: oklch(60% 0.22 25);
}indigo-50
indigo-100
indigo-200
indigo-400
indigo-500
indigo-600
indigo-700
indigo-900
Default indigo palette included with Tailwind v4.
Typography tokens
Override font families, sizes, weights, and line-heights using the same @theme approach.
/* styles/global.css */
@import "tailwindcss";
@theme {
/* Font families */
--font-sans: 'Inter', 'system-ui', sans-serif;
--font-mono: 'JetBrains Mono', 'Fira Code', monospace;
--font-display: 'Cal Sans', 'Inter', sans-serif;
/* Custom font sizes */
--text-2xs: 0.625rem; /* 10px */
--text-3xl: 1.875rem; /* 30px */
/* Line heights */
--leading-tighter: 1.15;
}
After defining --font-sans, use it as font-sans in your Tailwind class names. The
same applies to all other token categories.
Spacing and border-radius
@theme {
/* Custom spacing scale additions */
--spacing-18: 4.5rem;
--spacing-22: 5.5rem;
/* Border radii */
--radius-sm: 0.25rem;
--radius-md: 0.5rem;
--radius-lg: 0.75rem;
--radius-xl: 1rem;
--radius-2xl: 1.5rem;
--radius-full: 9999px;
}
Dark mode
Tailwind v4 supports dark mode via the dark: variant. Configure the strategy in your CSS:
@import "tailwindcss";
/* Use class-based dark mode (add 'dark' class to <html>) */
@variant dark (&:where(.dark, .dark *));
@layer base {
:root {
--bg-page: 255 255 255;
--text-primary: 17 24 39;
}
.dark {
--bg-page: 15 23 42;
--text-primary: 248 250 252;
}
}
/* Usage in components: */
/* <div class="bg-white dark:bg-slate-900 text-gray-900 dark:text-slate-100"> */
To toggle dark mode, add or remove the dark class on the
<html> element. You can do this with a small React hook
that reads from localStorage or the OS preference via
window.matchMedia('(prefers-color-scheme: dark)').
CSS layers
Tailwind v4 uses native CSS @layer for cascade
control. The three built-in layers are:
| Layer | Purpose | Example |
|---|---|---|
| base | Element-level defaults and resets | h1 { @apply text-3xl } |
| components | Reusable class abstractions | .btn { @apply px-4 py-2 } |
| utilities | Single-purpose helper classes | .text-balance { text-wrap: balance } |