@gfazioli/mantine-split-pane
Version:
A Mantine 9 React component for resizable split pane layouts with 7 resizer variants, context-based prop inheritance, responsive orientation, and dynamic pane generation.
224 lines (172 loc) • 6.98 kB
Markdown
# Mantine Split Pane Component
<img alt="Mantine Split Pane" src="https://github.com/gfazioli/mantine-split-pane/blob/master/logo.jpeg" />
<div align="center">
[](https://www.npmjs.com/package/@gfazioli/mantine-split-pane)
[](https://www.npmjs.com/package/@gfazioli/mantine-split-pane)
[](https://www.npmjs.com/package/@gfazioli/mantine-split-pane)

---
[<kbd> <br/> ❤️ If this component has been useful to you or your team, please consider becoming a sponsor <br/> </kbd>](https://github.com/sponsors/gfazioli?o=esc)
</div>
## Overview
A Mantine 9 React component for resizable split pane layouts with 7 resizer variants, context-based prop inheritance, responsive orientation, and dynamic pane generation.
This component is created on top of the [Mantine](https://mantine.dev/) library.
It requires **Mantine 9.x** and **React 19**.
> [!note]
>
> → [Demo and Documentation](https://gfazioli.github.io/mantine-split-pane/) → [Youtube Video](https://www.youtube.com/playlist?list=PL85tTROKkZrWyqCcmNCdWajpx05-cTal4) → [More Mantine Components](https://mantine-extensions.vercel.app/)
## Features
- Separate `Split.Pane` (content) and `Split.Resizer` (drag handle) architecture
- 7 resizer variants: `default`, `filled`, `outline`, `transparent`, `gradient`, `dotted`, `dashed`
- Initial sizes in pixels or percentages with min/max constraints
- `grow` property to let specific panes expand to fill available space
- Horizontal and vertical orientation, including responsive breakpoints
- Context-based prop inheritance: resizer props set on `Split` cascade to all children
- Per-resizer overrides for full control
- Snap points for common pane sizes during drag and keyboard resizing
- `autoResizers` mode to automatically insert resizers between panes
- `Split.Dynamic` helper to generate panes from a configuration array
- Resize lifecycle events (`onResizeStart`, `onResizing`, `onResizeEnd`) on both pane and resizer — fired on drag, keyboard resize, and double-click reset
- Custom content inside `Split.Resizer` for drag-affordance icons, labels, or fully bespoke handles
- Keyboard accessible: focusable resizer with configurable `step` and `shiftStep`
- Container resize tracking with drag ratio preservation
## Installation
```sh
npm install @gfazioli/mantine-split-pane
```
or
```sh
yarn add @gfazioli/mantine-split-pane
```
After installation import package styles at the root of your application:
```tsx
import '@gfazioli/mantine-split-pane/styles.css';
```
## Usage
```tsx
import { Split } from '@gfazioli/mantine-split-pane';
import { Paper } from '@mantine/core';
function Demo() {
return (
<Split>
<Split.Pane>
<Paper withBorder w="100%" mih="100%">
<h1>Pane 1</h1>
</Paper>
</Split.Pane>
<Split.Resizer />
<Split.Pane>
<Paper withBorder>
<h1>Pane 2</h1>
</Paper>
</Split.Pane>
</Split>
);
}
```
### Auto Resizers
Use the `autoResizers` prop to automatically insert resizers between panes:
```tsx
import { Split } from '@gfazioli/mantine-split-pane';
import { Paper } from '@mantine/core';
function Demo() {
return (
<Split autoResizers>
<Split.Pane>
<Paper withBorder w="100%" mih="100%">
<h1>Pane 1</h1>
</Paper>
</Split.Pane>
<Split.Pane>
<Paper withBorder>
<h1>Pane 2</h1>
</Paper>
</Split.Pane>
<Split.Pane>
<Paper withBorder>
<h1>Pane 3</h1>
</Paper>
</Split.Pane>
</Split>
);
}
```
### Snap Points
Use `snapPoints` and `snapTolerance` to snap a resizer to common pane sizes in pixels while dragging or using the keyboard:
```tsx
import { Split } from '@gfazioli/mantine-split-pane';
import { Paper } from '@mantine/core';
function Demo() {
return (
<Split autoResizers snapPoints={[200, 400, 600]} snapTolerance={20}>
<Split.Pane initialWidth={240}>
<Paper withBorder w="100%" mih="100%">
<h1>Pane 1</h1>
</Paper>
</Split.Pane>
<Split.Pane initialWidth={320}>
<Paper withBorder w="100%" mih="100%">
<h1>Pane 2</h1>
</Paper>
</Split.Pane>
<Split.Pane grow>
<Paper withBorder w="100%" mih="100%">
<h1>Pane 3</h1>
</Paper>
</Split.Pane>
</Split>
);
}
```
`snapPoints` and `snapTolerance` are also available on `Split.Resizer` for per-divider overrides. With `autoResizers`, the generated resizers inherit these values from `Split`.
### Dynamic Panes
You can also use `Split.Dynamic` to create panes from a configuration array:
```tsx
import { Split, PaneConfig } from '@gfazioli/mantine-split-pane';
import { Paper } from '@mantine/core';
function Demo() {
const panes: PaneConfig[] = [
{
id: 'sidebar',
initialWidth: 200,
minWidth: 150,
content: (
<Paper withBorder w="100%" h="100%">
<h1>Sidebar</h1>
</Paper>
),
},
{
id: 'main',
grow: true,
content: (
<Paper withBorder w="100%" h="100%">
<h1>Main Content</h1>
</Paper>
),
},
];
return (
<Split>
{Split.Dynamic({ panes })}
</Split>
);
}
```
## Sponsor
<div align="center">
[<kbd> <br/> ❤️ If this component has been useful to you or your team, please consider becoming a sponsor <br/> </kbd>](https://github.com/sponsors/gfazioli?o=esc)
</div>
Your support helps me:
- Keep the project actively maintained with timely bug fixes and security updates
- Add new features, improve performance, and refine the developer experience
- Expand test coverage and documentation for smoother adoption
- Ensure long-term sustainability without relying on ad hoc free time
- Prioritize community requests and roadmap items that matter most
Open source thrives when those who benefit can give back—even a small monthly contribution makes a real difference. Sponsorships help cover maintenance time, infrastructure, and the countless invisible tasks that keep a project healthy.
Your help truly matters.
💚 [Become a sponsor](https://github.com/sponsors/gfazioli?o=esc) today and help me keep this project reliable, up-to-date, and growing for everyone.
---
https://github.com/user-attachments/assets/2e45af2b-60c7-4cb3-9b9a-6cf0e710af1c
---
[](https://www.star-history.com/#gfazioli/mantine-split-pane&Timeline)