# Mantine UI

`@lazarv/react-server`は、フル機能のReactコンポーネントライブラリである[Mantine](https://mantine.dev/)と互換性があります。クライアントコンポーネントでMantineコンポーネントを使用し、サーバーサイドレンダリングのサポート、MantineのスタイリングシステムのためのPostCSS設定、テーマのための`MantineProvider`を利用できます。

## インストール

Mantineと必要なPostCSS依存関係をインストールします:

```sh
pnpm add @mantine/core @mantine/hooks
pnpm add -D postcss postcss-preset-mantine postcss-simple-vars
```

## PostCSS設定

Mantineには`postcss-preset-mantine`プラグインとブレークポイント変数を含むPostCSS設定が必要です:

```js filename="postcss.config.cjs"
module.exports = {
  plugins: {
    "postcss-preset-mantine": {},
    "postcss-simple-vars": {
      variables: {
        "mantine-breakpoint-xs": "36em",
        "mantine-breakpoint-sm": "48em",
        "mantine-breakpoint-md": "62em",
        "mantine-breakpoint-lg": "75em",
        "mantine-breakpoint-xl": "88em",
      },
    },
  },
};
```

## プロバイダーのセットアップ

コアMantineスタイルをインポートし、ルートレイアウトで`MantineProvider`でアプリをラップします。スタイルなしコンテンツのフラッシュを防ぐために、``に`ColorSchemeScript`を含めます:

```tsx filename="src/pages/layout.tsx"
import "@mantine/core/styles.css";

import { ColorSchemeScript, createTheme, MantineProvider } from "@mantine/core";

const theme = createTheme({
  /** Mantineのテーマオーバーライドをここに記述 */
});

export default function Layout({ children }: { children: React.ReactNode }) {
  return (
    <html lang="en" data-mantine-color-scheme="light" suppressHydrationWarning>
      <head>
        <ColorSchemeScript />
      </head>
      <body suppressHydrationWarning>
        <MantineProvider theme={theme}>
          {children}
        </MantineProvider>
      </body>
    </html>
  );
}
```

## コンポーネントの使用

ReactフックやブラウザAPIを使用するMantineコンポーネントは、クライアントコンポーネントで使用する必要があります。クライアントコンポーネントを作成し、必要なMantineコンポーネントをインポートします:

```tsx filename="src/components/Counter.tsx"
"use client";

import { useState } from "react";
import { Button, Group, Text } from "@mantine/core";

export function Counter() {
  const [count, setCount] = useState(0);

  return (
    <Group>
      <Button onClick={() => setCount((c) => c - 1)}>-</Button>
      <Text>{count}</Text>
      <Button onClick={() => setCount((c) => c + 1)}>+</Button>
    </Group>
  );
}
```

次に、サーバーコンポーネントページからクライアントコンポーネントを使用します:

```tsx filename="src/pages/index.tsx"
import { Counter } from "../components/Counter";

export default function HomePage() {
  return <Counter />;
}
```

## ナビゲーション

`@lazarv/react-server`のクライアントサイドナビゲーションでMantineの`NavLink`などのナビゲーションコンポーネントを使用するには、`component`プロップを介してランタイムの`Link`コンポーネントを渡します:

```tsx filename="src/components/MainNavigation.tsx"
"use client";

import { NavLink } from "@mantine/core";
import { Link, usePathname } from "@lazarv/react-server/navigation";

export function MainNavigation() {
  const pathname = usePathname();

  return (
    <>
      <NavLink
        component={Link}
        to="/"
        label="Home"
        active={pathname === "/"}
      />
      <NavLink
        component={Link}
        to="/about"
        label="About"
        active={pathname === "/about"}
      />
    </>
  );
}
```

## 拡張パッケージ

Mantineは追加機能のための多くの拡張パッケージを提供しています。使用するページやレイアウトでスタイルをインポートします:

```tsx filename="src/pages/dates.tsx"
import "@mantine/dates/styles.css";

import { MyDates } from "../components/MyDates";

export default function DatesPage() {
  return <MyDates />;
}
```

よく使われるMantine拡張パッケージとそのスタイルインポート:

| パッケージ | スタイルインポート |
|---------|-------------|
| `@mantine/dates` | `@mantine/dates/styles.css` |
| `@mantine/charts` | `@mantine/charts/styles.css` |
| `@mantine/notifications` | `@mantine/notifications/styles.css` |
| `@mantine/code-highlight` | `@mantine/code-highlight/styles.css` |
| `@mantine/carousel` | `@mantine/carousel/styles.css` |
| `@mantine/spotlight` | `@mantine/spotlight/styles.css` |
| `@mantine/nprogress` | `@mantine/nprogress/styles.css` |
| `@mantine/tiptap` | `@mantine/tiptap/styles.css` |
| `@mantine/dropzone` | `@mantine/dropzone/styles.css` |

## クライアント専用コンポーネント

一部のコンポーネント（ブラウザAPIに依存するチャートなど）はサーバーサイドレンダリングができません。`@lazarv/react-server/client`の`ClientOnly`を使用して、クライアントでのみレンダリングします:

```tsx filename="src/pages/charts.tsx"
import "@mantine/charts/styles.css";

import { ClientOnly } from "@lazarv/react-server/client";
import { MyAreaChart } from "../components/MyAreaChart";

export default function ChartsPage() {
  return (
    <ClientOnly>
      <MyAreaChart />
    </ClientOnly>
  );
}
```

> `@lazarv/react-server`でMantine UIを使用する完全な例については、[Mantine example](https://github.com/lazarv/react-server/tree/main/examples/mantine)を確認してください。