目次
TL;DR
- Tailwind CSS v4 では設定方法が **JavaScript(
tailwind.config.js)から CSS(@theme)**に移行した @configでの JS ファイル参照はまだ使えるが、今後廃止予定@themeディレクティブで カラー・フォント・ブレークポイント などをすべてCSS内で定義できる- カスタム CSS は必ず 適切な
@layerに配置する必要がある
はじめに
Tailwind CSS v4 は、v3 からのメジャーアップデートで設計思想に大きな変化があった。最も目立つ変更は CSS-first configuration、つまり設定を JavaScript ファイルからCSS内で完結させるアプローチへの転換だ。
この記事では、実際に自分のポートフォリオサイト(Astro製)を v3 → v4 に移行した際の変更点をまとめる。
1. パッケージの変更
v3
{
"dependencies": {
"tailwindcss": "^3.x",
"@astrojs/tailwind": "^x.x"
}
}
v4
{
"dependencies": {
"tailwindcss": "^4.x",
"@tailwindcss/vite": "^4.x"
}
}
v4 では Astro 公式の Tailwind インテグレーション(@astrojs/tailwind)の代わりに、Vite プラグイン(@tailwindcss/vite)を直接使う形になった。
// astro.config.mjs
import tailwindcss from "@tailwindcss/vite";
export default defineConfig({
vite: {
plugins: [tailwindcss()],
},
});
2. CSSエントリーポイントの変更
v3
@tailwind base;
@tailwind components;
@tailwind utilities;
v4
@import "tailwindcss";
たった1行になった。@import "tailwindcss" が内部で CSS Cascade Layers(@layer theme, base, components, utilities)を確立し、すべてのユーティリティを提供する。
3. tailwind.config.js → @theme
v3: JavaScript で設定
// tailwind.config.mjs
export default {
content: ["./src/**/*.{astro,html,js,jsx,md,mdx,svelte,ts,tsx,vue}"],
theme: {
colors: {
"primary-green": "#18ef95",
"primary-blue": "#13aed0",
white: "#ffffff",
black: "#000000",
// ...
},
},
plugins: [],
};
v4: CSS で設定
@import "tailwindcss";
@theme {
--color-*: initial; /* デフォルトカラーをクリア */
--color-primary-green: #18ef95;
--color-primary-blue: #13aed0;
--color-white: #ffffff;
--color-black: #000000;
--font-shippori: "Shippori Antique B1";
--font-comfortaa: "Comfortaa Variable";
--font-averia: "Averia Serif Libre";
}
@theme ディレクティブ内で CSS カスタムプロパティ の形式で定義する。命名規則は以下の通り:
| 設定項目 | v3 の書き方 | v4 の書き方 |
|---|---|---|
| カラー | theme.colors["primary-green"] | --color-primary-green |
| フォント | theme.fontFamily.sans | --font-sans |
| ブレークポイント | theme.screens.md | --breakpoint-md |
| スペーシング | theme.spacing[4] | --spacing (自動計算) |
ポイント:--color-*: initial の意味
v4 にはデフォルトで大量のカラー(red-500, blue-300 など)が組み込まれている。--color-*: initial を指定すると、デフォルトカラーをすべてクリアして自分が定義したカラーだけにできる。使わないカラーのCSSが生成されないので、バンドルサイズの削減にもなる。
4. カスタムユーティリティクラスの定義
v3
.font-shippori {
font-family: "Shippori Antique B1";
}
v4
@theme でフォントを定義すれば、font-shippori クラスが自動生成される:
@theme {
--font-shippori: "Shippori Antique B1";
}
<!-- 自動的に使える -->
<h1 class="font-shippori">見出し</h1>
手動でユーティリティクラスを書く必要がなくなった。
5. カスタムCSSと @layer の関係(最重要)
v4 で最もハマりやすいのがこの点。**別記事(CSS Cascade Layers の落とし穴)**で詳しく解説しているが、ここでも概要を示す。
NG パターン
@import "tailwindcss";
/* レイヤー外 → 全ユーティリティを上書きしてしまう! */
* {
padding: 0;
margin: 0;
}
html {
font-family: "Zen Kaku Gothic New";
}
OK パターン
@import "tailwindcss";
@layer base {
* {
padding: 0;
margin: 0;
}
html {
font-family: "Zen Kaku Gothic New";
}
}
CSS Cascade Layers の仕様上、レイヤー外のスタイルはすべてのレイヤーに優先する。そのため、@import "tailwindcss" と同じファイル内のカスタムCSSは必ず @layer 内に配置する必要がある。
6. content の指定が不要に
v3 では tailwind.config.js の content フィールドで、Tailwind がスキャンすべきファイルを明示的に指定する必要があった:
content: ["./src/**/*.{astro,html,js,jsx,md,mdx,svelte,ts,tsx,vue}"],
v4 では、ソースファイルの自動検出が行われる。Vite プラグイン経由で使用している場合、モジュールグラフからクラス名を自動的に収集するため、content の設定は基本的に不要になった。
7. 移行手順のまとめ
- パッケージ更新:
tailwindcssv4 +@tailwindcss/viteをインストール - Astro 設定変更:
@astrojs/tailwind→ Vite プラグインに切り替え - CSS エントリーポイント:
@tailwind base/components/utilities→@import "tailwindcss" - 設定の CSS 化:
tailwind.config.jsのテーマ設定を@themeに移植 - カスタム CSS の修正: レイヤー外のCSS を
@layer baseに移動 @config参照の削除: JS 設定ファイルが不要なら削除- ビルド確認: 各ページの見た目を確認
8. 公式アップグレードツール
Tailwind CSS は公式のアップグレードツールを提供している:
npx @tailwindcss/upgrade
これを実行すると、多くの変更を自動的に処理してくれるが、カスタムCSSの @layer 配置は自動では行われないケースがある。特に * セレクタや html/body へのスタイリングはレイヤー外に残りがちなので、手動で確認が必要。
おわりに
Tailwind CSS v4 の CSS-first approach は、JavaScript 設定ファイルの管理が不要になり、CSS の世界だけで完結するという点で開発体験が向上した。一方で、CSS Cascade Layers への理解が必要になるため、移行時には「今まで動いていたCSS」が突然壊れるケースがある。
特に * { padding: 0; } のような誰もが書くリセットCSSが最大の破壊者になるという点は、知らないとデバッグに相当な時間を費やすことになるだろう。この記事が移行のお役に立てば幸いです。