Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 12 additions & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -551,7 +551,18 @@ jobs:
- test-build-start-apps-edge
- test-build-start-apps-edge-entry
- test-rsc
if: always()
if: >-
always() && !(
needs.test-dev-base.result == 'skipped' &&
needs.test-build-start-base.result == 'skipped' &&
needs.test-build-start-base-edge.result == 'skipped' &&
needs.test-build-start-base-edge-entry.result == 'skipped' &&
needs.test-dev-apps.result == 'skipped' &&
needs.test-build-start-apps.result == 'skipped' &&
needs.test-build-start-apps-edge.result == 'skipped' &&
needs.test-build-start-apps-edge-entry.result == 'skipped' &&
needs.test-rsc.result == 'skipped'
)
runs-on: ubuntu-latest
steps:
- name: Checkout
Expand Down
190 changes: 188 additions & 2 deletions docs/src/pages/en/(pages)/integrations/mantine.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,198 @@
title: Mantine UI
category: Integrations
order: 5
contents: false
---

import Link from "../../../../components/Link.jsx";

# Mantine UI

> Coming soon.
`@lazarv/react-server` is compatible with [Mantine](https://mantine.dev/), a full-featured React component library. You can use Mantine components in your client components with server-side rendering support, PostCSS configuration for Mantine's styling system, and the `MantineProvider` for theming.

<Link name="installation">
## Installation
</Link>

Install Mantine and its required PostCSS dependencies:

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

<Link name="postcss-configuration">
## PostCSS configuration
</Link>

Mantine requires a PostCSS configuration with the `postcss-preset-mantine` plugin and breakpoint variables:

```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",
},
},
},
};
```

<Link name="provider-setup">
## Provider setup
</Link>

Import the core Mantine styles and wrap your app with `MantineProvider` in your root layout. Include the `ColorSchemeScript` in the `<head>` to prevent a flash of unstyled content:

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

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

const theme = createTheme({
/** Put your mantine theme override here */
});

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>
);
}
```

<Link name="using-components">
## Using components
</Link>

Mantine components that use React hooks or browser APIs must be used in client components. Create a client component and import the Mantine components you need:

```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>
);
}
```

Then use the client component from your server component page:

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

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

<Link name="navigation">
## Navigation
</Link>

To use Mantine's navigation components like `NavLink` with `@lazarv/react-server`'s client-side navigation, pass the framework's `Link` component via the `component` prop:

```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"}
/>
</>
);
}
```

<Link name="extension-packages">
## Extension packages
</Link>

Mantine offers many extension packages for additional functionality. Import their styles in the pages or layouts where they are used:

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

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

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

Some commonly used Mantine extensions and their style imports:

| Package | Style import |
|---------|-------------|
| `@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` |

<Link name="client-only-components">
## Client-only components
</Link>

Some components (like charts that depend on browser APIs) cannot be server-side rendered. Use `ClientOnly` from `@lazarv/react-server/client` to render them only on the client:

```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>
);
}
```

> Check out the [Mantine example](https://github.com/lazarv/react-server/tree/main/examples/mantine) to see a complete example of using Mantine UI with `@lazarv/react-server`.

166 changes: 164 additions & 2 deletions docs/src/pages/en/(pages)/integrations/mui.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,174 @@
title: Material UI
category: Integrations
order: 6
contents: false
---

import Link from "../../../../components/Link.jsx";

# Material UI

> Coming soon.
`@lazarv/react-server` is compatible with [Material UI (MUI)](https://mui.com/material-ui/), a popular React component library implementing Google's Material Design. MUI uses Emotion for CSS-in-JS styling, which works out of the box with `@lazarv/react-server`.

<Link name="installation">
## Installation
</Link>

Install Material UI and its required dependencies:

```sh
pnpm add @mui/material @emotion/react @emotion/styled
```

Optionally, install the Roboto font and Material Icons:

```sh
pnpm add @fontsource/roboto @mui/icons-material
```

<Link name="theme-setup">
## Theme setup
</Link>

Create a theme file to configure your Material UI theme:

```js filename="app/theme.mjs"
import { createTheme } from "@mui/material/styles";

const theme = createTheme({
palette: {
mode: "light",
},
typography: {
fontFamily: "Roboto",
},
});

export default theme;
```

<Link name="provider-setup">
## Provider setup
</Link>

Material UI requires a `ThemeProvider` and `CssBaseline` for proper theming and baseline styles. Create a client component that wraps your app:

```jsx filename="app/components/Layout.jsx"
"use client";

import Container from "@mui/material/Container";
import CssBaseline from "@mui/material/CssBaseline";
import { ThemeProvider } from "@mui/material/styles";

import theme from "../theme";

export default function Layout({ children }) {
return (
<ThemeProvider theme={theme}>
<CssBaseline />
<Container maxWidth="lg">
{children}
</Container>
</ThemeProvider>
);
}
```

Then set up your root layout to import the font and use the `Layout` provider component:

```jsx filename="app/layout.jsx"
import "@fontsource/roboto/300.css";
import "@fontsource/roboto/400.css";
import "@fontsource/roboto/500.css";
import "@fontsource/roboto/700.css";

import Layout from "./components/Layout";

export default function RootLayout({ children }) {
return (
<html lang="en" suppressHydrationWarning>
<head>
<meta charSet="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>My App</title>
</head>
<body suppressHydrationWarning>
<Layout>{children}</Layout>
</body>
</html>
);
}
```

<Link name="navigation">
## Navigation
</Link>

To use MUI link and button components with `@lazarv/react-server`'s client-side navigation, pass the framework's `Link` component via the `component` prop:

```jsx filename="app/page.jsx"
"use client";

import { Link as ReactServerLink } from "@lazarv/react-server/navigation";
import Link from "@mui/material/Link";

export default function Home() {
return (
<Link to="/about" color="secondary" component={ReactServerLink}>
Go to the about page
</Link>
);
}
```

The same pattern works with MUI `Button` for navigation:

```jsx filename="app/about/page.jsx"
"use client";

import { Link as ReactServerLink } from "@lazarv/react-server/navigation";
import Button from "@mui/material/Button";

export default function About() {
return (
<Button to="/" component={ReactServerLink}>
Go to the home page
</Button>
);
}
```

<Link name="server-components">
## Server components
</Link>

Some MUI components that don't rely on browser APIs or React hooks can be used directly in server components. Components like `Typography` and `Link` (without navigation) work in server components:

```jsx filename="app/components/Copyright.jsx"
import Typography from "@mui/material/Typography";
import Link from "@mui/material/Link";

export default function Copyright() {
return (
<Typography variant="body2" color="text.secondary" align="center">
{"Copyright © "}
<Link color="inherit" href="https://mui.com/">
Your Website
</Link>{" "}
{new Date().getFullYear()}.
</Typography>
);
}
```

<Link name="icons">
## Icons
</Link>

When using `@mui/icons-material`, import icons from the ESM path for proper module resolution:

```jsx
import LightbulbOutlined from "@mui/icons-material/esm/LightbulbOutlined";
```

> Check out the [Material UI example](https://github.com/lazarv/react-server/tree/main/examples/mui) to see a complete example of using MUI with `@lazarv/react-server`.

Loading