DrawerPanel
Drawers present related, contextual content next to an existing page, usually to support a single, focused task rather than general browsing. They interrupt the main experience, so they should be reserved for cases where that disruption is clearly justified. However, Drawers don't block users from completing their task, like a SideModal or ModalDialog would.
Status: Overview, When to Use, When Not to Use, and Accessibility text below were provided directly by the user (2026-08-19) and verified against the Naos Figma documentation page (file kGOhFhP2iZtOGmJsuFavq7, node 10637:3549, "🧩 Naos – Data display and structure") — the provided text matches that page's frame names (DOC_Drawer_Overview, DOC_Drawer_WhenToUse, DOC_Drawer_WhenNotToUse, DOC_TEXT_Drawer_Accessibility) verbatim, so it's treated as authoritative. Anatomy, behavior detail, and the Do/Don't rules below were read directly from the same Figma page.
Naming note: the Figma page calls this component simply "Drawer," but its anatomy (a header with Title/Slot/Actions/CloseButton, .DrawerHeader component) matches this repo's DrawerPanel molecular component — specifically DrawerPanelHeaderProps.actions?: React.ReactNode[] — not the low-level Drawer primitive (packages/primitives/Drawer, documented separately at drawer), which has no header/anatomy of its own. This scaffold assumes the Figma page describes DrawerPanel; flag to design if that mapping is wrong.
Source: DTSL/design-system → packages/product/@dtsl-react/src/components/molecular/DrawerPanel/types/DrawerPanel.types.ts (package @dtsl/react, exported as DrawerPanel, DPHeader, DPBody, DPFooter, useDrawerPanel)
Props (verbatim from source, trimmed)
export type DrawerPanelMode = 'collapsed' | 'expanded' | 'mobile'
export interface DrawerPanelProps {
drawerPanel: UseDrawerPanelReturn
children: React.ReactNode
className?: string
}
export interface DrawerPanelHeaderProps {
children?: React.ReactNode
drawerPanel?: UseDrawerPanelReturn
actions?: React.ReactNode[]
className?: string
}
export interface DrawerPanelBodyProps {
children?: React.ReactNode
className?: string
}
export interface DrawerPanelFooterProps {
children?: React.ReactNode
className?: string
}
The useDrawerPanel hook returns UseDrawerPanelReturn: visible, mode (DrawerPanelMode), open(), close(), toggle(), expand(), collapse(), plus setOffsetTopRef/setOffsetSideRef callback refs for layout offset tracking. Full shape in source.
Anatomy
Top level (from Figma "Anatomy" section):
- DrawerHeader
- Content
DrawerHeader, in detail:
- AI logo — optional (a distinct "AIDrawer" variant exists with this shown; see
chat-ui'sAIDrawer/ai-drawer.journal.mdin source for a related real implementation) - Title
- Slot — custom header content
- Actions — optional, maps directly to
DrawerPanelHeaderProps.actions - CloseButton
Device variants documented: Desktop, Tablet, Mobile — consistent with DrawerPanelMode (collapsed | expanded | mobile).
When to Use
- to display additional information to support the main content
- when the Drawer content is for reference only and doesn't update the main content data
When NOT to Use
- when the user needs to manipulate data that will change the main content — use a SideModal or ModalDialog instead
CRITICAL: Real behavior and layout rules
Verbatim from the Figma "Behavior" section:
Drawers can slide in from either the right or left side of the screen, depending on use case. Drawers do not overlay the page; instead, they push the existing content so both the Drawer and the underlying page remain visible. Overflow content within the Drawer can scroll vertically, independent of the rest of the UI, but horizontal scrolling is not supported. While a Drawer is open, users can still interact with the main page content, and must use the closeButton to dismiss the Drawer. This behavior differs from the SideModal, which overlays the page and prevents interaction with any content outside of itself.
Verbatim Do/Don't rules from the Figma "Usage" section:
✅ Drawers should always appear from the right- or left-hand side of the screen on devices above 745px ✅ Always include a closeButton so users can dismiss the drawer ❌ Do not move drawers to the center of the screen on devices above 745px ❌ Do not use an overlay with a drawer on devices above 745px
Also from the user-provided Usage notes: Drawers push and resize the underlying layout as they appear (unlike SideModal, which is always an overlay). When Drawer content is taller than the viewport, add vertical overflow handling (scrollbar). Because Drawers affect overall page layout, carefully consider behavior across different screen sizes.
Decision Logic
Does the user need to manipulate data that will change the main content?
YES → use SideModal or ModalDialog (blocking, overlay)
NO → DrawerPanel is appropriate if the content is reference-only
Is the viewport above 745px?
YES → Drawer pushes/resizes the layout, appears from left or right (never centered), no overlay
NO (mobile) → device variant differs — see Figma "Mobile" placement/behavior recordings (not text-extracted here)
Does the Drawer's content overflow vertically?
YES → add vertical scroll, scoped to the Drawer only (horizontal scroll is not supported)
DrawerPanel vs SideModal, now resolved: DrawerPanel pushes/resizes the page and allows continued interaction with content outside it (dismissed only via its close button); SideModal overlays the page and blocks interaction with anything outside itself. This is a real, stated distinction, not inferred.
Accessibility
- Once open, Drawer inputs can be reached by Tab and selected with Enter.
- Pressing Esc allows users to focus on content outside the Drawer while the Drawer itself remains open.
- Drawers can only be dismissed via keyboard if the user navigates to the close button and selects it with Enter.
Common Mistakes
- ❌ Centering a Drawer on screens above 745px (per the explicit Don't rule)
- ❌ Adding an overlay/backdrop behind a Drawer on screens above 745px
- ❌ Omitting the close button — it's the only way to dismiss a Drawer, by mouse or keyboard
- ❌ Using DrawerPanel when the task requires the user to manipulate data that changes the main content — use SideModal/ModalDialog instead
- ❌ Allowing horizontal scroll inside Drawer content — only vertical overflow is supported