Drawer

A panel that slides in from a screen edge. It is an HTML popover: a DrawerToggle button opens and closes it through popovertarget, and the browser closes it on Escape or a click outside and shows it...

Demos

For usage examples, visit the component demo page: Drawer

Import

import { Drawer } from '@soroush.tech/design-system/Drawer'

Props

PropTypeDefaultDescription
idstring-The id a DrawerToggle's drawer names.
childrenReactNode-The drawer content.
isOpenboolean-With JavaScript: open state, for controlled use.
onClose(event, reason: 'escapeKey' | 'dismiss') => void-Fired when it closes by itself: Escape, a click outside, its toggle.
anchor'left' | 'right' | 'top' | 'bottom''left'Edge the drawer slides in from.
elevation0-2416Shadow depth of the panel, forwarded to Paper.
transitionDurationnumber225Slide duration in milliseconds.
hasBackdropbooleantrueDim the page behind the open drawer.
shouldLockScrollbooleantrueWith JavaScript: lock body scroll while open.
shouldAutoFocusbooleantrueWith JavaScript: move focus into the drawer when it opens.
shouldTrapFocusbooleantrueWith JavaScript: keep Tab cycling within the open drawer.
shouldRestoreFocusbooleantrueWith JavaScript: return focus to where it was when it closes.

DrawerToggle

A Button that opens and closes a drawer. Takes every Button prop, plus:

PropTypeDefaultDescription
drawerstring-The id of the Drawer.
action'toggle' | 'show' | 'hide''toggle'What a click does to the drawer.

Why id is required

The toggle opens the drawer with plain HTML - <button popovertarget="nav"> - which is what makes it work with JavaScript off, and popovertarget can only name an element by its id. The toggle usually lives far from the drawer (in an AppBar), so the pair is linked by name: <Drawer id="nav"> and <DrawerToggle drawer="nav">.

Browsers without the Popover API

Browsers before Safari 17 and Firefox 125 have no Popover API. There a drawer stays closed - a controlled isOpen does nothing rather than throwing - and the rest of the page keeps working.

Testing

jsdom has no Popover API either. installPopover from @soroush.tech/design-system/testing stands in for it - show, hide, the toggle event, Escape and DrawerToggle clicks - and returns a function that removes it:

import { installPopover } from '@soroush.tech/design-system/testing'

let restore = () => {}
beforeAll(() => {
  restore = installPopover()
})
afterAll(() => restore())

The top layer, clicks outside and focus need a real browser.

Source code

If this page does not answer your question, have a look at the implementation of the component for more detail.