Skip to content

Styling

There are many ways to make your Next.js app look good. This page covers the four most popular ones - from simple to powerful. You don’t have to use all of them. Pick what makes sense for your project.

Here’s a quick overview before we dive in:

MethodBest for
Global StylesBasic rules that apply to your whole app
CSS ModulesStyles that only affect one specific component
Tailwind CSSStyling quickly without leaving your JSX
DaisyUIReady-made components built on Tailwind

Global styles are CSS rules that apply to your entire app - every page, every component. Think of it like setting the default font and background color for your whole house before decorating individual rooms.

In Next.js, your global styles live in app/globals.css. This file is already imported for you in app/layout.tsx.

/* app/globals.css */
/* Set defaults for the whole app */
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
body {
font-family: Arial, sans-serif;
background-color: #f9f9f9;
color: #333;
}
h1 {
font-size: 2rem;
font-weight: bold;
}
a {
color: #0070f3;
text-decoration: none;
}
a:hover {
text-decoration: underline;
}

CSS Modules let you write styles for one specific component without worrying about them breaking other parts of your app.

The trick is simple: name your file something.module.css. Next.js will make sure those styles only apply to the component that imports them.

Here’s an example - a card component with its own styles:

/* components/ui/card.module.css */
.card {
background: white;
border: 1px solid #e0e0e0;
border-radius: 8px;
padding: 1.5rem;
box-shadow: 0 2px 6px rgba(0, 0, 0, 0.08);
}
.title {
font-size: 1.25rem;
font-weight: 600;
margin-bottom: 0.5rem;
}
.description {
color: #666;
font-size: 0.95rem;
}
// components/ui/card.tsx
import styles from "./card.module.css";
type CardProps = { title: string; description: string };
export default function Card({ title, description }: CardProps) {
return (
<div className={styles.card}>
<h2 className={styles.title}>{title}</h2>
<p className={styles.description}>{description}</p>
</div>
);
}
// app/page.tsx
import Card from "@/components/ui/card";
export default function Home() {
return (
<main style={{ padding: "2rem" }}>
<Card
title="Welcome to Next.js"
description="This card is styled with CSS Modules - its styles won't leak into other components."
/>
</main>
);
}

Tailwind is a different way of writing styles. Instead of creating a separate CSS file, you add small utility classes directly in your JSX. Each class does one thing - p-4 adds padding, text-blue-500 makes text blue, rounded-lg adds rounded corners.

It sounds messy at first, but once you get used to it, it’s very fast.

Set up Tailwind:

Terminal window
bun add tailwindcss @tailwindcss/postcss postcss

Add this to app/globals.css:

/* app/globals.css */
@import "tailwindcss";

That’s it - Tailwind is ready.

Example - a profile card using Tailwind:

// components/ui/profile-card.tsx
type ProfileCardProps = { name: string; role: string; avatarUrl: string };
export default function ProfileCard({ name, role, avatarUrl }: ProfileCardProps) {
return (
<div className="bg-white border border-gray-200 rounded-xl p-6 shadow-sm flex items-center gap-4">
<img src={avatarUrl} alt={name} className="w-16 h-16 rounded-full object-cover" />
<div>
<h2 className="text-lg font-semibold text-gray-800">{name}</h2>
<p className="text-sm text-gray-500">{role}</p>
</div>
</div>
);
}
// app/page.tsx
import ProfileCard from "@/components/ui/profile-card";
export default function Home() {
return (
<main className="min-h-screen bg-gray-50 flex items-center justify-center p-8">
<ProfileCard name="Sarah Johnson" role="Frontend Developer" avatarUrl="https://i.pravatar.cc/150?img=47" />
</main>
);
}

DaisyUI is a plugin for Tailwind that gives you ready-made components - buttons, cards, alerts, modals, and more - all styled and ready to use. Instead of building everything from scratch with Tailwind classes, you just use class names like btn, card, or alert.

Set up DaisyUI:

Terminal window
bun add daisyui

Add DaisyUI to your globals.css:

/* app/globals.css */
@import "tailwindcss";
@plugin "daisyui";

Example - a sign-up card using DaisyUI:

// app/sign-up/page.tsx
export default function SignUpPage() {
return (
<main className="min-h-screen bg-base-200 flex items-center justify-center">
<div className="card bg-base-100 shadow-xl w-full max-w-sm">
<div className="card-body">
<h2 className="card-title text-2xl">Create an account</h2>
<p className="text-base-content/60 text-sm">It's free and always will be.</p>
<div className="form-control mt-2">
<label className="label">
<span className="label-text">Your name</span>
</label>
<input type="text" placeholder="John Smith" className="input input-bordered" />
</div>
<div className="form-control">
<label className="label">
<span className="label-text">Email address</span>
</label>
<input type="email" placeholder="john@example.com" className="input input-bordered" />
</div>
<div className="form-control mt-4">
<button className="btn btn-primary w-full">Sign Up</button>
</div>
<p className="text-center text-sm text-base-content/60 mt-2">
Already have an account?{" "}
<a href="/sign-in" className="link link-primary">
Sign in
</a>
</p>
</div>
</div>
</main>
);
}

Changing the theme:

DaisyUI comes with 30+ built-in themes. You can switch them in globals.css:

/* app/globals.css */
@import "tailwindcss";
@plugin "daisyui" {
themes:
light --default,
dark --prefersdark,
cupcake;
}

Now your app supports light, dark, and cupcake themes out of the box - including automatic dark mode for users who have it turned on in their OS.

You don’t have to pick just one. Most Next.js projects use a mix:

Global Styles -> fonts, colors, resets
Tailwind CSS -> layout and spacing
DaisyUI -> buttons, forms, cards
CSS Modules -> one-off custom components

A good starting point for most projects is Tailwind + DaisyUI. You get speed and flexibility from Tailwind, and ready-made polished components from DaisyUI.