# Drawer URL: https://ark-ui.com/docs/components/drawer Source: https://raw.githubusercontent.com/chakra-ui/ark/refs/heads/main/website/src/content/pages/components/drawer.mdx A panel that slides in from the edge of the screen, typically used for navigation or forms. --- ## Anatomy ```tsx ``` ## Examples **Example: basic** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const Basic = () => ( Open Drawer Title

This is the content of the drawer.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const Basic = () => ( Open Drawer Title

This is the content of the drawer.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Drawer Title

This is the content of the drawer.

``` ### Swipe Direction Use the `swipeDirection` prop to control which edge the drawer slides in from. **Example: swipe-direction** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const SwipeDirection = () => ( Open Right Right Drawer

This drawer slides in from the right side.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const SwipeDirection = () => ( Open Right Right Drawer

This drawer slides in from the right side.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Right Right Drawer

This drawer slides in from the right side.

``` ### Snap Points Use the `snapPoints` prop to define intermediate positions the drawer can snap to. **Example: snap-points** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const SnapPoints = () => ( Open Drawer with Snap Points

This drawer has multiple snap points at 25%, 50%, and 100% of the viewport height.

Drag the grabber to snap between different heights, or swipe to dismiss.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const SnapPoints = () => ( Open Drawer with Snap Points

This drawer has multiple snap points at 25%, 50%, and 100% of the viewport height.

Drag the grabber to snap between different heights, or swipe to dismiss.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Drawer with Snap Points

This drawer has multiple snap points at 25%, 50%, and 100% of the viewport height.

Drag the grabber to snap between different heights, or swipe to dismiss.

``` ### Modal Set `modal` to `false` to allow interaction with the rest of the page while the drawer is open. **Example: modal** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const Modal = () => ( Open Modal Drawer ) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const Modal = () => ( Open Modal Drawer ) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Modal Drawer ``` ### Controlled Use the `open` and `onOpenChange` props to control the drawer state. **Example: controlled** #### React ```tsx import { Drawer, type DrawerOpenChangeDetails } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import { useState } from 'react' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' export const Controlled = () => { const [open, setOpen] = useState(false) return ( <> setOpen(details.open)}> Controlled Drawer

This drawer is controlled via state.

) } ``` #### Solid ```tsx import { Drawer, type DrawerOpenChangeDetails } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import { createSignal } from 'solid-js' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' export const Controlled = () => { const [open, setOpen] = createSignal(false) return ( <> setOpen(details.open)}> Controlled Drawer

This drawer is controlled via state.

) } ``` #### Vue ```vue ``` #### Svelte ```svelte Controlled Drawer

This drawer is controlled via state.

``` ### Scrollable **Example: scrollable** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const Scrollable = () => ( Open Scrollable Drawer
{Array.from({ length: 50 }).map((_, index) => (
Item {index + 1}
))}
) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import { For } from 'solid-js' import styles from 'styles/drawer.module.css' export const Scrollable = () => ( Open Scrollable Drawer
{(_, index) =>
Item {index() + 1}
}
) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Scrollable Drawer
{#each Array.from({ length: 50 }) as _, index}
Item {index + 1}
{/each}
``` ### No Drag Area Apply the `data-no-drag` attribute to any element inside the drawer to prevent dragging from starting on it. **Example: no-drag-area** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const NoDragArea = () => ( Open Drawer Title

This is the no drag area of the drawer.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const NoDragArea = () => ( Open Drawer Title

This is the no drag area of the drawer.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Drawer Title

This is the no drag area of the drawer.

``` ### Non Draggable Set `draggable` to `false` to disable drag-to-dismiss entirely. **Example: non-draggable** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const NonDraggable = () => ( Open Drawer Title

This is the content of the drawer.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const NonDraggable = () => ( Open Drawer Title

This is the content of the drawer.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Drawer Title

This is the content of the drawer.

``` ### Indent Background Use `Drawer.IndentBackground` to create a visual indent effect on the page behind the drawer. **Example: indent-background** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import styles from 'styles/drawer.module.css' export const IndentBackground = () => ( Open Drawer Stacked Drawer

This drawer uses indent background and indent effects when swiped.

) ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import styles from 'styles/drawer.module.css' export const IndentBackground = () => ( Open Drawer Stacked Drawer

This drawer uses indent background and indent effects when swiped.

) ``` #### Vue ```vue ``` #### Svelte ```svelte Open Drawer Stacked Drawer

