はじめに
本記事では Next.js (App Router) で Radix と Tailwind CSS が動作するところまでをまとめました。 pnpm を使っているので、npm や yarn を使っている場合は適宜読み替えてください。
記載時の各ライブラリのバージョンや環境
Next.js のプロジェクトを作成
pnpm create next-app
以下のように質問されるので、回答します。
✔ What is your project named? … my-next-app
✔ Would you like to use TypeScript? … Yes
✔ Would you like to use ESLint? … Yes
✔ Would you like to use Tailwind CSS? … Yes
✔ Would you like to use `src/` directory? … No
✔ Would you like to use App Router? (recommended) … Yes
✔ Would you like to customize the default import alias (@/*)? … No
Radix をインストール
pnpm add @radix-ui/themes
globals.css を変更する
app/globals.css を以下のように変更します。
@tailwind base;
@tailwind components;
@tailwind utilities;
@import "@radix-ui/themes/styles.css"
layout.tsx を変更する
app/layout.tsx を以下のように変更します。
追加したのは、@radix-ui/themes
の Theme コンポーネントです。
import type { Metadata } from "next";
import { Inter } from "next/font/google";
import "./globals.css";
import { Theme } from "@radix-ui/themes"
const inter = Inter({ subsets: ["latin"] });
export const metadata: Metadata = {
title: "Create Next App",
description: "Generated by create next app",
};
export default function RootLayout({
children,
}: Readonly<{
children: React.ReactNode;
}>) {
return (
<html lang="en">
<body className={inter.className}>
<Theme>{children}</Theme>
</body>
</html>
);
}
[Optional] Radix Themes の Token を Tailwind CSS の Class として使えるようにする
例えば、以下のように Radix Themes で定義されている Token を Tailwind CSS の Class として使いたい場合に有効です。
<button className="bg-accent-9 px-rx-2">Click Me 😘</Button>
radix-themes-tw をインストールします
pnpm add -D radix-themes-tw
tailwind.config.js を変更します
tailwind.config.ts を以下のように変更します。
import type { Config } from "tailwindcss"
import { radixThemePreset } from "radix-themes-tw"
const config: Config = {
presets: [radixThemePreset],
content: [
"./components/**/*.{js,ts,jsx,tsx,mdx}",
"./app/**/*.{js,ts,jsx,tsx,mdx}",
],
}
export default config
client component への対応
Dialog コンポーネントを使う場合、以下のようなエラーが発生することがあります。
Unhandled Runtime Error
Error: Could not find the module "/Users/path/to/project/node_modules/.pnpm/@radix-ui+themes@2.0.3_@types+react-dom@18.2.19_@types+react@18.2.58_react-dom@18.2.0_react@18.2.0/node_modules/@radix-ui/themes/dist/esm/components/dialog.js#Dialog#Root" in the React Client Manifest. This is probably a bug in the React Server Components bundler.
Dialog コンポーネントは Client Component として ‘use client’ directive を使用する必要がありますが、Dialog コンポーネント自体には ‘use client’ directive が含まれていないことが原因です。
今回は、元の使用感を変えないために以下のように対応しました。
components 配下に client.tsx と index.tsx を作成します
components/
└── dialog
├── client.tsx
└── index.tsx
client.tsx
"use client"
import { Dialog } from "@radix-ui/themes"
const Root = Dialog.Root
const Trigger = Dialog.Trigger
const Content = Dialog.Content
const Title = Dialog.Title
const Description = Dialog.Description
const Close = Dialog.Close
export { Root, Trigger, Content, Title, Description, Close }
index.tsx
import {
Root,
Trigger,
Content,
Title,
Description,
Close,
} from "@/components/dialog/client"
export const Dialog = {
Root,
Trigger,
Content,
Title,
Description,
Close,
}
このようにすることで、Server Components から直接 Dialog をコンポーネントを使うことができます。
app/path/to/page.tsx
import { Dialog } from "@/components/dialog"
export default function Home() {
return (
<Dialog.Root>
<Dialog.Trigger>
<Button variant="solid" color="blue">
Edit profile
</Button>
</Dialog.Trigger>
<Dialog.Content style={{ maxWidth: 450 }}>
<Dialog.Title>Edit profile</Dialog.Title>
<Dialog.Description size="2" mb="4">
Make changes to your profile.
</Dialog.Description>
</Dialog.Content>
</Dialog.Root>
)
};
できなかったこと
特定条件で Tailwind CSS の button, [type='button']
に対する Reset CSS が Radix の Button コンポーネントの background-color
よりも優先されるため、背景色があたらないケースがあります。
Dialog の Trigger などで、type="button"
を付与された場合に発生します。
radix-ui/primitives/Dialog.tsx での実装箇所
パッと対応方法がわからなかったので何かわかれば追記します