Drawer is a modal dialog that slides in from an edge of the viewport. It is built on the same pieces as Dialog: it renders into a portal on the body, makes the rest of the page inert, locks page scroll, keeps Tab inside with FocusTrap, and gives focus back to whatever opened it when it closes. Escape, a click on the overlay and the close button all ask it to close through onClose; the drawer never closes itself.
The title is the dialog's accessible name and the description its description. Without a title, pass aria-label so a screen reader can announce what opened. The content scrolls between the header and the footer.
side picks the edge: left, right (the default), top or bottom. size is the drawer's extent from that edge: the width of a left or right drawer, and the maximum height of a top or bottom one, which is otherwise as tall as its content.
The drawer floats a small step in from the edge, as Dialog does on small screens, and never grows past the viewport.
A mobile navigation is a left drawer. flush drops the header and the padding, so a list reaches the edges, and floats the close button in the corner. The title still names the dialog, for screen readers only. This replaces the hand-made Animation and fixed-Column menus behind a NavIcon, which had no dialog role, no focus trap and no Escape.
Close it when the route changes, as the menus it replaces did:
On open, focus moves to the first focusable element (the close button, unless showClose is off), or to initialFocusRef. On close it returns to the element that had it before, or to returnFocusRef, and it is returned even if the drawer unmounts while open. While the drawer slides out it is inert itself, so a quick Tab cannot land back inside it.
A dropdown or picker inside the drawer that handles Escape itself (and calls preventDefault, as Once UI's do) closes on its own without closing the drawer.
Set closeOnClickaway={false} for a drawer that holds unsaved input, so a stray click on the overlay does not throw it away.