This drawer uses indent background and indent effects when swiped.

``` ### Multiple Triggers Use the `value` prop on `Drawer.Trigger` to share a single drawer across multiple trigger elements. The `onTriggerValueChange` callback fires when a different trigger is activated. **Example: multiple-triggers** #### React ```tsx import { Drawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import { useState } from 'react' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' import field from 'styles/field.module.css' interface User { id: string name: string email: string } const users: User[] = [ { id: '1', name: 'Alice Johnson', email: 'alice@example.com' }, { id: '2', name: 'Bob Smith', email: 'bob@example.com' }, { id: '3', name: 'Carol Davis', email: 'carol@example.com' }, ] export const MultipleTriggers = () => { const [activeUser, setActiveUser] = useState(null) return ( { setActiveUser(users.find((u) => u.id === e.value) ?? null) }} >
{users.map((user) => ( Edit {user.name} ))}
Edit User {activeUser && (
Cancel Save Changes
)}
) } ``` #### Solid ```tsx import { Drawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import { For, Show, createSignal } from 'solid-js' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' import field from 'styles/field.module.css' interface User { id: string name: string email: string } const users: User[] = [ { id: '1', name: 'Alice Johnson', email: 'alice@example.com' }, { id: '2', name: 'Bob Smith', email: 'bob@example.com' }, { id: '3', name: 'Carol Davis', email: 'carol@example.com' }, ] export const MultipleTriggers = () => { const [activeUser, setActiveUser] = createSignal(null) return ( { setActiveUser(users.find((u) => u.id === e.value) ?? null) }} >
{(user) => ( Edit {user.name} )}
Edit User {(user) => (
Cancel Save Changes
)}
) } ``` #### Vue ```vue ``` #### Svelte ```svelte { activeUser = users.find((u) => u.id === e.value) ?? null }} >
{#each users as user (user.id)} Edit {user.name} {/each}
Edit User {#if activeUser}
Cancel Save Changes
{/if}
``` ### Using the Root Provider Use the `useDrawer` hook and `Drawer.RootProvider` to control the drawer from outside the component tree. **Example: root-provider** #### React ```tsx import { Drawer, useDrawer } from '@ark-ui/react/drawer' import { XIcon } from 'lucide-react' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' export const RootProvider = () => { const drawer = useDrawer({ defaultSnapPoint: 0.5, snapPoints: [0.25, 0.5, 1], }) return (
Drawer with RootProvider

This drawer is controlled via the useDrawer hook and RootProvider.

Active snap point: {drawer.snapPoint}

) } ``` #### Solid ```tsx import { Drawer, useDrawer } from '@ark-ui/solid/drawer' import { XIcon } from 'lucide-solid' import button from 'styles/button.module.css' import styles from 'styles/drawer.module.css' export const RootProvider = () => { const drawer = useDrawer({ defaultSnapPoint: 0.5, snapPoints: [0.25, 0.5, 1], }) return (
Drawer with RootProvider

This drawer is controlled via the useDrawer hook and RootProvider.

Active snap point: {drawer().snapPoint}

) } ``` #### Vue ```vue ``` #### Svelte ```svelte
Drawer with RootProvider

This drawer is controlled via the useDrawer hook and RootProvider.

Active snap point: {drawer().snapPoint}

