Resizable
A split-pane layout arranging Resizable.Panel and Resizable.Handle parts along a shared axis.
One
Two
Three
View code
// A session per group, since each one drags along its own axis.
let rowSession = new ResizeSession();
let columnSession = new ResizeSession();
<Resizable aria-label="Layout panes" data-resizable-group>
<Resizable.Panel
id="one"
defaultSize={50}
minSize={25}
data-resizable-panel
data-resizable-min="25"
mix={[center(), weight("semibold")]}
>
One
</Resizable.Panel>
<Resizable.Handle
aria-label="Resize the first pane"
aria-controls="one stack"
data-resizable-handle
mix={[resizeHandle("horizontal", rowSession)]}
/>
<Resizable.Panel id="stack" defaultSize={50} minSize={25} data-resizable-panel>
{/* A group nested in a panel splits that panel along the other axis; the
frame around it is the outer group's, so this one draws none of its own. */}
<Resizable
orientation="vertical"
aria-label="Stacked panes"
data-resizable-group
style={{ border: "none", borderRadius: "0" }}
mix={[bs("100%")]}
>
<Resizable.Panel
id="two"
defaultSize={25}
minSize={15}
data-resizable-panel
data-resizable-min="15"
mix={[center(), weight("semibold")]}
>
Two
</Resizable.Panel>
<Resizable.Handle
aria-label="Resize the upper pane"
aria-controls="two three"
data-resizable-handle
mix={[resizeHandle("vertical", columnSession)]}
/>
<Resizable.Panel
id="three"
defaultSize={75}
minSize={15}
data-resizable-panel
data-resizable-min="15"
mix={[center(), weight("semibold")]}
>
Three
</Resizable.Panel>
</Resizable>
</Resizable.Panel>
</Resizable>Installation
An ordinary dependency: install it, import the theme once, and import the component where it is used.
npm add @sdxc/uiimport "@sdxc/ui/theme.css";Usage
import { Resizable } from "@sdxc/ui";Renders the root host: a <div> laying Resizable.Panel and
Resizable.Handle children out in a row, or a column when
orientation is "vertical", sharing the resolved axis through context; set aria-disabled="true" to dim the whole group.
Composition
The parts the component publishes, each a static property of the host.
ResizableResizable.PanelRenders a single pane: a<div>that grows and shrinks to fill its share of the group's main axis, clipping overflow with scrolling.Resizable.HandleRenders a draggable divider between two adjacent panels: arole="separator"<div>reachable in Tab order, its bar darkening on hover and ready for&[data-resizing]to color it during a drag.
Examples
<Resizable orientation="vertical" aria-label={t("layout.panes")}>
<Resizable.Panel defaultSize={60}>{t("layout.top")}</Resizable.Panel>
<Resizable.Handle aria-label={t("layout.resizeVertically")} />
<Resizable.Panel defaultSize={40}>{t("layout.bottom")}</Resizable.Panel>
</Resizable>Props
Read from the component's own types, so every prop, every default and every allowed value is listed.
| Prop | Type | Description |
|---|---|---|
orientation? | "horizontal" | "vertical" | Layout axis. Defaults to DEFAULT_ORIENTATION. |
Also accepts everything in TagProps<"div">.
Resizable.Panel
| Prop | Type | Description |
|---|---|---|
defaultSize? | number | Starting share of the group's main axis, as a percentage (e.g. 30 for 30%). Panels left without one split whatever share remains evenly among themselves. |
minSize? | number | Smallest share of the group's main axis this panel will shrink to, as a percentage. Left unset, the panel can shrink down to nothing. |
maxSize? | number | Largest share of the group's main axis this panel will grow to, as a percentage. Left unset, the panel can grow up to the group's entire main axis. |
Also accepts everything in TagProps<"div">.
Resizable.Handle
Also accepts everything in TagProps<"div">.
Types
| Name | Values | What it decides |
|---|---|---|
Orientation | "horizontal" | "vertical" | Axis the panels lay out along: a row of panels side by side, or a column of panels stacked one above another. |