How to use
Drawer is a slide-in panel from any edge of the viewport — filters, notifications, a details view opened from a table row. It's built on the same overlay stack, focus-trapping, and backdrop machinery as Modal, so the two behave consistently and stack correctly together; the difference is purely presentational (an edge-anchored panel instead of a centered box).
import { Drawer, Button } from "oks-ui";Same controlled shape as Modal: you own isOpen, onClose fires from every dismissal path (backdrop click, Escape, the header close button).
function NotificationsDrawer() {
const [isOpen, setIsOpen] = useState(false);
return (
<>
<Button variant="ghost" onPress={() => setIsOpen(true)}>Notifications</Button>
<Drawer isOpen={isOpen} onClose={() => setIsOpen(false)} title="Notifications" position="right">
<NotificationsList />
</Drawer>
</>
);
}position picks the edge it slides in from (left, right, top, bottom — right is the default). width applies to left/right drawers, height to top/bottom ones; both accept the usual token scale or a raw string/number for an exact size.
<Drawer isOpen={isOpen} onClose={onClose} position="left" width="320px" title="Filters">
<FilterForm />
</Drawer>
<Drawer isOpen={isOpen} onClose={onClose} position="bottom" height="60%" title="Details">
<DetailsPanel />
</Drawer>Same three-slot shape as Modal — title for the header, children for the body, actions for the footer. Any of the three can be omitted independently.
<Drawer
isOpen={isOpen}
onClose={onClose}
title="Edit item"
actions={
<>
<Button variant="soft" onPress={onClose}>Cancel</Button>
<Button color="primary" onPress={handleSave}>Save</Button>
</>
}
>
<ItemForm />
</Drawer>Because Drawer shares Modal's overlay stack, opening a Drawer from inside an already-open Modal (or vice versa) layers correctly without any manual z-index coordination, and Escape only dismisses the topmost overlay.
All available props for Drawer. See the full component page for an interactive playground.
| Prop | Type | Default | Description |
|---|---|---|---|
title | ReactNode | — | Header title. |
children | ReactNode | — | Body content. |
actions | ReactNode | — | Footer action buttons. |
title
ReactNode
Default: —
Header title.
children
ReactNode
Default: —
Body content.
actions
ReactNode
Default: —
Footer action buttons.
| Prop | Type | Default | Description |
|---|---|---|---|
blur | boolean | "sm" | "md" | "lg" | number | — | Backdrop blur amount. |
backgroundOpacity | number | — | Backdrop opacity (0-100). |
blur
boolean | "sm" | "md" | "lg" | number
Default: —
Backdrop blur amount.
backgroundOpacity
number
Default: —
Backdrop opacity (0-100).
| Prop | Type | Default | Description |
|---|---|---|---|
position | "left" | "right" | "top" | "bottom" | right | Edge the drawer slides in from. |
width | "xs" | "sm" | "md" | "lg" | "xl" | "full" | string | number | "420px" | Panel width, for left/right positions. |
height | "xs" | "sm" | "md" | "lg" | "xl" | "full" | string | number | "360px" | Panel height, for top/bottom positions. |
portal | boolean | true | Renders through a React portal. |
container | Element | DocumentFragment | null | — | Custom portal mount target. |
zIndex | number | — | Explicit stacking z-index; auto-computed when unset. |
position
"left" | "right" | "top" | "bottom"
Default: right
Edge the drawer slides in from.
width
"xs" | "sm" | "md" | "lg" | "xl" | "full" | string | number
Default: "420px"
Panel width, for left/right positions.
height
"xs" | "sm" | "md" | "lg" | "xl" | "full" | string | number
Default: "360px"
Panel height, for top/bottom positions.
portal
boolean
Default: true
Renders through a React portal.
container
Element | DocumentFragment | null
Default: —
Custom portal mount target.
zIndex
number
Default: —
Explicit stacking z-index; auto-computed when unset.
| Prop | Type | Default | Description |
|---|---|---|---|
isOpen | boolean | — | Controls whether the drawer is open (required). |
ariaLabel | string | "Drawer" | Accessible name for the drawer region. |
dismissible | boolean | true | Shows a close button in the header. |
closeLabel | string | "Close drawer" | Accessible label for the close button. |
closeOnOutsideClick | boolean | true | Closes on backdrop click. |
closeOnEscape | boolean | true | Closes on Escape. |
initialFocusRef | RefObject<HTMLElement | null> | — | Element to focus when the drawer opens. |
isOpen
boolean
Default: —
Controls whether the drawer is open (required).
ariaLabel
string
Default: "Drawer"
Accessible name for the drawer region.
dismissible
boolean
Default: true
Shows a close button in the header.
closeLabel
string
Default: "Close drawer"
Accessible label for the close button.
closeOnOutsideClick
boolean
Default: true
Closes on backdrop click.
closeOnEscape
boolean
Default: true
Closes on Escape.
initialFocusRef
RefObject<HTMLElement | null>
Default: —
Element to focus when the drawer opens.
| Prop | Type | Default | Description |
|---|---|---|---|
animationDuration | number | — | Enter/exit animation duration in seconds. |
easing | "ease" | "easeIn" | "easeOut" | "easeInOut" | — | Animation easing curve. |
animationDuration
number
Default: —
Enter/exit animation duration in seconds.
easing
"ease" | "easeIn" | "easeOut" | "easeInOut"
Default: —
Animation easing curve.
| Prop | Type | Default | Description |
|---|---|---|---|
onClose | () => void | — | Called to close the drawer (required). |
onClose
() => void
Default: —
Called to close the drawer (required).
| Prop | Type | Default | Description |
|---|---|---|---|
backdrop | Partial<BackdropProps> | — | Extra props forwarded to the underlying Backdrop. |
headers | Partial<PageTitleProps> | — | Extra props forwarded to the header's PageTitle. |
divider | Partial<DividerProps> | — | Extra props for the header/body divider. |
classNames | Partial<Record<DrawerSlot, string>> | — | Per-slot class overrides (base/header/headerTitle/body/footer/closeButton). |
className | string | — | Class applied to the root drawer element. |
style | CSSProperties | — | Inline styles for the root element. |
backdrop
Partial<BackdropProps>
Default: —
Extra props forwarded to the underlying Backdrop.
headers
Partial<PageTitleProps>
Default: —
Extra props forwarded to the header's PageTitle.
divider
Partial<DividerProps>
Default: —
Extra props for the header/body divider.
classNames
Partial<Record<DrawerSlot, string>>
Default: —
Per-slot class overrides (base/header/headerTitle/body/footer/closeButton).
className
string
Default: —
Class applied to the root drawer element.
style
CSSProperties
Default: —
Inline styles for the root element.