``` ## Guides ### Styling by Swipe Direction The `Drawer.Content` elements expose a `data-swipe-direction` attribute (`up` | `down` | `left` | `right`) that reflects the resolved physical direction the drawer slides in from. Target it to apply direction-aware styles — for example, rounded corners on the side facing the viewport: ```css [data-scope='drawer'][data-part='content'] { /* Top drawer */ &[data-swipe-direction='up'] { border-top-left-radius: 0; border-top-right-radius: 0; border-bottom-left-radius: 16px; border-bottom-right-radius: 16px; } /* Bottom drawer */ &[data-swipe-direction='down'] { border-bottom-left-radius: 0; border-bottom-right-radius: 0; border-top-left-radius: 16px; border-top-right-radius: 16px; } /* Left drawer */ &[data-swipe-direction='left'] { border-top-left-radius: 0; border-bottom-right-radius: 16px; border-top-left-radius: 16px; border-top-right-radius: 0; } /* Right drawer */ &[data-swipe-direction='right'] { border-top-right-radius: 0; border-bottom-left-radius: 16px; border-top-left-radius: 0; border-top-right-radius: 16px; } } ``` ### Preventing Overdrag Gaps When a user drags the drawer past its open position, a small gap can appear between the drawer content and the viewport edge. To prevent this, extend the drawer's background beyond its visible bounds using a CSS `::after` pseudo-element: ```css [data-scope='drawer'][data-part='content'] { --bleed: 3rem; position: relative; /* Bleed effect */ &::after { content: ''; position: absolute; inset-inline: 0; top: 100%; height: var(--bleed); background-color: inherit; pointer-events: none; } } ``` For side drawers, adjust the pseudo-element to extend horizontally: ```css [data-scope='drawer'][data-part='content'] { /* Right drawer */ &[data-swipe-direction='right']::after { inset-inline: auto; inset-block: 0; top: 0; left: 100%; width: var(--bleed); height: auto; } /* Left drawer */ &[data-swipe-direction='left']::after { inset-inline: auto; inset-block: 0; top: 0; right: 100%; width: var(--bleed); height: auto; } } ``` The `::after` element inherits the drawer's background color and sits just outside the content bounds. During overdrag, the dampened movement reveals this extension instead of an empty gap. ## API Reference ### Props **Component API Reference** #### React **Root Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `closeOnEscape` | `boolean` | No | Whether to close the drawer when the escape key is pressed. | | `closeOnInteractOutside` | `boolean` | No | Whether to close the drawer when the outside is clicked. | | `closeThreshold` | `number` | No | The threshold distance for dismissing the drawer. | | `defaultOpen` | `boolean` | No | The initial open state of the drawer. | | `defaultSnapPoint` | `SnapPoint` | No | | | `finalFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is closed. | | `id` | `string` | No | The unique identifier of the machine. | | `ids` | `Partial<{ backdrop: string positioner: string content: string title: string header: string trigger: string grabber: string grabberIndicator: string closeTrigger: string }>` | No | The ids of the elements in the drawer. Useful for composition. | | `immediate` | `boolean` | No | Whether to synchronize the present change immediately or defer it to the next frame | | `initialFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is opened. | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `modal` | `boolean` | No | Whether to prevent pointer interaction outside the element and hide all content below it. | | `onEscapeKeyDown` | `(event: KeyboardEvent) => void` | No | Function called when the escape key is pressed | | `onExitComplete` | `VoidFunction` | No | Function called when the animation ends in the closed state | | `onFocusOutside` | `(event: FocusOutsideEvent) => void` | No | Function called when the focus is moved outside the component | | `onInteractOutside` | `(event: InteractOutsideEvent) => void` | No | Function called when an interaction happens outside the component | | `onOpenChange` | `(details: OpenChangeDetails) => void` | No | Function called when the open state changes. | | `onPointerDownOutside` | `(event: PointerDownOutsideEvent) => void` | No | Function called when the pointer is pressed down outside the component | | `onRequestDismiss` | `(event: LayerDismissEvent) => void` | No | Function called when this layer is closed due to a parent layer being closed | | `onSnapPointChange` | `(details: SnapPointChangeDetails) => void` | No | Callback fired when the snap point changes. | | `open` | `boolean` | No | Whether the drawer is open. | | `present` | `boolean` | No | Whether the node is present (controlled by the user) | | `preventDragOnScroll` | `boolean` | No | Whether to prevent dragging on scrollable elements. When enabled, the sheet will not start dragging if the user is interacting with a scrollable element. | | `preventScroll` | `boolean` | No | Whether to prevent scrolling behind the sheet when it's opened | | `restoreFocus` | `boolean` | No | Whether to restore focus to the element that had focus before the sheet was opened. | | `role` | `'dialog' | 'alertdialog'` | No | The sheet's role | | `skipAnimationOnMount` | `boolean` | No | Whether to allow the initial presence animation. | | `snapPoint` | `SnapPoint` | No | The currently active snap point. | | `snapPoints` | `SnapPoint[]` | No | The snap points of the drawer. Array of numbers or strings representing the snap points. | | `snapToSequentialPoints` | `boolean` | No | Whether the drawer should snap to sequential points when swiping. | | `stack` | `DrawerStack` | No | Optional external store for coordinating app-level drawer stack visuals (e.g. indent and background layers). | | `swipeDirection` | `SwipeDirection` | No | The direction in which the drawer can be swiped. | | `swipeVelocityThreshold` | `number` | No | The threshold velocity (in pixels/s) for closing the drawer. | | `trapFocus` | `boolean` | No | Whether to trap focus inside the sheet when it's opened. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Backdrop Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Backdrop Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | backdrop | | `[data-state]` | "open" | "closed" | | `[data-swiping]` | | **Backdrop CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-swipe-progress` | The drawer swipe progress value for the Backdrop | | `--drawer-swipe-strength` | The drawer swipe strength value for the Backdrop | | `--layer-index` | The index of the dismissable in the layer stack | **CloseTrigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Content Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `draggable` | `boolean` | No | Whether the drawer content is draggable. If false, the drawer can only be dragged by the grabber. | **Content Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | content | | `[data-state]` | "open" | "closed" | | `[data-expanded]` | Present when expanded | | `[data-swipe-direction]` | | | `[data-swiping]` | | | `[data-dragging]` | Present when in the dragging state | **Content CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-translate` | The drawer translate value for the Content | | `--drawer-translate-x` | The drawer translate x value for the Content | | `--drawer-translate-y` | The drawer translate y value for the Content | | `--drawer-snap-point-offset-x` | The offset position for drawer snap point | | `--drawer-snap-point-offset-y` | The offset position for drawer snap point | | `--drawer-swipe-movement-x` | The drawer swipe movement x value for the Content | | `--drawer-swipe-movement-y` | The drawer swipe movement y value for the Content | | `--drawer-swipe-strength` | The drawer swipe strength value for the Content | | `--layer-index` | The index of the dismissable in the layer stack | | `--nested-layer-count` | The number of nested drawers | **GrabberIndicator Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Grabber Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **IndentBackground Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Indent Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | positioner | | `[data-state]` | "open" | "closed" | | `[data-swipe-direction]` | | **RootProvider Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `value` | `UseDrawerReturn` | Yes | | | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `immediate` | `boolean` | No | Whether to synchronize the present change immediately or defer it to the next frame | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `onExitComplete` | `VoidFunction` | No | Function called when the animation ends in the closed state | | `present` | `boolean` | No | Whether the node is present (controlled by the user) | | `skipAnimationOnMount` | `boolean` | No | Whether to allow the initial presence animation. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Title Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | trigger | | `[data-value]` | The value of the item | | `[data-state]` | "open" | "closed" | | `[data-current]` | Present when current | #### Solid **Root Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `closeOnEscape` | `boolean` | No | Whether to close the drawer when the escape key is pressed. | | `closeOnInteractOutside` | `boolean` | No | Whether to close the drawer when the outside is clicked. | | `closeThreshold` | `number` | No | The threshold distance for dismissing the drawer. | | `defaultOpen` | `boolean` | No | The initial open state of the drawer. | | `defaultSnapPoint` | `SnapPoint` | No | | | `finalFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is closed. | | `id` | `string` | No | The unique identifier of the machine. | | `ids` | `Partial<{ backdrop: string positioner: string content: string title: string header: string trigger: string grabber: string grabberIndicator: string closeTrigger: string }>` | No | The ids of the elements in the drawer. Useful for composition. | | `immediate` | `boolean` | No | Whether to synchronize the present change immediately or defer it to the next frame | | `initialFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is opened. | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `modal` | `boolean` | No | Whether to prevent pointer interaction outside the element and hide all content below it. | | `onEscapeKeyDown` | `(event: KeyboardEvent) => void` | No | Function called when the escape key is pressed | | `onExitComplete` | `VoidFunction` | No | Function called when the animation ends in the closed state | | `onFocusOutside` | `(event: FocusOutsideEvent) => void` | No | Function called when the focus is moved outside the component | | `onInteractOutside` | `(event: InteractOutsideEvent) => void` | No | Function called when an interaction happens outside the component | | `onOpenChange` | `(details: OpenChangeDetails) => void` | No | Function called when the open state changes. | | `onPointerDownOutside` | `(event: PointerDownOutsideEvent) => void` | No | Function called when the pointer is pressed down outside the component | | `onRequestDismiss` | `(event: LayerDismissEvent) => void` | No | Function called when this layer is closed due to a parent layer being closed | | `onSnapPointChange` | `(details: SnapPointChangeDetails) => void` | No | Callback fired when the snap point changes. | | `open` | `boolean` | No | Whether the drawer is open. | | `present` | `boolean` | No | Whether the node is present (controlled by the user) | | `preventDragOnScroll` | `boolean` | No | Whether to prevent dragging on scrollable elements. When enabled, the sheet will not start dragging if the user is interacting with a scrollable element. | | `preventScroll` | `boolean` | No | Whether to prevent scrolling behind the sheet when it's opened | | `restoreFocus` | `boolean` | No | Whether to restore focus to the element that had focus before the sheet was opened. | | `role` | `'dialog' | 'alertdialog'` | No | The sheet's role | | `skipAnimationOnMount` | `boolean` | No | Whether to allow the initial presence animation. | | `snapPoint` | `SnapPoint` | No | The currently active snap point. | | `snapPoints` | `SnapPoint[]` | No | The snap points of the drawer. Array of numbers or strings representing the snap points. | | `snapToSequentialPoints` | `boolean` | No | Whether the drawer should snap to sequential points when swiping. | | `stack` | `DrawerStack` | No | Optional external store for coordinating app-level drawer stack visuals (e.g. indent and background layers). | | `swipeDirection` | `SwipeDirection` | No | The direction in which the drawer can be swiped. | | `swipeVelocityThreshold` | `number` | No | The threshold velocity (in pixels/s) for closing the drawer. | | `trapFocus` | `boolean` | No | Whether to trap focus inside the sheet when it's opened. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Backdrop Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Backdrop Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | backdrop | | `[data-state]` | "open" | "closed" | | `[data-swiping]` | | **Backdrop CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-swipe-progress` | The drawer swipe progress value for the Backdrop | | `--drawer-swipe-strength` | The drawer swipe strength value for the Backdrop | | `--layer-index` | The index of the dismissable in the layer stack | **CloseTrigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'button'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Content Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `draggable` | `boolean` | No | Whether the drawer content is draggable. If false, the drawer can only be dragged by the grabber. | **Content Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | content | | `[data-state]` | "open" | "closed" | | `[data-expanded]` | Present when expanded | | `[data-swipe-direction]` | | | `[data-swiping]` | | | `[data-dragging]` | Present when in the dragging state | **Content CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-translate` | The drawer translate value for the Content | | `--drawer-translate-x` | The drawer translate x value for the Content | | `--drawer-translate-y` | The drawer translate y value for the Content | | `--drawer-snap-point-offset-x` | The offset position for drawer snap point | | `--drawer-snap-point-offset-y` | The offset position for drawer snap point | | `--drawer-swipe-movement-x` | The drawer swipe movement x value for the Content | | `--drawer-swipe-movement-y` | The drawer swipe movement y value for the Content | | `--drawer-swipe-strength` | The drawer swipe strength value for the Content | | `--layer-index` | The index of the dismissable in the layer stack | | `--nested-layer-count` | The number of nested drawers | **GrabberIndicator Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Grabber Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **IndentBackground Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Indent Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'div'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | positioner | | `[data-state]` | "open" | "closed" | | `[data-swipe-direction]` | | **RootProvider Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `value` | `UseDrawerReturn` | Yes | | | `immediate` | `boolean` | No | Whether to synchronize the present change immediately or defer it to the next frame | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `onExitComplete` | `VoidFunction` | No | Function called when the animation ends in the closed state | | `present` | `boolean` | No | Whether the node is present (controlled by the user) | | `skipAnimationOnMount` | `boolean` | No | Whether to allow the initial presence animation. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Title Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'h2'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `(props: ParentProps<'button'>) => Element` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | trigger | | `[data-value]` | The value of the item | | `[data-state]` | "open" | "closed" | | `[data-current]` | Present when current | #### Vue **Root Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `closeOnEscape` | `boolean` | No | Whether to close the drawer when the escape key is pressed. | | `closeOnInteractOutside` | `boolean` | No | Whether to close the drawer when the outside is clicked. | | `closeThreshold` | `number` | No | The threshold distance for dismissing the drawer. | | `defaultOpen` | `boolean` | No | The initial open state of the drawer. | | `defaultSnapPoint` | `string | number` | No | The default snap point of the drawer. | | `finalFocusEl` | `() => HTMLElement | null` | No | Element to receive focus when the sheet is closed. | | `id` | `string` | No | The unique identifier of the machine. | | `ids` | `Partial<{ backdrop: string positioner: string content: string title: string trigger: string grabber: string grabberIndicator: string closeTrigger: string }>` | No | The ids of the elements in the drawer. Useful for composition. | | `initialFocusEl` | `() => HTMLElement | null` | No | Element to receive focus when the sheet is opened. | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `modal` | `boolean` | No | Whether to prevent pointer interaction outside the element and hide all content below it. | | `open` | `boolean` | No | Whether the drawer is open. | | `preventDragOnScroll` | `boolean` | No | Whether to prevent dragging on scrollable elements. | | `preventScroll` | `boolean` | No | Whether to prevent scrolling behind the sheet when it's opened | | `restoreFocus` | `boolean` | No | Whether to restore focus to the element that had focus before the sheet was opened. | | `role` | `'dialog' | 'alertdialog'` | No | The sheet's role | | `snapPoint` | `string | number` | No | The currently active snap point. | | `snapPoints` | `(string | number)[]` | No | The snap points of the drawer. | | `snapToSequentialPoints` | `boolean` | No | Whether the drawer should snap to sequential points when swiping. | | `swipeDirection` | `'up' | 'down' | 'left' | 'right'` | No | The direction in which the drawer can be swiped. | | `swipeVelocityThreshold` | `number` | No | The threshold velocity (in pixels/s) for closing the drawer. | | `trapFocus` | `boolean` | No | Whether to trap focus inside the sheet when it's opened. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Backdrop Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Backdrop Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | backdrop | | `[data-state]` | "open" | "closed" | | `[data-swiping]` | | **Backdrop CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-swipe-progress` | The drawer swipe progress value for the Backdrop | | `--drawer-swipe-strength` | The drawer swipe strength value for the Backdrop | | `--layer-index` | The index of the dismissable in the layer stack | **CloseTrigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Content Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `draggable` | `boolean` | No | Whether the drawer content is draggable. If false, the drawer can only be dragged by the grabber. | **Content Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | content | | `[data-state]` | "open" | "closed" | | `[data-expanded]` | Present when expanded | | `[data-swipe-direction]` | | | `[data-swiping]` | | | `[data-dragging]` | Present when in the dragging state | **Content CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-translate` | The drawer translate value for the Content | | `--drawer-translate-x` | The drawer translate x value for the Content | | `--drawer-translate-y` | The drawer translate y value for the Content | | `--drawer-snap-point-offset-x` | The offset position for drawer snap point | | `--drawer-snap-point-offset-y` | The offset position for drawer snap point | | `--drawer-swipe-movement-x` | The drawer swipe movement x value for the Content | | `--drawer-swipe-movement-y` | The drawer swipe movement y value for the Content | | `--drawer-swipe-strength` | The drawer swipe strength value for the Content | | `--layer-index` | The index of the dismissable in the layer stack | | `--nested-layer-count` | The number of nested drawers | **GrabberIndicator Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Grabber Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **IndentBackground Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Indent Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Positioner Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | positioner | | `[data-state]` | "open" | "closed" | | `[data-swipe-direction]` | | **RootProvider Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `value` | `DrawerApi` | Yes | | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Title Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `boolean` | No | Use the provided child element as the default rendered element, combining their props and behavior. | **Trigger Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | trigger | | `[data-value]` | The value of the item | | `[data-state]` | "open" | "closed" | | `[data-current]` | Present when current | #### Svelte **Root Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `closeOnEscape` | `boolean` | No | Whether to close the drawer when the escape key is pressed. | | `closeOnInteractOutside` | `boolean` | No | Whether to close the drawer when the outside is clicked. | | `closeThreshold` | `number` | No | The threshold distance for dismissing the drawer. | | `defaultOpen` | `boolean` | No | The initial open state of the drawer. | | `defaultSnapPoint` | `SnapPoint` | No | | | `finalFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is closed. | | `id` | `string` | No | The unique identifier of the machine. | | `ids` | `Partial<{ backdrop: string positioner: string content: string title: string header: string trigger: string grabber: string grabberIndicator: string closeTrigger: string }>` | No | The ids of the elements in the drawer. Useful for composition. | | `immediate` | `boolean` | No | Whether to synchronize the present change immediately or defer it to the next frame | | `initialFocusEl` | `() => MaybeElement` | No | Element to receive focus when the sheet is opened. | | `lazyMount` | `boolean` | No | Whether to enable lazy mounting | | `modal` | `boolean` | No | Whether to prevent pointer interaction outside the element and hide all content below it. | | `onEscapeKeyDown` | `(event: KeyboardEvent) => void` | No | Function called when the escape key is pressed | | `onExitComplete` | `VoidFunction` | No | Function called when the animation ends in the closed state | | `onFocusOutside` | `(event: FocusOutsideEvent) => void` | No | Function called when the focus is moved outside the component | | `onInteractOutside` | `(event: InteractOutsideEvent) => void` | No | Function called when an interaction happens outside the component | | `onOpenChange` | `(details: OpenChangeDetails) => void` | No | Function called when the open state changes. | | `onPointerDownOutside` | `(event: PointerDownOutsideEvent) => void` | No | Function called when the pointer is pressed down outside the component | | `onRequestDismiss` | `(event: LayerDismissEvent) => void` | No | Function called when this layer is closed due to a parent layer being closed | | `onSnapPointChange` | `(details: SnapPointChangeDetails) => void` | No | Callback fired when the snap point changes. | | `open` | `boolean` | No | Whether the drawer is open. | | `present` | `boolean` | No | Whether the node is present (controlled by the user) | | `preventDragOnScroll` | `boolean` | No | Whether to prevent dragging on scrollable elements. When enabled, the sheet will not start dragging if the user is interacting with a scrollable element. | | `preventScroll` | `boolean` | No | Whether to prevent scrolling behind the sheet when it's opened | | `restoreFocus` | `boolean` | No | Whether to restore focus to the element that had focus before the sheet was opened. | | `role` | `'alertdialog' | 'dialog'` | No | The sheet's role | | `skipAnimationOnMount` | `boolean` | No | Whether to allow the initial presence animation. | | `snapPoint` | `SnapPoint` | No | The currently active snap point. | | `snapPoints` | `SnapPoint[]` | No | The snap points of the drawer. Array of numbers or strings representing the snap points. | | `snapToSequentialPoints` | `boolean` | No | Whether the drawer should snap to sequential points when swiping. | | `stack` | `DrawerStack` | No | Optional external store for coordinating app-level drawer stack visuals (e.g. indent and background layers). | | `swipeDirection` | `SwipeDirection` | No | The direction in which the drawer can be swiped. | | `swipeVelocityThreshold` | `number` | No | The threshold velocity (in pixels/s) for closing the drawer. | | `trapFocus` | `boolean` | No | Whether to trap focus inside the sheet when it's opened. | | `unmountOnExit` | `boolean` | No | Whether to unmount on exit. | **Backdrop Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Backdrop Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | backdrop | | `[data-state]` | "open" | "closed" | | `[data-swiping]` | | **Backdrop CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-swipe-progress` | The drawer swipe progress value for the Backdrop | | `--drawer-swipe-strength` | The drawer swipe strength value for the Backdrop | | `--layer-index` | The index of the dismissable in the layer stack | **CloseTrigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'button'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Content Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `draggable` | `boolean` | No | Whether the drawer content is draggable. If false, the drawer can only be dragged by the grabber. | | `ref` | `Element` | No | | **Content Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | content | | `[data-state]` | "open" | "closed" | | `[data-expanded]` | Present when expanded | | `[data-swipe-direction]` | | | `[data-swiping]` | | | `[data-dragging]` | Present when in the dragging state | **Content CSS Variables:** | Variable | Description | |----------|-------------| | `--drawer-translate` | The drawer translate value for the Content | | `--drawer-translate-x` | The drawer translate x value for the Content | | `--drawer-translate-y` | The drawer translate y value for the Content | | `--drawer-snap-point-offset-x` | The offset position for drawer snap point | | `--drawer-snap-point-offset-y` | The offset position for drawer snap point | | `--drawer-swipe-movement-x` | The drawer swipe movement x value for the Content | | `--drawer-swipe-movement-y` | The drawer swipe movement y value for the Content | | `--drawer-swipe-strength` | The drawer swipe strength value for the Content | | `--layer-index` | The index of the dismissable in the layer stack | | `--nested-layer-count` | The number of nested drawers | **GrabberIndicator Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Grabber Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **IndentBackground Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Indent Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Positioner Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'div'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Positioner Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | positioner | | `[data-state]` | "open" | "closed" | | `[data-swipe-direction]` | | **RootProvider Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `value` | `UseDrawerReturn` | Yes | | **Title Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'h2'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Trigger Props:** | Prop | Type | Required | Description | |------|------|----------|-------------| | `asChild` | `Snippet<[PropsFn<'button'>]>` | No | Use the provided child element as the default rendered element, combining their props and behavior. | | `ref` | `Element` | No | | **Trigger Data Attributes:** | Attribute | Value | |-----------|-------| | `[data-scope]` | drawer | | `[data-part]` | trigger | | `[data-value]` | The value of the item | | `[data-state]` | "open" | "closed" | | `[data-current]` | Present when current | ### Context **API:** | Property | Type | Description | |----------|------|-------------| | `open` | `boolean` | Whether the drawer is open. | | `dragging` | `boolean` | Whether the drawer is currently being dragged. | | `triggerValue` | `string | null` | The value of the active trigger. | | `setTriggerValue` | `(value: string | null) => void` | Set the active trigger value. | | `setOpen` | `(open: boolean) => void` | Function to open or close the menu. | | `snapPoints` | `SnapPoint[]` | The snap points of the drawer. | | `swipeDirection` | `SwipeDirection` | The swipe direction of the drawer. | | `snapPoint` | `SnapPoint | null` | The currently active snap point. | | `setSnapPoint` | `(snapPoint: SnapPoint | null) => void` | Function to set the active snap point. | | `getOpenPercentage` | `() => number` | Get the current open percentage of the drawer. | | `getSnapPointIndex` | `() => number` | Get the index of the currently active snap point. | | `getContentSize` | `() => number | null` | Get the current main-axis size of the drawer content. | ## Accessibility Complies with the [Dialog WAI-ARIA design pattern](https://www.w3.org/WAI/ARIA/apg/patterns/dialog-modal/).