# Tailwind CSS Customization
Config file structure, custom utilities, plugins, and theme extensions.
## @theme Directive
Modern approach to customize Tailwind using CSS:
```css
@import "tailwindcss";
@theme {
/* Custom colors */
--color-brand-50: oklch(0.97 0.02 264);
--color-brand-500: oklch(0.55 0.22 264);
--color-brand-900: oklch(0.25 0.15 264);
/* Custom fonts */
--font-display: "Satoshi", "Inter", sans-serif;
--font-body: "Inter", system-ui, sans-serif;
/* Custom spacing */
--spacing-18: calc(var(--spacing) * 18);
--spacing-navbar: 4.5rem;
/* Custom breakpoints */
--breakpoint-3xl: 120rem;
--breakpoint-tablet: 48rem;
/* Custom shadows */
--shadow-glow: 0 0 20px rgba(139, 92, 246, 0.3);
/* Custom radius */
--radius-large: 1.5rem;
}
```
**Usage:**
```html
Custom themed element
Custom breakpoints
```
## Color Customization
### Custom Color Palette
```css
@theme {
/* Full color scale */
--color-primary-50: oklch(0.98 0.02 250);
--color-primary-100: oklch(0.95 0.05 250);
--color-primary-200: oklch(0.90 0.10 250);
--color-primary-300: oklch(0.85 0.15 250);
--color-primary-400: oklch(0.75 0.18 250);
--color-primary-500: oklch(0.65 0.22 250);
--color-primary-600: oklch(0.55 0.22 250);
--color-primary-700: oklch(0.45 0.20 250);
--color-primary-800: oklch(0.35 0.18 250);
--color-primary-900: oklch(0.25 0.15 250);
--color-primary-950: oklch(0.15 0.10 250);
}
```
### Semantic Colors
```css
@theme {
--color-success: oklch(0.65 0.18 145);
--color-warning: oklch(0.75 0.15 85);
--color-error: oklch(0.60 0.22 25);
--color-info: oklch(0.65 0.18 240);
}
```
```html
Success message
Error state
```
## Typography Customization
### Custom Fonts
```css
@theme {
--font-sans: "Inter", system-ui, sans-serif;
--font-serif: "Merriweather", Georgia, serif;
--font-mono: "JetBrains Mono", Consolas, monospace;
--font-display: "Playfair Display", serif;
}
```
```html
Display heading
Body text
Code block
```
### Custom Font Sizes
```css
@theme {
--font-size-xs: 0.75rem;
--font-size-sm: 0.875rem;
--font-size-base: 1rem;
--font-size-lg: 1.125rem;
--font-size-xl: 1.25rem;
--font-size-2xl: 1.5rem;
--font-size-3xl: 1.875rem;
--font-size-4xl: 2.25rem;
--font-size-5xl: 3rem;
--font-size-jumbo: 4rem;
}
```
## Spacing Customization
```css
@theme {
/* Add custom spacing values */
--spacing-13: calc(var(--spacing) * 13);
--spacing-15: calc(var(--spacing) * 15);
--spacing-18: calc(var(--spacing) * 18);
/* Named spacing */
--spacing-header: 4rem;
--spacing-footer: 3rem;
--spacing-section: 6rem;
}
```
```html
Custom padding
```
## Custom Utilities
Create reusable utility classes:
```css
@utility content-auto {
content-visibility: auto;
}
@utility tab-* {
tab-size: var(--tab-size-*);
}
@utility glass {
background: rgba(255, 255, 255, 0.1);
backdrop-filter: blur(10px);
border: 1px solid rgba(255, 255, 255, 0.2);
}
```
**Usage:**
```html
Optimized rendering
Code with 4-space tabs
Glassmorphism effect
```
## Custom Variants
Create custom state variants:
```css
@custom-variant theme-midnight (&:where([data-theme="midnight"] *));
@custom-variant aria-checked (&[aria-checked="true"]);
@custom-variant required (&:required);
```
**Usage:**
```html
Applies in midnight theme
```
## Layer Organization
Organize CSS into layers:
```css
@layer base {
h1 {
@apply text-4xl font-bold tracking-tight;
}
h2 {
@apply text-3xl font-semibold;
}
a {
@apply text-blue-600 hover:text-blue-700 underline-offset-4 hover:underline;
}
body {
@apply bg-background text-foreground antialiased;
}
}
@layer components {
.btn {
@apply px-4 py-2 rounded-lg font-medium transition-colors;
}
.btn-primary {
@apply bg-blue-600 text-white hover:bg-blue-700;
}
.btn-secondary {
@apply bg-gray-200 text-gray-900 hover:bg-gray-300;
}
.card {
@apply bg-white rounded-xl shadow-md p-6 hover:shadow-lg transition-shadow;
}
.input {
@apply w-full px-4 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-transparent;
}
}
@layer utilities {
.text-balance {
text-wrap: balance;
}
.scrollbar-hide {
-ms-overflow-style: none;
scrollbar-width: none;
}
.scrollbar-hide::-webkit-scrollbar {
display: none;
}
}
```
## @apply Directive
Extract repeated utility patterns:
```css
.btn-primary {
@apply bg-blue-600 hover:bg-blue-700 active:bg-blue-800 text-white font-semibold px-6 py-3 rounded-lg shadow-md hover:shadow-lg transition-all duration-200 focus:outline-none focus:ring-4 focus:ring-blue-300;
}
.input-field {
@apply w-full px-4 py-2 border border-gray-300 rounded-md focus:outline-none focus:ring-2 focus:ring-blue-500 focus:border-transparent disabled:bg-gray-100 disabled:cursor-not-allowed;
}
.section-container {
@apply container mx-auto px-4 sm:px-6 lg:px-8 max-w-7xl;
}
```
**Usage:**
```html
Content
```
## Plugins
### Official Plugins
```bash
npm install -D @tailwindcss/typography @tailwindcss/forms @tailwindcss/container-queries
```
```javascript
// tailwind.config.js
export default {
plugins: [
require('@tailwindcss/typography'),
require('@tailwindcss/forms'),
require('@tailwindcss/container-queries'),
],
}
```
**Typography plugin:**
```html
Styled article
Automatically styled prose content
```
**Forms plugin:**
```html
```
### Custom Plugin
```javascript
// tailwind.config.js
const plugin = require('tailwindcss/plugin')
export default {
plugins: [
plugin(function({ addUtilities, addComponents, theme }) {
// Add utilities
addUtilities({
'.text-shadow': {
textShadow: '2px 2px 4px rgba(0, 0, 0, 0.1)',
},
'.text-shadow-lg': {
textShadow: '4px 4px 8px rgba(0, 0, 0, 0.2)',
},
})
// Add components
addComponents({
'.card-custom': {
backgroundColor: theme('colors.white'),
borderRadius: theme('borderRadius.lg'),
padding: theme('spacing.6'),
boxShadow: theme('boxShadow.md'),
},
})
}),
],
}
```
## Configuration Examples
### Complete Tailwind Config
```javascript
// tailwind.config.ts
import type { Config } from 'tailwindcss'
const config: Config = {
darkMode: ["class"],
content: [
'./pages/**/*.{ts,tsx}',
'./components/**/*.{ts,tsx}',
'./app/**/*.{ts,tsx}',
],
theme: {
container: {
center: true,
padding: "2rem",
screens: {
"2xl": "1400px",
},
},
extend: {
colors: {
border: "hsl(var(--border))",
input: "hsl(var(--input))",
ring: "hsl(var(--ring))",
background: "hsl(var(--background))",
foreground: "hsl(var(--foreground))",
primary: {
DEFAULT: "hsl(var(--primary))",
foreground: "hsl(var(--primary-foreground))",
},
brand: {
50: '#f0f9ff',
500: '#3b82f6',
900: '#1e3a8a',
},
},
fontFamily: {
sans: ['Inter', 'system-ui', 'sans-serif'],
display: ['Playfair Display', 'serif'],
},
spacing: {
'18': '4.5rem',
'88': '22rem',
'128': '32rem',
},
borderRadius: {
lg: "var(--radius)",
md: "calc(var(--radius) - 2px)",
sm: "calc(var(--radius) - 4px)",
},
keyframes: {
"slide-in": {
"0%": { transform: "translateX(-100%)" },
"100%": { transform: "translateX(0)" },
},
},
animation: {
"slide-in": "slide-in 0.5s ease-out",
},
},
},
plugins: [require("tailwindcss-animate")],
}
export default config
```
## Dark Mode Configuration
```javascript
// tailwind.config.js
export default {
darkMode: ["class"], // or "media" for automatic
// ...
}
```
**Usage:**
```html
Responds to .dark class
Responds to system preference automatically
```
## Content Configuration
Specify files to scan for classes:
```javascript
// tailwind.config.js
export default {
content: [
"./src/**/*.{js,jsx,ts,tsx}",
"./app/**/*.{js,jsx,ts,tsx}",
"./components/**/*.{js,jsx,ts,tsx}",
"./pages/**/*.{js,jsx,ts,tsx}",
],
// ...
}
```
### Safelist
Preserve dynamic classes:
```javascript
export default {
safelist: [
'bg-red-500',
'bg-green-500',
'bg-blue-500',
{
pattern: /bg-(red|green|blue)-(100|500|900)/,
},
],
}
```
## Best Practices
1. **Use @theme for simple customizations**: Prefer CSS-based customization
2. **Extract components sparingly**: Use @apply only for truly repeated patterns
3. **Leverage design tokens**: Define custom tokens in @theme
4. **Layer organization**: Keep base, components, and utilities separate
5. **Plugin for complex logic**: Use plugins for advanced customizations
6. **Test dark mode**: Ensure custom colors work in both themes
7. **Document custom utilities**: Add comments explaining custom classes
8. **Semantic naming**: Use descriptive names (primary not blue)