@mortenbrudvik/waveui 0.14.1 → 0.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +413 -53
- package/dist/components/data-display/InfoButton.cjs +1 -1
- package/dist/components/data-display/InfoButton.cjs.map +1 -1
- package/dist/components/data-display/InfoButton.mjs +90 -82
- package/dist/components/data-display/InfoButton.mjs.map +1 -1
- package/dist/components/data-display/InfoLabel.cjs +1 -1
- package/dist/components/data-display/InfoLabel.cjs.map +1 -1
- package/dist/components/data-display/InfoLabel.mjs +19 -18
- package/dist/components/data-display/InfoLabel.mjs.map +1 -1
- package/dist/components/data-display/List.cjs +1 -1
- package/dist/components/data-display/List.cjs.map +1 -1
- package/dist/components/data-display/List.mjs +405 -219
- package/dist/components/data-display/List.mjs.map +1 -1
- package/dist/components/data-display/List.registry.cjs +1 -1
- package/dist/components/data-display/List.registry.cjs.map +1 -1
- package/dist/components/data-display/List.registry.mjs +12 -6
- package/dist/components/data-display/List.registry.mjs.map +1 -1
- package/dist/components/feedback/MessageBarGroup.cjs +2 -0
- package/dist/components/feedback/MessageBarGroup.cjs.map +1 -0
- package/dist/components/feedback/MessageBarGroup.mjs +63 -0
- package/dist/components/feedback/MessageBarGroup.mjs.map +1 -0
- package/dist/components/feedback/ProgressBar.cjs +1 -1
- package/dist/components/feedback/ProgressBar.cjs.map +1 -1
- package/dist/components/feedback/ProgressBar.mjs +41 -39
- package/dist/components/feedback/ProgressBar.mjs.map +1 -1
- package/dist/components/feedback/Toaster.cjs +1 -1
- package/dist/components/feedback/Toaster.cjs.map +1 -1
- package/dist/components/feedback/Toaster.mjs +222 -216
- package/dist/components/feedback/Toaster.mjs.map +1 -1
- package/dist/components/input/Combobox.cjs +1 -1
- package/dist/components/input/Combobox.cjs.map +1 -1
- package/dist/components/input/Combobox.mjs +163 -148
- package/dist/components/input/Combobox.mjs.map +1 -1
- package/dist/components/input/Dropdown.cjs +1 -1
- package/dist/components/input/Dropdown.cjs.map +1 -1
- package/dist/components/input/Dropdown.mjs +132 -117
- package/dist/components/input/Dropdown.mjs.map +1 -1
- package/dist/components/input/Listbox.cjs +1 -1
- package/dist/components/input/Listbox.cjs.map +1 -1
- package/dist/components/input/Listbox.mjs +90 -78
- package/dist/components/input/Listbox.mjs.map +1 -1
- package/dist/components/input/Option.cjs +1 -1
- package/dist/components/input/Option.cjs.map +1 -1
- package/dist/components/input/Option.data.cjs +2 -0
- package/dist/components/input/Option.data.cjs.map +1 -0
- package/dist/components/input/Option.data.mjs +114 -0
- package/dist/components/input/Option.data.mjs.map +1 -0
- package/dist/components/input/Option.mjs +21 -17
- package/dist/components/input/Option.mjs.map +1 -1
- package/dist/components/layout/Accordion.cjs +1 -1
- package/dist/components/layout/Accordion.cjs.map +1 -1
- package/dist/components/layout/Accordion.mjs +124 -109
- package/dist/components/layout/Accordion.mjs.map +1 -1
- package/dist/components/layout/Carousel.cjs +1 -1
- package/dist/components/layout/Carousel.cjs.map +1 -1
- package/dist/components/layout/Carousel.mjs +207 -193
- package/dist/components/layout/Carousel.mjs.map +1 -1
- package/dist/components/layout/FlatTree.cjs +2 -0
- package/dist/components/layout/FlatTree.cjs.map +1 -0
- package/dist/components/layout/FlatTree.context.cjs +2 -0
- package/dist/components/layout/FlatTree.context.cjs.map +1 -0
- package/dist/components/layout/FlatTree.context.mjs +20 -0
- package/dist/components/layout/FlatTree.context.mjs.map +1 -0
- package/dist/components/layout/FlatTree.item.cjs +2 -0
- package/dist/components/layout/FlatTree.item.cjs.map +1 -0
- package/dist/components/layout/FlatTree.item.mjs +90 -0
- package/dist/components/layout/FlatTree.item.mjs.map +1 -0
- package/dist/components/layout/FlatTree.mjs +276 -0
- package/dist/components/layout/FlatTree.mjs.map +1 -0
- package/dist/components/layout/TabList.cjs +1 -1
- package/dist/components/layout/TabList.cjs.map +1 -1
- package/dist/components/layout/TabList.mjs +149 -108
- package/dist/components/layout/TabList.mjs.map +1 -1
- package/dist/components/layout/Tree.cjs.map +1 -1
- package/dist/components/layout/Tree.context.cjs +1 -1
- package/dist/components/layout/Tree.context.cjs.map +1 -1
- package/dist/components/layout/Tree.context.mjs +2 -1
- package/dist/components/layout/Tree.context.mjs.map +1 -1
- package/dist/components/layout/Tree.core.cjs +1 -1
- package/dist/components/layout/Tree.core.cjs.map +1 -1
- package/dist/components/layout/Tree.core.mjs +162 -148
- package/dist/components/layout/Tree.core.mjs.map +1 -1
- package/dist/components/layout/Tree.mjs.map +1 -1
- package/dist/components/layout/Tree.selection.cjs +1 -1
- package/dist/components/layout/Tree.selection.cjs.map +1 -1
- package/dist/components/layout/Tree.selection.mjs +11 -57
- package/dist/components/layout/Tree.selection.mjs.map +1 -1
- package/dist/components/layout/useFlatTree.cjs +2 -0
- package/dist/components/layout/useFlatTree.cjs.map +1 -0
- package/dist/components/layout/useFlatTree.mjs +83 -0
- package/dist/components/layout/useFlatTree.mjs.map +1 -0
- package/dist/components/navigation/Menu.popover.cjs +1 -1
- package/dist/components/navigation/Menu.popover.cjs.map +1 -1
- package/dist/components/navigation/Menu.popover.mjs +154 -168
- package/dist/components/navigation/Menu.popover.mjs.map +1 -1
- package/dist/components/navigation/Nav.cjs +1 -1
- package/dist/components/navigation/Nav.cjs.map +1 -1
- package/dist/components/navigation/Nav.mjs +156 -136
- package/dist/components/navigation/Nav.mjs.map +1 -1
- package/dist/components/navigation/NavDrawer.cjs +1 -1
- package/dist/components/navigation/NavDrawer.cjs.map +1 -1
- package/dist/components/navigation/NavDrawer.mjs +48 -45
- package/dist/components/navigation/NavDrawer.mjs.map +1 -1
- package/dist/components/overlays/Dialog.cjs +1 -1
- package/dist/components/overlays/Dialog.cjs.map +1 -1
- package/dist/components/overlays/Dialog.mjs +128 -122
- package/dist/components/overlays/Dialog.mjs.map +1 -1
- package/dist/components/overlays/Dialog.slots.cjs +1 -1
- package/dist/components/overlays/Dialog.slots.cjs.map +1 -1
- package/dist/components/overlays/Dialog.slots.mjs +12 -12
- package/dist/components/overlays/Dialog.slots.mjs.map +1 -1
- package/dist/components/overlays/Drawer.cjs.map +1 -1
- package/dist/components/overlays/Drawer.mjs.map +1 -1
- package/dist/components/overlays/Drawer.panel.cjs +1 -1
- package/dist/components/overlays/Drawer.panel.cjs.map +1 -1
- package/dist/components/overlays/Drawer.panel.mjs +97 -81
- package/dist/components/overlays/Drawer.panel.mjs.map +1 -1
- package/dist/components/overlays/Drawer.root.cjs +1 -1
- package/dist/components/overlays/Drawer.root.cjs.map +1 -1
- package/dist/components/overlays/Drawer.root.mjs +34 -31
- package/dist/components/overlays/Drawer.root.mjs.map +1 -1
- package/dist/components/overlays/Popover.cjs +1 -1
- package/dist/components/overlays/Popover.cjs.map +1 -1
- package/dist/components/overlays/Popover.mjs +231 -216
- package/dist/components/overlays/Popover.mjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.cjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.mjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.parts.cjs +1 -1
- package/dist/components/overlays/TeachingPopover.parts.cjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.parts.mjs +199 -177
- package/dist/components/overlays/TeachingPopover.parts.mjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.root.cjs +1 -1
- package/dist/components/overlays/TeachingPopover.root.cjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.root.mjs +93 -92
- package/dist/components/overlays/TeachingPopover.root.mjs.map +1 -1
- package/dist/components/overlays/Tooltip.cjs +1 -1
- package/dist/components/overlays/Tooltip.cjs.map +1 -1
- package/dist/components/overlays/Tooltip.mjs +66 -61
- package/dist/components/overlays/Tooltip.mjs.map +1 -1
- package/dist/components/provider/WaveProvider.cjs +1 -1
- package/dist/components/provider/WaveProvider.cjs.map +1 -1
- package/dist/components/provider/WaveProvider.mjs +26 -23
- package/dist/components/provider/WaveProvider.mjs.map +1 -1
- package/dist/components/table/DataGrid.cjs +1 -1
- package/dist/components/table/DataGrid.cjs.map +1 -1
- package/dist/components/table/DataGrid.context.cjs +2 -0
- package/dist/components/table/DataGrid.context.cjs.map +1 -0
- package/dist/components/table/DataGrid.context.mjs +74 -0
- package/dist/components/table/DataGrid.context.mjs.map +1 -0
- package/dist/components/table/DataGrid.header.cjs +2 -0
- package/dist/components/table/DataGrid.header.cjs.map +1 -0
- package/dist/components/table/DataGrid.header.mjs +168 -0
- package/dist/components/table/DataGrid.header.mjs.map +1 -0
- package/dist/components/table/DataGrid.mjs +488 -591
- package/dist/components/table/DataGrid.mjs.map +1 -1
- package/dist/components/table/DataGrid.sizing.cjs +2 -0
- package/dist/components/table/DataGrid.sizing.cjs.map +1 -0
- package/dist/components/table/DataGrid.sizing.mjs +187 -0
- package/dist/components/table/DataGrid.sizing.mjs.map +1 -0
- package/dist/components/table/DataGrid.store.cjs +2 -0
- package/dist/components/table/DataGrid.store.cjs.map +1 -0
- package/dist/components/table/DataGrid.store.mjs +108 -0
- package/dist/components/table/DataGrid.store.mjs.map +1 -0
- package/dist/components/table/DataGrid.window.cjs +2 -0
- package/dist/components/table/DataGrid.window.cjs.map +1 -0
- package/dist/components/table/DataGrid.window.mjs +165 -0
- package/dist/components/table/DataGrid.window.mjs.map +1 -0
- package/dist/components/table/Table.cjs +1 -1
- package/dist/components/table/Table.cjs.map +1 -1
- package/dist/components/table/Table.mjs +74 -72
- package/dist/components/table/Table.mjs.map +1 -1
- package/dist/components/table/Table.resize.cjs +2 -0
- package/dist/components/table/Table.resize.cjs.map +1 -0
- package/dist/components/table/Table.resize.mjs +98 -0
- package/dist/components/table/Table.resize.mjs.map +1 -0
- package/dist/components/table/useGridNavigation.cjs +1 -1
- package/dist/components/table/useGridNavigation.cjs.map +1 -1
- package/dist/components/table/useGridNavigation.mjs +343 -140
- package/dist/components/table/useGridNavigation.mjs.map +1 -1
- package/dist/components/table/useTableColumnSizing.cjs +2 -0
- package/dist/components/table/useTableColumnSizing.cjs.map +1 -0
- package/dist/components/table/useTableColumnSizing.mjs +76 -0
- package/dist/components/table/useTableColumnSizing.mjs.map +1 -0
- package/dist/components/table/useTableFeatures.cjs +2 -0
- package/dist/components/table/useTableFeatures.cjs.map +1 -0
- package/dist/components/table/useTableFeatures.mjs +110 -0
- package/dist/components/table/useTableFeatures.mjs.map +1 -0
- package/dist/components/table/useTableSelection.cjs +2 -0
- package/dist/components/table/useTableSelection.cjs.map +1 -0
- package/dist/components/table/useTableSelection.mjs +39 -0
- package/dist/components/table/useTableSelection.mjs.map +1 -0
- package/dist/components/table/useTableSort.cjs +2 -0
- package/dist/components/table/useTableSort.cjs.map +1 -0
- package/dist/components/table/useTableSort.mjs +58 -0
- package/dist/components/table/useTableSort.mjs.map +1 -0
- package/dist/hooks/useActiveDescendant.cjs +1 -1
- package/dist/hooks/useActiveDescendant.cjs.map +1 -1
- package/dist/hooks/useActiveDescendant.mjs +33 -25
- package/dist/hooks/useActiveDescendant.mjs.map +1 -1
- package/dist/hooks/useCollapsePresence.cjs +2 -0
- package/dist/hooks/useCollapsePresence.cjs.map +1 -0
- package/dist/hooks/useCollapsePresence.mjs +21 -0
- package/dist/hooks/useCollapsePresence.mjs.map +1 -0
- package/dist/hooks/useFocusBeforeClose.cjs +2 -0
- package/dist/hooks/useFocusBeforeClose.cjs.map +1 -0
- package/dist/hooks/useFocusBeforeClose.mjs +33 -0
- package/dist/hooks/useFocusBeforeClose.mjs.map +1 -0
- package/dist/hooks/useListbox.cjs +1 -1
- package/dist/hooks/useListbox.cjs.map +1 -1
- package/dist/hooks/useListbox.mjs +140 -130
- package/dist/hooks/useListbox.mjs.map +1 -1
- package/dist/hooks/useMotion.cjs +2 -0
- package/dist/hooks/useMotion.cjs.map +1 -0
- package/dist/hooks/useMotion.mjs +14 -0
- package/dist/hooks/useMotion.mjs.map +1 -0
- package/dist/hooks/usePresenceGroup.cjs +2 -0
- package/dist/hooks/usePresenceGroup.cjs.map +1 -0
- package/dist/hooks/usePresenceGroup.mjs +68 -0
- package/dist/hooks/usePresenceGroup.mjs.map +1 -0
- package/dist/hooks/useRovingTabIndex.cjs +1 -1
- package/dist/hooks/useRovingTabIndex.cjs.map +1 -1
- package/dist/hooks/useRovingTabIndex.mjs +1 -1
- package/dist/hooks/useRovingTabIndex.mjs.map +1 -1
- package/dist/hooks/useSelection.cjs +2 -0
- package/dist/hooks/useSelection.cjs.map +1 -0
- package/dist/hooks/useSelection.mjs +57 -0
- package/dist/hooks/useSelection.mjs.map +1 -0
- package/dist/hooks/useVirtualWindow.cjs +2 -0
- package/dist/hooks/useVirtualWindow.cjs.map +1 -0
- package/dist/hooks/useVirtualWindow.mjs +102 -0
- package/dist/hooks/useVirtualWindow.mjs.map +1 -0
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +2249 -179
- package/dist/index.d.ts +2249 -179
- package/dist/index.mjs +147 -135
- package/dist/lib/classNames.cjs +1 -1
- package/dist/lib/classNames.cjs.map +1 -1
- package/dist/lib/classNames.mjs +125 -95
- package/dist/lib/classNames.mjs.map +1 -1
- package/dist/lib/columnSizing.cjs +2 -0
- package/dist/lib/columnSizing.cjs.map +1 -0
- package/dist/lib/columnSizing.mjs +27 -0
- package/dist/lib/columnSizing.mjs.map +1 -0
- package/dist/lib/flatTree.cjs +2 -0
- package/dist/lib/flatTree.cjs.map +1 -0
- package/dist/lib/flatTree.mjs +118 -0
- package/dist/lib/flatTree.mjs.map +1 -0
- package/dist/lib/motion.cjs +2 -0
- package/dist/lib/motion.cjs.map +1 -0
- package/dist/lib/motion.mjs +43 -0
- package/dist/lib/motion.mjs.map +1 -0
- package/dist/lib/selection.cjs +2 -0
- package/dist/lib/selection.cjs.map +1 -0
- package/dist/lib/selection.mjs +28 -0
- package/dist/lib/selection.mjs.map +1 -0
- package/dist/lib/treeCascade.cjs +2 -0
- package/dist/lib/treeCascade.cjs.map +1 -0
- package/dist/lib/treeCascade.mjs +52 -0
- package/dist/lib/treeCascade.mjs.map +1 -0
- package/dist/lib/virtual.cjs +2 -0
- package/dist/lib/virtual.cjs.map +1 -0
- package/dist/lib/virtual.mjs +54 -0
- package/dist/lib/virtual.mjs.map +1 -0
- package/dist/styles.css +1 -1
- package/package.json +2 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Drawer.panel.mjs","names":["InlinePanel","React","useDrawerOpen","isClient","useIsClient","type","openState","getDrawerSizeAxis","position","drawerSizeClasses","drawerEdgeClasses","overlayPlacementClasses","getOverlayInsetClasses","size","getOverlayPanelClasses","inlinePanelClasses","forcedColors","getInlinePanelClasses","axis","OVERLAY_PANEL_CLASSES","DrawerPanel","rest","inline","overlay","nonModal","modalType","nonModalOverlay","keptMounted","unmountOnClose","presenceRef","usePresence","open","overlayPanel","setOverlayPanel","inlinePanel","setInlinePanel","panelRef","attachOverlayPanel","node","attachInlinePanel","overlayRef","useMergedRefs","ref","inlineRef","trigger","portalRef","backdropPress","useBackdropPress","onDismiss","useModalDismiss","requestOpen","componentName","layer","useModalLayer","opener","useModalOpener","onTabOrderKeyDown","usePopoverTabOrder","getTabbableThrough","backdropIgnored","backdrop","warnOnce","coversUsablePage","isMounted","inlineAs","separator","presenceProps","cn","rootClassName","className","Portal","ModalBackdrop","backdropClassName","composeEventHandlers","onKeyDown"],"sources":["../../../src/components/overlays/Drawer.panel.tsx"],"sourcesContent":["import * as React from 'react';\nimport { cn } from '../../lib/cn';\nimport { composeEventHandlers } from '../../lib/composeEventHandlers';\nimport { warnOnce } from '../../lib/dev';\nimport type { Slot, SlotObject } from '../../lib/slot';\nimport { forcedColors } from '../../lib/styles';\nimport type { BackdropAppearance, ModalType } from '../../lib/types';\nimport { useIsClient } from '../../hooks/useIsClient';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { useModalLayer } from '../../hooks/useModalLayer';\nimport { usePresence } from '../../hooks/usePresence';\nimport { useRestoreFocus } from '../../hooks/useRestoreFocus';\nimport { Portal } from '../portal/Portal';\nimport {\n useBackdropPress,\n useModalDismiss,\n useModalOpener,\n useOpenInsideWarning,\n useRaiseOnOpen,\n type ModalRequestOpen,\n type ModalTrigger,\n} from './Dialog.shared';\nimport { ModalBackdrop } from './Dialog.slots';\nimport type { DrawerPosition, DrawerSize, DrawerType } from './Drawer.context';\nimport { getTabbableThrough, usePopoverTabOrder } from './Popover.shared';\n\n/*\n * The drawer panel shell (D108): the panel element of both drawer types with its machinery, its\n * open state, and its placement, size and safe-area classes. Drawer's root and NavDrawer render it.\n * Imports the context module only among the Drawer modules (never the root, the parts or\n * `Drawer.tsx`), and no Nav module.\n */\n\n/**\n * The open state a drawer reports (its triggers' `aria-expanded`, its contexts): an inline\n * drawer's state as it is; an overlay's `false` until the page has hydrated (the portal renders\n * only in the browser), so the server HTML never points `aria-controls` at a panel that is not\n * there.\n */\nexport function useDrawerOpen(type: DrawerType, openState: boolean): boolean {\n const isClient = useIsClient();\n return type === 'inline' ? openState : openState && isClient;\n}\n\n/** The axis a drawer's `size` applies to: the width at a side, the height at the bottom. */\ntype DrawerSizeAxis = 'width' | 'height';\n\n/** The axis `size` sets for a drawer at `position`. */\nfunction getDrawerSizeAxis(position: DrawerPosition): DrawerSizeAxis {\n return position === 'bottom' ? 'height' : 'width';\n}\n\n/**\n * The size classes, keyed by axis: 320px, 592px and 940px on the spacing scale (rem, so they\n * follow the user's font size), and `full` the whole axis. A width (height) class in the\n * consumer's `className` replaces the size, as the consumer's class comes last in `cn()`.\n */\nconst drawerSizeClasses: Readonly<Record<DrawerSizeAxis, Readonly<Record<DrawerSize, string>>>> = {\n width: { small: 'w-80', medium: 'w-148', large: 'w-235', full: 'w-full' },\n height: { small: 'h-80', medium: 'h-148', large: 'h-235', full: 'h-full' },\n};\n\n/**\n * A border on the panel's inner edge (the one facing the page): it marks the panel where the\n * shadow cannot, in high contrast (page, backdrop and panel are black) and in forced colors\n * (which drop shadows).\n */\nconst drawerEdgeClasses: Readonly<Record<DrawerPosition, string>> = {\n start: 'border-e',\n end: 'border-s',\n left: 'border-r', // wave-allow-physical: the consumer asked for the physical left edge\n right: 'border-l', // wave-allow-physical: the consumer asked for the physical right edge\n bottom: 'border-t',\n};\n\n/**\n * Where an overlay panel is pinned: a side panel spans the window's height, a bottom one its\n * width; neither grows past the window (a size larger than the screen acts as `full`).\n */\nconst overlayPlacementClasses: Readonly<Record<DrawerPosition, string>> = {\n start: 'start-0 top-0 h-full max-w-full',\n end: 'end-0 top-0 h-full max-w-full',\n left: 'left-0 top-0 h-full max-w-full', // wave-allow-physical: the consumer asked for the physical left edge\n right: 'right-0 top-0 h-full max-w-full', // wave-allow-physical: the consumer asked for the physical right edge\n bottom: 'inset-x-0 bottom-0 w-full max-h-full',\n};\n\n/**\n * The safe-area insets of the screen edges an overlay panel touches (the iOS home indicator, a\n * notch; `0` unless the page sets `viewport-fit=cover`). The panel has no padding of its own, so\n * the inset is the whole padding. A side panel touches the top and bottom edges; a bottom panel\n * the bottom edge, and the top one too at `full`. The side insets (a landscape notch) are not\n * padded.\n */\nfunction getOverlayInsetClasses(position: DrawerPosition, size: DrawerSize): string {\n if (position === 'bottom' && size !== 'full') return 'pb-[env(safe-area-inset-bottom)]';\n return 'pt-[env(safe-area-inset-top)] pb-[env(safe-area-inset-bottom)]';\n}\n\n/**\n * The classes that place and size an overlay panel at `position`: the placement, the inner-edge\n * border, the size on the position's axis and the safe-area insets. They go after the panel's\n * base classes and before the consumer's `className`.\n */\nfunction getOverlayPanelClasses(position: DrawerPosition, size: DrawerSize): string {\n return [\n overlayPlacementClasses[position],\n drawerEdgeClasses[position],\n drawerSizeClasses[getDrawerSizeAxis(position)][size],\n getOverlayInsetClasses(position, size),\n ].join(' ');\n}\n\n/**\n * The base classes of an inline panel: an element of the page layout that keeps its width in a\n * flex row and lets its body scroll once the layout bounds its height. Its inner edge is\n * transparent unless the Drawer has `separator` (`data-separator`), and always drawn in forced\n * colors.\n */\nconst inlinePanelClasses = [\n 'relative flex min-h-0 shrink-0 flex-col max-w-full bg-background text-foreground',\n 'border-transparent data-[separator]:border-border',\n forcedColors.border,\n].join(' ');\n\n/**\n * The classes that place and size an inline panel at `position`: the inner-edge border and the\n * size on the position's axis (a bottom panel is as wide as its container and never taller than\n * it). `full` is the container's width (height). No placement, insets or shadow: where the panel\n * sits is up to the page layout. They go after {@link inlinePanelClasses} and before the\n * consumer's `className`.\n */\nfunction getInlinePanelClasses(position: DrawerPosition, size: DrawerSize): string {\n const axis = getDrawerSizeAxis(position);\n return [\n drawerEdgeClasses[position],\n axis === 'height' ? 'w-full max-h-full' : '',\n drawerSizeClasses[axis][size],\n ]\n .filter(Boolean)\n .join(' ');\n}\n\n/** What the drawer panel shell renders and wires (the frozen contract of D108). */\nexport interface DrawerPanelProps extends Omit<React.HTMLAttributes<HTMLElement>, 'children'> {\n /**\n * The public component, for the warning keys and texts: `'Drawer'`, `'NavDrawer'`\n * (`<componentName>:open-inside`, `:backdrop-ignored`, `:focus-outside`, `:non-modal-full`).\n */\n componentName: string;\n /**\n * `'overlay'`: a portal, the backdrop, `role=\"dialog\"` and the modal or non-modal machinery;\n * `'inline'`: the panel in place, with the inline focus restore only.\n */\n type: DrawerType;\n /** The reported open state, from {@link useDrawerOpen}. */\n open: boolean;\n /** The root's request function (`useModalOpenState`): Escape and the backdrop ask through it. */\n requestOpen: ModalRequestOpen;\n /** Rendered as `data-position`; picks the overlay's edge or the inline panel's inner edge. */\n position: DrawerPosition;\n /** Rendered as `data-size` (always: the component resolves its own default). */\n size: DrawerSize;\n /** Inline only: draws the inner edge (`data-separator`). Ignored by an overlay. */\n separator: boolean;\n /**\n * Overlay only: `modal`, `alert` or `non-modal` (`data-modal-type`, the role and the layer kind).\n * Ignored inline.\n */\n modalType: ModalType;\n /** `false` keeps the panel mounted while closed, `hidden` and `inert`. */\n unmountOnClose: boolean;\n /**\n * The element of an inline panel: `'aside'` (Drawer, a complementary landmark) or `'div'`\n * (NavDrawer, whose `<nav>` is the landmark).\n */\n inlineAs: 'aside' | 'div';\n /**\n * The root's triggers (`useModalTrigger()`), or `inertModalTrigger` for a component without\n * trigger parts (the layer and the inline restore then capture the element that had focus).\n */\n trigger: ModalTrigger;\n /** Where focus goes when the panel closes, if it can take focus (the root's `finalFocusRef`). */\n finalFocusRef?: React.RefObject<HTMLElement | null>;\n /**\n * The panel's stable class(es), first in its `cn()`: `drawerClassNames.root`, followed by a\n * variant's root (`cn(drawerClassNames.root, navDrawerClassNames.root)`).\n */\n rootClassName: string;\n /**\n * The backdrop's stable class(es), first in its `cn()`: `drawerClassNames.backdrop`, followed by\n * a variant's (`cn(drawerClassNames.backdrop, navDrawerClassNames.backdrop)`).\n */\n backdropClassName: string;\n /**\n * The `backdrop` slot (overlay `modal` and `alert` only; a slot on a non-modal or inline panel\n * renders nothing and warns). `null` renders no backdrop.\n */\n backdrop?: Slot<'div'> | (SlotObject<'div'> & { appearance?: BackdropAppearance });\n /** The panel's id (always set: triggers point `aria-controls` at it). */\n id: string;\n /** Merged with the shell's own ref and the presence ref. */\n ref?: React.Ref<HTMLElement>;\n /** The panel's content, rendered as is: the shell adds no header, Close button or padding. */\n children?: React.ReactNode;\n}\n\n/**\n * The classes every overlay panel carries after its stable class: a fixed flex column on the\n * page's background with the overlay shadow, its inner edge in the border colour.\n */\nconst OVERLAY_PANEL_CLASSES =\n 'fixed flex flex-col border-border bg-background text-foreground shadow-64';\n\n/**\n * The drawer panel shell: the panel element of an overlay (in a portal, with its backdrop and the\n * modal or non-modal machinery) or of an inline drawer (in place, with the inline focus restore),\n * on the presence core, with the placement, size, separator and safe-area classes and the\n * `data-type`, `data-position`, `data-size`, `data-modal-type`, `data-separator` and\n * `data-presence` attributes. Returns `null` while unmounted. Its hooks key on `open`.\n *\n * It renders its `children` raw and provides no context: no header, title registry, Close button\n * or padding. The component that renders it holds the open state (`useModalOpenState`, then\n * {@link useDrawerOpen}), renders its triggers itself, names the panel, and calls\n * `useModalTriggerSession(trigger, open)` after rendering it (the shell's effects run first). A\n * change of `type` remounts the panel and its content.\n */\nexport const DrawerPanel = ({\n componentName,\n type,\n open,\n requestOpen,\n position,\n size,\n separator,\n modalType,\n unmountOnClose,\n inlineAs,\n trigger,\n finalFocusRef,\n rootClassName,\n backdropClassName,\n backdrop,\n id,\n className,\n onKeyDown,\n ref,\n children,\n ...rest\n}: DrawerPanelProps): React.ReactNode => {\n const inline = type === 'inline';\n const overlay = !inline;\n const nonModal = modalType === 'non-modal';\n const nonModalOverlay = overlay && nonModal;\n const keptMounted = !unmountOnClose;\n // The panel mounts through the presence core (D5, D103), with no motion of its own: kept mounted\n // while closed with `unmountOnClose={false}`, else removed once it has exited.\n const {\n isMounted,\n ref: presenceRef,\n presenceProps,\n } = usePresence(open, { unmountOnExit: unmountOnClose });\n\n // The panel element of each type, held in state through its own callback ref. A change of `type`\n // remounts the panel (D105): the overlay's hooks see only the portaled element and the inline\n // restore only the inline one, also in the commit that swaps them (the inline restore then still\n // knows the panel that focus was lost from).\n const [overlayPanel, setOverlayPanel] = React.useState<HTMLElement | null>(null);\n const [inlinePanel, setInlinePanel] = React.useState<HTMLElement | null>(null);\n // The mounted panel of either type; each element clears it only while it is still the one held.\n const panelRef = React.useRef<HTMLElement | null>(null);\n const attachOverlayPanel = React.useCallback((node: HTMLElement | null) => {\n if (!node) return undefined;\n panelRef.current = node;\n setOverlayPanel(node);\n return () => {\n if (panelRef.current === node) panelRef.current = null;\n setOverlayPanel(null);\n };\n }, []);\n const attachInlinePanel = React.useCallback((node: HTMLElement | null) => {\n if (!node) return undefined;\n panelRef.current = node;\n setInlinePanel(node);\n return () => {\n if (panelRef.current === node) panelRef.current = null;\n setInlinePanel(null);\n };\n }, []);\n const overlayRef = useMergedRefs<HTMLElement>(ref, attachOverlayPanel, presenceRef);\n const inlineRef = useMergedRefs<HTMLElement>(ref, attachInlinePanel, presenceRef);\n\n // An inline panel takes no focus on open and returns it on close only from inside (D101). Called\n // before useModalLayer: on a switch from inline to overlay it restores before the overlay's trap\n // moves focus in.\n useRestoreFocus({\n enabled: open && inline,\n container: inlinePanel,\n triggerRef: trigger.focusRef,\n finalFocusRef,\n requireFocusInside: true,\n });\n // The portal wrapper: a kept-mounted overlay moves to the top of its stack when it opens (D104),\n // before the layer registers and the trap moves focus in.\n const portalRef = React.useRef<HTMLDivElement | null>(null);\n useRaiseOnOpen(open && overlay, keptMounted, portalRef);\n\n // A backdrop press asks to close, except an alert's (Escape still does; useModalLayer registers\n // its layer without outside presses).\n const backdropPress = useBackdropPress(panelRef, modalType !== 'alert');\n const onDismiss = useModalDismiss(requestOpen, componentName, backdropPress.afterOutsidePress);\n // Only an overlay is a layer: an inline panel is page content (no trap, isolation, scroll lock,\n // Escape or outside press; toasts keep their corner). The overlay's layer is the one the Toaster\n // measures (`modal`, or `dialog` for a non-modal one).\n const layer = useModalLayer({\n open: open && overlay,\n modalType,\n onDismiss,\n refs: [panelRef],\n container: overlayPanel,\n triggerRef: trigger.focusRef,\n finalFocusRef,\n });\n // A non-modal overlay keeps its place in the page's keyboard order right after its opener\n // (D87.5). Both hooks are always called (C-HOOKS, D91). The opener is captured whenever the\n // overlay opens, so a modal panel that turns non-modal while open (focus inside it by then)\n // still knows it.\n const opener = useModalOpener(open && overlay, trigger, overlayPanel);\n const onTabOrderKeyDown = usePopoverTabOrder({\n enabled: open && nonModalOverlay,\n surface: overlayPanel,\n anchorRef: opener,\n getPreviousStop: getTabbableThrough,\n });\n // A popup opened inside a kept-mounted panel that is still open when the panel closes (D106).\n useOpenInsideWarning(open, keptMounted, layer.layerId, componentName, panelRef);\n // A non-modal or inline panel has no backdrop: a given slot (not undefined, null or a boolean)\n // is ignored.\n const backdropIgnored =\n (nonModal || inline) &&\n backdrop !== undefined &&\n backdrop !== null &&\n typeof backdrop !== 'boolean';\n React.useEffect(() => {\n if (!backdropIgnored) return;\n warnOnce(\n `${componentName}:backdrop-ignored`,\n `${componentName}: \\`backdrop\\` is ignored: a non-modal or inline drawer has no backdrop, so the page around it stays usable.`,\n );\n }, [backdropIgnored, componentName]);\n // A full non-modal overlay covers the page it leaves usable (D87.8).\n const coversUsablePage = open && nonModalOverlay && size === 'full';\n React.useEffect(() => {\n if (!coversUsablePage) return;\n warnOnce(\n `${componentName}:non-modal-full`,\n `${componentName}: \\`size=\"full\"\\` with \\`modalType=\"non-modal\"\\` covers the whole page while leaving it usable, so Tab reaches controls hidden behind the drawer. Use \\`modalType=\"modal\"\\`, \\`type=\"inline\"\\`, or a smaller size with its room reserved in the page layout.`,\n );\n }, [coversUsablePage, componentName]);\n\n if (!isMounted) return null;\n\n if (inline) {\n const InlinePanel = inlineAs;\n // In place: no role, tabIndex or modal attributes (D100). The presence attributes come after\n // the consumer's props: hidden and inert while kept closed.\n return (\n <InlinePanel\n ref={inlineRef}\n id={id}\n data-type=\"inline\"\n data-position={position}\n data-size={size}\n data-separator={separator ? '' : undefined}\n {...rest}\n {...presenceProps}\n onKeyDown={onKeyDown}\n className={cn(\n rootClassName,\n inlinePanelClasses,\n getInlinePanelClasses(position, size),\n className,\n )}\n >\n {children}\n </InlinePanel>\n );\n }\n\n return (\n <Portal ref={portalRef} layerId={layer.layerId}>\n {/* The backdrop of a modal or alert panel, the panel's sibling; a non-modal one has none.\n Both carry the presence attributes (D7, D103): hidden and inert while kept closed, so a\n closed panel leaves no backdrop over the page. */}\n {!nonModal && (\n <ModalBackdrop\n backdrop={backdrop}\n className={backdropClassName}\n layerId={layer.layerId}\n open={open}\n onMouseDown={backdropPress.onMouseDown}\n presenceProps={presenceProps}\n />\n )}\n <div\n ref={overlayRef}\n role={modalType === 'alert' ? 'alertdialog' : 'dialog'}\n id={id}\n tabIndex={-1}\n data-type=\"overlay\"\n data-position={position}\n data-size={size}\n data-modal-type={modalType}\n {...rest}\n {...presenceProps}\n onKeyDown={composeEventHandlers(onKeyDown, onTabOrderKeyDown)}\n className={cn(\n rootClassName,\n OVERLAY_PANEL_CLASSES,\n getOverlayPanelClasses(position, size),\n className,\n )}\n >\n {children}\n </div>\n </Portal>\n );\n};\nDrawerPanel.displayName = 'DrawerPanel';\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"Drawer.panel.mjs","names":["React","useDrawerOpen","isClient","useIsClient","type","openState","getDrawerSizeAxis","position","drawerSizeClasses","drawerEdgeClasses","overlayPlacementClasses","getOverlayInsetClasses","size","getOverlayPanelClasses","inlinePanelClasses","forcedColors","getInlinePanelClasses","axis","OVERLAY_PANEL_CLASSES","DrawerPanel","rest","inline","overlay","nonModal","modalType","nonModalOverlay","keptMounted","unmountOnClose","presenceRef","usePresence","open","panelMotion","useMotionClasses","motion","inlineDrawerMotion","drawerDurations","drawerMotion","className","backdropMotionClassName","backdropMotion","drawerBackdropMotion","legacyMotion","usesLegacyMotion","overlayPanel","setOverlayPanel","inlinePanel","setInlinePanel","panelRef","attachOverlayPanel","node","attachInlinePanel","overlayRef","useMergedRefs","ref","inlineRef","trigger","portalRef","backdropPress","useBackdropPress","onDismiss","useModalDismiss","requestOpen","componentName","layer","useModalLayer","opener","useModalOpener","onTabOrderKeyDown","usePopoverTabOrder","getTabbableThrough","backdropIgnored","backdrop","warnOnce","coversUsablePage","isMounted","InlinePanel","inlineAs","presenceProps","cn","collapseClassName","inlineDrawerStructure","separator","rootClassName","Portal","ModalBackdrop","backdropClassName","composeEventHandlers","onKeyDown"],"sources":["../../../src/components/overlays/Drawer.panel.tsx"],"sourcesContent":["import * as React from 'react';\nimport { cn } from '../../lib/cn';\nimport { composeEventHandlers } from '../../lib/composeEventHandlers';\nimport { warnOnce } from '../../lib/dev';\nimport {\n drawerBackdropMotion,\n drawerDurations,\n drawerMotion,\n inlineDrawerMotion,\n inlineDrawerStructure,\n usesLegacyMotion,\n} from '../../lib/motion';\nimport type { Slot, SlotObject } from '../../lib/slot';\nimport { forcedColors } from '../../lib/styles';\nimport type { BackdropAppearance, ModalType, MotionSlot } from '../../lib/types';\nimport { useIsClient } from '../../hooks/useIsClient';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { useModalLayer } from '../../hooks/useModalLayer';\nimport { useMotionClasses } from '../../hooks/useMotion';\nimport { usePresence } from '../../hooks/usePresence';\nimport { useRestoreFocus } from '../../hooks/useRestoreFocus';\nimport { Portal } from '../portal/Portal';\nimport {\n useBackdropPress,\n useModalDismiss,\n useModalOpener,\n useOpenInsideWarning,\n useRaiseOnOpen,\n type ModalRequestOpen,\n type ModalTrigger,\n} from './Dialog.shared';\nimport { ModalBackdrop } from './Dialog.slots';\nimport type { DrawerPosition, DrawerSize, DrawerType } from './Drawer.context';\nimport { getTabbableThrough, usePopoverTabOrder } from './Popover.shared';\n\n/*\n * The drawer panel shell (D108): the panel element of both drawer types with its machinery, its\n * open state, and its placement, size and safe-area classes. Drawer's root and NavDrawer render it.\n * Imports the context module only among the Drawer modules (never the root, the parts or\n * `Drawer.tsx`), and no Nav module.\n */\n\n/**\n * The open state a drawer reports (its triggers' `aria-expanded`, its contexts): an inline\n * drawer's state as it is; an overlay's `false` until the page has hydrated (the portal renders\n * only in the browser), so the server HTML never points `aria-controls` at a panel that is not\n * there.\n */\nexport function useDrawerOpen(type: DrawerType, openState: boolean): boolean {\n const isClient = useIsClient();\n return type === 'inline' ? openState : openState && isClient;\n}\n\n/** The axis a drawer's `size` applies to: the width at a side, the height at the bottom. */\ntype DrawerSizeAxis = 'width' | 'height';\n\n/** The axis `size` sets for a drawer at `position`. */\nfunction getDrawerSizeAxis(position: DrawerPosition): DrawerSizeAxis {\n return position === 'bottom' ? 'height' : 'width';\n}\n\n/**\n * The size classes, keyed by axis: 320px, 592px and 940px on the spacing scale (rem, so they\n * follow the user's font size), and `full` the whole axis. A width (height) class in the\n * consumer's `className` replaces the size, as the consumer's class comes last in `cn()`.\n */\nconst drawerSizeClasses: Readonly<Record<DrawerSizeAxis, Readonly<Record<DrawerSize, string>>>> = {\n width: { small: 'w-80', medium: 'w-148', large: 'w-235', full: 'w-full' },\n height: { small: 'h-80', medium: 'h-148', large: 'h-235', full: 'h-full' },\n};\n\n/**\n * A border on the panel's inner edge (the one facing the page): it marks the panel where the\n * shadow cannot, in high contrast (page, backdrop and panel are black) and in forced colors\n * (which drop shadows).\n */\nconst drawerEdgeClasses: Readonly<Record<DrawerPosition, string>> = {\n start: 'border-e',\n end: 'border-s',\n left: 'border-r', // wave-allow-physical: the consumer asked for the physical left edge\n right: 'border-l', // wave-allow-physical: the consumer asked for the physical right edge\n bottom: 'border-t',\n};\n\n/**\n * Where an overlay panel is pinned: a side panel spans the window's height, a bottom one its\n * width; neither grows past the window (a size larger than the screen acts as `full`).\n */\nconst overlayPlacementClasses: Readonly<Record<DrawerPosition, string>> = {\n start: 'start-0 top-0 h-full max-w-full',\n end: 'end-0 top-0 h-full max-w-full',\n left: 'left-0 top-0 h-full max-w-full', // wave-allow-physical: the consumer asked for the physical left edge\n right: 'right-0 top-0 h-full max-w-full', // wave-allow-physical: the consumer asked for the physical right edge\n bottom: 'inset-x-0 bottom-0 w-full max-h-full',\n};\n\n/**\n * The safe-area insets of the screen edges an overlay panel touches (the iOS home indicator, a\n * notch; `0` unless the page sets `viewport-fit=cover`). The panel has no padding of its own, so\n * the inset is the whole padding. A side panel touches the top and bottom edges; a bottom panel\n * the bottom edge, and the top one too at `full`. The side insets (a landscape notch) are not\n * padded.\n */\nfunction getOverlayInsetClasses(position: DrawerPosition, size: DrawerSize): string {\n if (position === 'bottom' && size !== 'full') return 'pb-[env(safe-area-inset-bottom)]';\n return 'pt-[env(safe-area-inset-top)] pb-[env(safe-area-inset-bottom)]';\n}\n\n/**\n * The classes that place and size an overlay panel at `position`: the placement, the inner-edge\n * border, the size on the position's axis and the safe-area insets. They go after the panel's\n * base classes and before the consumer's `className`.\n */\nfunction getOverlayPanelClasses(position: DrawerPosition, size: DrawerSize): string {\n return [\n overlayPlacementClasses[position],\n drawerEdgeClasses[position],\n drawerSizeClasses[getDrawerSizeAxis(position)][size],\n getOverlayInsetClasses(position, size),\n ].join(' ');\n}\n\n/**\n * The base classes of an inline panel: an element of the page layout that keeps its width in a\n * flex row and lets its body scroll once the layout bounds its height. Its inner edge is\n * transparent unless the Drawer has `separator` (`data-separator`), and always drawn in forced\n * colors.\n */\nconst inlinePanelClasses = [\n 'relative flex min-h-0 shrink-0 flex-col max-w-full bg-background text-foreground',\n 'border-transparent data-[separator]:border-border',\n forcedColors.border,\n].join(' ');\n\n/**\n * The classes that place and size an inline panel at `position`: the inner-edge border and the\n * size on the position's axis (a bottom panel is as wide as its container and never taller than\n * it). `full` is the container's width (height). No placement, insets or shadow: where the panel\n * sits is up to the page layout. They go after {@link inlinePanelClasses} and before the\n * consumer's `className`.\n */\nfunction getInlinePanelClasses(position: DrawerPosition, size: DrawerSize): string {\n const axis = getDrawerSizeAxis(position);\n return [\n drawerEdgeClasses[position],\n axis === 'height' ? 'w-full max-h-full' : '',\n drawerSizeClasses[axis][size],\n ]\n .filter(Boolean)\n .join(' ');\n}\n\n/** What the drawer panel shell renders and wires (the frozen contract of D108). */\nexport interface DrawerPanelProps extends Omit<React.HTMLAttributes<HTMLElement>, 'children'> {\n /**\n * The public component, for the warning keys and texts: `'Drawer'`, `'NavDrawer'`\n * (`<componentName>:open-inside`, `:backdrop-ignored`, `:focus-outside`, `:non-modal-full`).\n */\n componentName: string;\n /**\n * `'overlay'`: a portal, the backdrop, `role=\"dialog\"` and the modal or non-modal machinery;\n * `'inline'`: the panel in place, with the inline focus restore only.\n */\n type: DrawerType;\n /** The reported open state, from {@link useDrawerOpen}. */\n open: boolean;\n /** The root's request function (`useModalOpenState`): Escape and the backdrop ask through it. */\n requestOpen: ModalRequestOpen;\n /** Rendered as `data-position`; picks the overlay's edge or the inline panel's inner edge. */\n position: DrawerPosition;\n /** Rendered as `data-size` (always: the component resolves its own default). */\n size: DrawerSize;\n /** Inline only: draws the inner edge (`data-separator`). Ignored by an overlay. */\n separator: boolean;\n /**\n * Overlay only: `modal`, `alert` or `non-modal` (`data-modal-type`, the role and the layer kind).\n * Ignored inline.\n */\n modalType: ModalType;\n /** `false` keeps the panel mounted while closed, `hidden` and `inert`. */\n unmountOnClose: boolean;\n /**\n * The element of an inline panel: `'aside'` (Drawer, a complementary landmark) or `'div'`\n * (NavDrawer, whose `<nav>` is the landmark).\n */\n inlineAs: 'aside' | 'div';\n /**\n * The root's triggers (`useModalTrigger()`), or `inertModalTrigger` for a component without\n * trigger parts (the layer and the inline restore then capture the element that had focus).\n */\n trigger: ModalTrigger;\n /** Where focus goes when the panel closes, if it can take focus (the root's `finalFocusRef`). */\n finalFocusRef?: React.RefObject<HTMLElement | null>;\n /**\n * The panel's stable class(es), first in its `cn()`: `drawerClassNames.root`, followed by a\n * variant's root (`cn(drawerClassNames.root, navDrawerClassNames.root)`).\n */\n rootClassName: string;\n /**\n * The backdrop's stable class(es), first in its `cn()`: `drawerClassNames.backdrop`, followed by\n * a variant's (`cn(drawerClassNames.backdrop, navDrawerClassNames.backdrop)`).\n */\n backdropClassName: string;\n /**\n * The stable class(es) of the collapse element around an inline panel, first in its `cn()`:\n * `drawerClassNames.collapse`, followed by a variant's\n * (`cn(drawerClassNames.collapse, navDrawerClassNames.collapse)`). Unused by an overlay.\n */\n collapseClassName: string;\n /**\n * The `backdrop` slot (overlay `modal` and `alert` only; a slot on a non-modal or inline panel\n * renders nothing and warns). `null` renders no backdrop.\n */\n backdrop?: Slot<'div'> | (SlotObject<'div'> & { appearance?: BackdropAppearance });\n /**\n * The panel's motion slot: `undefined` the default, `null` none, a value replaces it (see\n * `MotionSlot`). The default of an overlay panel is its slide from its edge, on the panel; the\n * default of an inline panel is the collapse of the element around it (the space it takes opens\n * and closes on its axis, with a fade), on that element, and it is the element a value goes on.\n * Both take the duration of the panel's size. An inline panel at `full` has no motion: its\n * element carries the collapse structure only, also with a value. A `className` with presence\n * variants keeps 0.14's own motion while it is `undefined`: no default, and the presence core\n * waits for the panel element (inline too, rather than for the element around it).\n */\n motion?: MotionSlot | null;\n /**\n * The backdrop's motion slot (overlay `modal` and `alert` only): `undefined` the default fade\n * over the duration of the panel's size, `null` none, a value replaces it. Given on a non-modal\n * or inline panel (`null` included), it is ignored with the `backdrop-ignored` warning.\n */\n backdropMotion?: MotionSlot | null;\n /** The panel's id (always set: triggers point `aria-controls` at it). */\n id: string;\n /** Merged with the shell's own ref and the presence ref. */\n ref?: React.Ref<HTMLElement>;\n /** The panel's content, rendered as is: the shell adds no header, Close button or padding. */\n children?: React.ReactNode;\n}\n\n/**\n * The classes every overlay panel carries after its stable class: a fixed flex column on the\n * page's background with the overlay shadow, its inner edge in the border colour.\n */\nconst OVERLAY_PANEL_CLASSES =\n 'fixed flex flex-col border-border bg-background text-foreground shadow-64';\n\n/**\n * The drawer panel shell: the panel element of an overlay (in a portal, with its backdrop and the\n * modal or non-modal machinery) or of an inline drawer (in place, with the inline focus restore),\n * on the presence core, with the placement, size, separator and safe-area classes and the\n * `data-type`, `data-position`, `data-size`, `data-modal-type`, `data-separator` and\n * `data-presence` attributes. Returns `null` while unmounted. Its hooks key on `open`. An overlay\n * enters also when it mounts open, and its panel and backdrop carry their motion classes\n * (`motion`, `backdropMotion`); the presence core waits for the panel's. An inline panel renders\n * as the only child of a collapse element (`collapseClassName`, D13), which carries the presence\n * attributes too and the inline motion classes, and which the presence core waits for (the panel\n * itself under 0.14's `className` rule); it never enters on mount.\n *\n * It renders its `children` raw and provides no context: no header, title registry, Close button\n * or padding. The component that renders it holds the open state (`useModalOpenState`, then\n * {@link useDrawerOpen}), renders its triggers itself, names the panel, and calls\n * `useModalTriggerSession(trigger, open)` after rendering it (the shell's effects run first). A\n * change of `type` remounts the panel and its content.\n */\nexport const DrawerPanel = ({\n componentName,\n type,\n open,\n requestOpen,\n position,\n size,\n separator,\n modalType,\n unmountOnClose,\n inlineAs,\n trigger,\n finalFocusRef,\n rootClassName,\n backdropClassName,\n collapseClassName,\n backdrop,\n motion,\n backdropMotion,\n id,\n className,\n onKeyDown,\n ref,\n children,\n ...rest\n}: DrawerPanelProps): React.ReactNode => {\n const inline = type === 'inline';\n const overlay = !inline;\n const nonModal = modalType === 'non-modal';\n const nonModalOverlay = overlay && nonModal;\n const keptMounted = !unmountOnClose;\n // The panel mounts through the presence core (D5, D103): kept mounted while closed with\n // `unmountOnClose={false}`, else removed once it has exited. An overlay also enters when it\n // mounts open (D9: an overlay open by default slides in on a client render as after hydration);\n // an inline panel is page content and never animates on mount.\n const {\n isMounted,\n ref: presenceRef,\n presenceProps,\n } = usePresence(open, { appear: overlay, unmountOnExit: unmountOnClose });\n // The motion classes over the size's duration: an overlay panel slides from its edge and its\n // backdrop fades with it; an inline panel's collapse element opens and closes its space on the\n // panel's axis (D13). A `className` with presence variants keeps 0.14's own motion (D19): no\n // default, and inline the presence core waits for the panel rather than its collapse element.\n const panelMotion = useMotionClasses(\n motion,\n inline\n ? `${inlineDrawerMotion[getDrawerSizeAxis(position)]} ${drawerDurations[size]}`\n : `${drawerMotion[position]} ${drawerDurations[size]}`,\n className,\n );\n const backdropMotionClassName = useMotionClasses(backdropMotion, drawerBackdropMotion[size]);\n const legacyMotion = usesLegacyMotion(motion, className);\n\n // The panel element of each type, held in state through its own callback ref. A change of `type`\n // remounts the panel (D105): the overlay's hooks see only the portaled element and the inline\n // restore only the inline one, also in the commit that swaps them (the inline restore then still\n // knows the panel that focus was lost from).\n const [overlayPanel, setOverlayPanel] = React.useState<HTMLElement | null>(null);\n const [inlinePanel, setInlinePanel] = React.useState<HTMLElement | null>(null);\n // The mounted panel of either type; each element clears it only while it is still the one held.\n const panelRef = React.useRef<HTMLElement | null>(null);\n const attachOverlayPanel = React.useCallback((node: HTMLElement | null) => {\n if (!node) return undefined;\n panelRef.current = node;\n setOverlayPanel(node);\n return () => {\n if (panelRef.current === node) panelRef.current = null;\n setOverlayPanel(null);\n };\n }, []);\n const attachInlinePanel = React.useCallback((node: HTMLElement | null) => {\n if (!node) return undefined;\n panelRef.current = node;\n setInlinePanel(node);\n return () => {\n if (panelRef.current === node) panelRef.current = null;\n setInlinePanel(null);\n };\n }, []);\n const overlayRef = useMergedRefs<HTMLElement>(ref, attachOverlayPanel, presenceRef);\n const inlineRef = useMergedRefs<HTMLElement>(\n ref,\n attachInlinePanel,\n legacyMotion ? presenceRef : null,\n );\n\n // An inline panel takes no focus on open and returns it on close only from inside (D101). Called\n // before useModalLayer: on a switch from inline to overlay it restores before the overlay's trap\n // moves focus in.\n useRestoreFocus({\n enabled: open && inline,\n container: inlinePanel,\n triggerRef: trigger.focusRef,\n finalFocusRef,\n requireFocusInside: true,\n });\n // The portal wrapper: a kept-mounted overlay moves to the top of its stack when it opens (D104),\n // before the layer registers and the trap moves focus in.\n const portalRef = React.useRef<HTMLDivElement | null>(null);\n useRaiseOnOpen(open && overlay, keptMounted, portalRef);\n\n // A backdrop press asks to close, except an alert's (Escape still does; useModalLayer registers\n // its layer without outside presses).\n const backdropPress = useBackdropPress(panelRef, modalType !== 'alert');\n const onDismiss = useModalDismiss(requestOpen, componentName, backdropPress.afterOutsidePress);\n // Only an overlay is a layer: an inline panel is page content (no trap, isolation, scroll lock,\n // Escape or outside press; toasts keep their corner). The overlay's layer is the one the Toaster\n // measures (`modal`, or `dialog` for a non-modal one).\n const layer = useModalLayer({\n open: open && overlay,\n modalType,\n onDismiss,\n refs: [panelRef],\n container: overlayPanel,\n triggerRef: trigger.focusRef,\n finalFocusRef,\n });\n // A non-modal overlay keeps its place in the page's keyboard order right after its opener\n // (D87.5). Both hooks are always called (C-HOOKS, D91). The opener is captured whenever the\n // overlay opens, so a modal panel that turns non-modal while open (focus inside it by then)\n // still knows it.\n const opener = useModalOpener(open && overlay, trigger, overlayPanel);\n const onTabOrderKeyDown = usePopoverTabOrder({\n enabled: open && nonModalOverlay,\n surface: overlayPanel,\n anchorRef: opener,\n getPreviousStop: getTabbableThrough,\n });\n // A popup opened inside a kept-mounted panel that is still open when the panel closes (D106).\n useOpenInsideWarning(open, keptMounted, layer.layerId, componentName, panelRef);\n // A non-modal or inline panel has no backdrop: a given slot (not undefined, null or a boolean)\n // and a given backdrop motion (not undefined) are ignored.\n const backdropIgnored =\n (nonModal || inline) &&\n ((backdrop !== undefined && backdrop !== null && typeof backdrop !== 'boolean') ||\n backdropMotion !== undefined);\n React.useEffect(() => {\n if (!backdropIgnored) return;\n warnOnce(\n `${componentName}:backdrop-ignored`,\n `${componentName}: \\`backdrop\\` and \\`backdropMotion\\` are ignored: a non-modal or inline drawer has no backdrop, so the page around it stays usable.`,\n );\n }, [backdropIgnored, componentName]);\n // A full non-modal overlay covers the page it leaves usable (D87.8).\n const coversUsablePage = open && nonModalOverlay && size === 'full';\n React.useEffect(() => {\n if (!coversUsablePage) return;\n warnOnce(\n `${componentName}:non-modal-full`,\n `${componentName}: \\`size=\"full\"\\` with \\`modalType=\"non-modal\"\\` covers the whole page while leaving it usable, so Tab reaches controls hidden behind the drawer. Use \\`modalType=\"modal\"\\`, \\`type=\"inline\"\\`, or a smaller size with its room reserved in the page layout.`,\n );\n }, [coversUsablePage, componentName]);\n\n if (!isMounted) return null;\n\n if (inline) {\n const InlinePanel = inlineAs;\n // In place, in its collapse element (D13): the presence element, which opens and closes the\n // panel's space and renders no box while open, so the panel lays out as in 0.14. A full panel's\n // size is its container's, so it has nothing to collapse from: no motion. The panel keeps the\n // consumer's props and no role, tabIndex or modal attributes (D100); both elements take the\n // presence attributes (after the consumer's props on the panel): hidden and inert while kept\n // closed.\n return (\n <div\n ref={legacyMotion ? undefined : presenceRef}\n {...presenceProps}\n className={cn(\n collapseClassName,\n inlineDrawerStructure[position],\n size === 'full' ? '' : panelMotion,\n )}\n >\n <InlinePanel\n ref={inlineRef}\n id={id}\n data-type=\"inline\"\n data-position={position}\n data-size={size}\n data-separator={separator ? '' : undefined}\n {...rest}\n {...presenceProps}\n onKeyDown={onKeyDown}\n className={cn(\n rootClassName,\n inlinePanelClasses,\n getInlinePanelClasses(position, size),\n className,\n )}\n >\n {children}\n </InlinePanel>\n </div>\n );\n }\n\n return (\n <Portal ref={portalRef} layerId={layer.layerId}>\n {/* The backdrop of a modal or alert panel, the panel's sibling; a non-modal one has none.\n Both carry the presence attributes (D7, D103): hidden and inert while kept closed, so a\n closed panel leaves no backdrop over the page. */}\n {!nonModal && (\n <ModalBackdrop\n backdrop={backdrop}\n className={backdropClassName}\n layerId={layer.layerId}\n open={open}\n onMouseDown={backdropPress.onMouseDown}\n presenceProps={presenceProps}\n motionClassName={backdropMotionClassName}\n />\n )}\n <div\n ref={overlayRef}\n role={modalType === 'alert' ? 'alertdialog' : 'dialog'}\n id={id}\n tabIndex={-1}\n data-type=\"overlay\"\n data-position={position}\n data-size={size}\n data-modal-type={modalType}\n {...rest}\n {...presenceProps}\n onKeyDown={composeEventHandlers(onKeyDown, onTabOrderKeyDown)}\n className={cn(\n rootClassName,\n OVERLAY_PANEL_CLASSES,\n getOverlayPanelClasses(position, size),\n panelMotion,\n className,\n )}\n >\n {children}\n </div>\n </Portal>\n );\n};\nDrawerPanel.displayName = 'DrawerPanel';\n"],"mappings":"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"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/children.cjs"),r=require("../../lib/dev.cjs"),i=require("../../lib/slot.cjs"),a=require("../../lib/classNames.cjs"),o=require("../../hooks/useId.cjs"),s=require("../../hooks/useMergedRefs.cjs"),c=require("../../lib/styles.cjs"),l=require("./Dialog.shared.cjs"),u=require("./Drawer.panel.cjs"),d=require("./Drawer.scroll.cjs"),f=require("./Drawer.context.cjs"),p=require("./Drawer.parts.cjs");let m=require("react");m=e.__toESM(m,1);let h=require("react/jsx-runtime");var g=`Drawer:unreachable`,_="Drawer has no way to open: a second after mounting it is still uncontrolled (no `open` prop), closed, and has no Drawer.Trigger as a direct child (or in a Fragment there). A Drawer.Trigger rendered by a component or nested in an element is panel content, which is not rendered or is hidden while the drawer is closed. Make the trigger a direct child of Drawer, or control the Drawer with `open`/`onOpenChange`.",v=1e3,y=32;function b(e){let t=(e,r,i)=>{if(i>y||typeof e!=`object`||!e)return!1;if(Array.isArray(e))return e.some(e=>t(e,r,i));if(!m.isValidElement(e))return!1;let a=n.getElementType(e,{suspend:!1});if(a===p.DrawerTrigger)return r>0;let o=a===m.Fragment;if(typeof a!=`string`&&!o)return!1;let{children:s}=e.props;return t(s,o?r:r+1,i+1)};return t(e,0,0)}var
|
|
1
|
+
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/children.cjs"),r=require("../../lib/dev.cjs"),i=require("../../lib/slot.cjs"),a=require("../../lib/classNames.cjs"),o=require("../../hooks/useId.cjs"),s=require("../../hooks/useMergedRefs.cjs"),c=require("../../lib/styles.cjs"),l=require("./Dialog.shared.cjs"),u=require("./Drawer.panel.cjs"),d=require("./Drawer.scroll.cjs"),f=require("./Drawer.context.cjs"),p=require("./Drawer.parts.cjs");let m=require("react");m=e.__toESM(m,1);let h=require("react/jsx-runtime");var g=`Drawer:unreachable`,_="Drawer has no way to open: a second after mounting it is still uncontrolled (no `open` prop), closed, and has no Drawer.Trigger as a direct child (or in a Fragment there). A Drawer.Trigger rendered by a component or nested in an element is panel content, which is not rendered or is hidden while the drawer is closed. Make the trigger a direct child of Drawer, or control the Drawer with `open`/`onOpenChange`.",v=1e3,y=32;function b(e){let t=(e,r,i)=>{if(i>y||typeof e!=`object`||!e)return!1;if(Array.isArray(e))return e.some(e=>t(e,r,i));if(!m.isValidElement(e))return!1;let a=n.getElementType(e,{suspend:!1});if(a===p.DrawerTrigger)return r>0;let o=a===m.Fragment;if(typeof a!=`string`&&!o)return!1;let{children:s}=e.props;return t(s,o?r:r+1,i+1)};return t(e,0,0)}var ee=`Drawer:title-ignored`,te="Drawer: `title` and `titleAction` are ignored because a Drawer.Header is among the children. Put a Drawer.HeaderTitle (with its `action`) in the header instead.",ne=`Drawer.Body:duplicate`,re=`Drawer has more than one Drawer.Body: the props of the first one apply to the scrolling body, and the children of every one render in their place. Render one Drawer.Body.`;function x(e){let t={triggers:[],headers:[],bodyProps:void 0,bodyCount:0,content:[],footers:[]};for(let{key:r,node:i}of n.flattenChildren(e)){if(n.isElementOfType(i,p.DrawerBody)){t.bodyCount+=1,t.bodyCount===1&&(t.bodyProps=i.props),t.content.push((0,h.jsx)(m.Fragment,{children:i.props.children},r));continue}let e=m.isValidElement(i)?m.cloneElement(i,{key:r}):i;n.isElementOfType(i,p.DrawerTrigger)?t.triggers.push(e):n.isElementOfType(i,p.DrawerHeader)?t.headers.push(e):n.isElementOfType(i,p.DrawerFooter)?t.footers.push(e):t.content.push(e)}return t}function S({title:e,hasTitle:n,titleId:r,titleAction:o,requestOpen:s,closeLabel:c,closeButton:l}){let u=m.useContext(f.DrawerScrollStateContext)??`none`,g=i.slotRendersContent(o);return!n&&!g&&l===null?null:(0,h.jsxs)(`div`,{"data-scroll-state":u,className:t.cn(a.drawerClassNames.header,`flex shrink-0 items-center justify-between gap-2 p-4`,d.scrollSeparatorClasses.header),children:[n&&(0,h.jsx)(`h2`,{id:r,className:t.cn(a.drawerTitleClassNames.root,`text-subtitle-1 font-semibold`),children:e}),g?i.renderSlot(o,`span`,t.cn(a.drawerClassNames.titleAction,`ms-auto flex shrink-0 items-center gap-1`)):null,(0,h.jsx)(p.DrawerCloseButton,{requestOpen:s,label:c,closeButton:l,className:t.cn(!g&&`ms-auto`,`text-muted-foreground`)})]})}S.displayName=`DrawerBuiltInHeader`;function C({header:e,bodyProps:n,content:r,footers:i}){let[o,l]=m.useState(null),u=d.useScrollState(o),{children:p,className:g,ref:_,...v}=n??{},y=s.useMergedRefs(l,_);return(0,h.jsx)(f.DrawerScrollStateContext.Provider,{value:u,children:(0,h.jsxs)(f.DrawerHeaderContext.Provider,{value:!1,children:[(0,h.jsx)(f.DrawerPartContext.Provider,{value:`placed`,children:e}),(0,h.jsx)(`div`,{"data-scroll-state":u,...v,ref:y,className:t.cn(a.drawerClassNames.body,n&&a.drawerBodyClassNames.root,`min-h-0 flex-1 overflow-y-auto p-4`,c.focusRingInset,g),children:(0,h.jsx)(f.DrawerPartContext.Provider,{value:`content`,children:r})}),(0,h.jsx)(f.DrawerPartContext.Provider,{value:`placed`,children:i})]})})}C.displayName=`DrawerLayout`;var w=({open:e,defaultOpen:t,onOpenChange:n,type:c=`overlay`,separator:d=!1,position:y=`end`,size:w=`small`,modalType:ie=`modal`,backdrop:ae,motion:T,backdropMotion:E,closeButton:D,titleAction:O,title:k,closeLabel:A=`Close`,finalFocusRef:j,unmountOnClose:M=!0,children:N,id:oe,ref:se,...ce})=>{let[le,P]=l.useModalOpenState(e,t,n),F=u.useDrawerOpen(c,le),I=l.useModalTrigger(),ue=o.useId(`wave-drawer`),L=oe??ue,R=o.useId(`wave-drawer-title`),z=l.useTitleRegistry(),[B,V]=m.useState(null),H=s.useMergedRefs(se,V);l.useUnnamedModalWarning(F?B:null,z.hasTitle,`Drawer`,`Drawer.HeaderTitle or a Drawer.Title`);let{triggers:U,headers:W,bodyProps:de,bodyCount:fe,content:pe,footers:me}=x(N),G=W.length>0,K=i.slotRendersContent(k),q=K&&!G,J=(K||i.slotRendersContent(O))&&G;m.useEffect(()=>{J&&r.warnOnce(ee,te)},[J]);let Y=fe>1;m.useEffect(()=>{Y&&r.warnOnce(ne,re)},[Y]);let X=m.useRef(!1);m.useEffect(()=>{r.isDev&&!X.current&&b(N)&&(X.current=!0,r.warnOnce(p.NESTED_TRIGGER_WARNING_KEY,p.NESTED_TRIGGER_WARNING))},[N]);let Z=e===void 0&&!t&&U.length===0,Q=m.useRef({unreachable:Z,children:N});m.useLayoutEffect(()=>{Q.current={unreachable:Z,children:N}}),m.useEffect(()=>{if(!r.isDev||!Q.current.unreachable)return;let e=setTimeout(()=>{let e=Q.current;e.unreachable&&!b(e.children)&&r.warnOnce(g,_)},v);return()=>clearTimeout(e)},[]);let $=m.useMemo(()=>({open:F,requestOpen:P,trigger:I,panelId:L,type:c,inPanel:!1,closeLabel:A,closeButton:D}),[F,P,I,L,c,A,D]),he=m.useMemo(()=>({...$,inPanel:!0}),[$]),ge=(0,h.jsx)(f.DrawerContext.Provider,{value:he,children:(0,h.jsx)(l.ModalSurfaceContext.Provider,{value:z.context,children:(0,h.jsx)(C,{header:G?W:(0,h.jsx)(S,{title:k,hasTitle:q,titleId:R,titleAction:O,requestOpen:P,closeLabel:A,closeButton:D}),bodyProps:de,content:pe,footers:me})})}),_e=q?R:z.titleId,ve=(0,h.jsx)(u.DrawerPanel,{componentName:`Drawer`,type:c,open:F,requestOpen:P,position:y,size:w,separator:d,modalType:ie,unmountOnClose:M,inlineAs:`aside`,trigger:I,finalFocusRef:j,rootClassName:a.drawerClassNames.root,backdropClassName:a.drawerClassNames.backdrop,collapseClassName:a.drawerClassNames.collapse,backdrop:ae,motion:T,backdropMotion:E,id:L,"aria-labelledby":_e,...ce,ref:H,children:ge});return l.useModalTriggerSession(I,F),(0,h.jsxs)(f.DrawerContext.Provider,{value:$,children:[U,ve]})};w.displayName=`Drawer`,exports.DrawerRoot=w;
|
|
2
2
|
//# sourceMappingURL=Drawer.root.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Drawer.root.cjs","names":["React","getElementType","DrawerTrigger","flattenChildren","isElementOfType","DrawerBody","DrawerHeader","DrawerFooter","DrawerScrollStateContext","slotRendersContent","cn","drawerClassNames","scrollSeparatorClasses","drawerTitleClassNames","renderSlot","DrawerCloseButton","useScrollState","useMergedRefs","DrawerHeaderContext","DrawerPartContext","drawerBodyClassNames","focusRingInset","useModalOpenState","useDrawerOpen","useModalTrigger","useId","useTitleRegistry","isDev","NESTED_TRIGGER_WARNING_KEY","NESTED_TRIGGER_WARNING","DrawerContext","ModalSurfaceContext","DrawerPanel","require_runtime","require_cn","require_children","require_dev","require_slot","require_classNames","require_useId","require_useMergedRefs","require_styles","require_Dialog_shared","require_Drawer_panel","require_Drawer_scroll","require_Drawer_context","require_Drawer_parts","react","react_jsx_runtime","UNREACHABLE_WARNING_KEY","UNREACHABLE_WARNING","REACHABILITY_CHECK_DELAY","NESTED_TRIGGER_MAX_DEPTH","hasNestedTrigger","visit","level","node","item","depth","type","isFragment","nested","children","TITLE_IGNORED_WARNING_KEY","TITLE_IGNORED_WARNING","BODY_DUPLICATE_WARNING_KEY","BODY_DUPLICATE_WARNING","splitChildren","partition","key","keyed","DrawerBuiltInHeader","scrollState","hasTitleAction","titleAction","hasTitle","closeButton","titleId","title","closeLabel","DrawerLayout","body","setBody","_children","bodyRest","bodyProps","bodyRef","ref","header","className","content","footers","DrawerRoot","openProp","rest","openState","requestOpen","defaultOpen","onOpenChange","open","trigger","generatedId","panelId","id","propTitleId","titles","panel","setPanel","panelRef","hasHeader","headers","titleRendersContent","titleIgnored","duplicateBody","bodyCount","nestedWarnedRef","unreachable","triggers","latestRef","timer","latest","context","panelContext","layout","labelledBy","panelElement"],"sources":["../../../src/components/overlays/Drawer.root.tsx"],"sourcesContent":["import * as React from 'react';\nimport { flattenChildren, getElementType, isElementOfType } from '../../lib/children';\nimport { cn } from '../../lib/cn';\nimport {\n drawerBodyClassNames,\n drawerClassNames,\n drawerTitleClassNames,\n} from '../../lib/classNames';\nimport { isDev, warnOnce } from '../../lib/dev';\nimport { renderSlot, slotRendersContent, type Slot, type SlotObject } from '../../lib/slot';\nimport { focusRingInset } from '../../lib/styles';\nimport type { BackdropAppearance } from '../../lib/types';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport {\n ModalSurfaceContext,\n useModalOpenState,\n useModalTrigger,\n useModalTriggerSession,\n useTitleRegistry,\n useUnnamedModalWarning,\n type ModalRequestOpen,\n} from './Dialog.shared';\nimport {\n DrawerContext,\n DrawerHeaderContext,\n DrawerPartContext,\n DrawerScrollStateContext,\n type DrawerContextValue,\n type DrawerModalType,\n type DrawerOpenChangeDetails,\n type DrawerPosition,\n type DrawerSize,\n type DrawerType,\n} from './Drawer.context';\nimport { DrawerPanel, useDrawerOpen } from './Drawer.panel';\nimport {\n DrawerBody,\n DrawerCloseButton,\n DrawerFooter,\n DrawerHeader,\n DrawerTrigger,\n NESTED_TRIGGER_WARNING,\n NESTED_TRIGGER_WARNING_KEY,\n type DrawerBodyProps,\n} from './Drawer.parts';\nimport { scrollSeparatorClasses, useScrollState } from './Drawer.scroll';\n\n/*\n * The Drawer root: its props, the child scan, the layout and the development checks, on the drawer\n * panel shell (`DrawerPanel`), which renders the panel element and its machinery. Imports the\n * parts, panel, scroll and context modules (never `Drawer.tsx`, which holds the compound).\n */\n\n/** Properties for the Drawer component. */\nexport interface DrawerProps extends Omit<React.HTMLAttributes<HTMLElement>, 'title'> {\n /**\n * Controlled open state of the drawer. An overlay drawer's panel renders only in the browser:\n * open, it is closed in the server HTML and opens once it has hydrated. An inline drawer renders\n * in the server HTML: open, or hidden when kept mounted (`unmountOnClose={false}`).\n */\n open?: boolean;\n /**\n * Default open state for uncontrolled usage. An overlay drawer open by default is closed in the\n * server HTML and opens once it has hydrated; an inline one is open in the server HTML.\n * @default false\n */\n defaultOpen?: boolean;\n /**\n * Called with the new open state when it changes. `details.reason` tells how — `trigger`,\n * `close` (a `.Close` part), `close-button` (the built-in Close button), `escape` or\n * `outside-press` (the backdrop) — so a controlled drawer can refuse only some ways of closing\n * (for example keep a form with unsaved changes open on `outside-press`); `details.event` is the\n * DOM event behind the request. WaveUI always passes `details`; it is typed optional until 1.0\n * so that code which calls this prop itself keeps compiling. An inline drawer asks only with\n * `trigger` (its `Drawer.Trigger` toggles it), `close` and `close-button`: Escape and presses\n * outside it never close it.\n *\n * Fires only when the value changes; a controlled drawer stays as it is until the parent updates\n * `open`.\n */\n onOpenChange?: (open: boolean, details?: DrawerOpenChangeDetails) => void;\n /**\n * How the drawer sits on the page (Fluent's `type`).\n * - `overlay`: a panel over the page, rendered in a portal while open: modal by default (focus\n * moves in and stays there, toasts included; the rest of the page is `inert` and does not\n * scroll; Escape and a backdrop press close it), or `modalType=\"non-modal\"`.\n * - `inline`: a panel in the page layout, rendered where the Drawer is (after its direct\n * `Drawer.Trigger`s) as an `<aside>`, a complementary landmark named by its title. The page\n * stays usable around it: no backdrop, no focus trap, no portal, no scroll lock; Escape and\n * presses outside do not close it. Opening it leaves focus where it is; closing it while focus\n * is inside returns focus to `finalFocusRef`, else the element that opened it, else the\n * trigger. `position` and `size` pick its inner edge and its width (its height at the bottom);\n * where it sits is up to your layout (a flex row of panel and content, for example).\n * `modalType` and `backdrop` do not apply to it, and toasts do not move out of its way: it is\n * page content.\n *\n * Changing `type` remounts the panel and its content (what was typed in it is lost); focus\n * inside an overlay that becomes inline returns to the trigger, and focus inside an inline panel\n * that becomes an overlay moves into the overlay. Rendered as `data-type`.\n * @default 'overlay'\n */\n type?: DrawerType;\n /**\n * Inline drawers: draws a line on the panel's inner edge, the edge facing the page content\n * (`data-separator`). An overlay drawer always draws that edge and ignores this prop. In forced\n * colours an inline drawer's inner edge is always drawn. Fluent's `separator`.\n * @default false\n */\n separator?: boolean;\n /**\n * Side of the screen the drawer is attached to. `start`/`end` follow the text direction;\n * `left`/`right` are physical sides; `bottom` runs along the bottom edge (`size` sets its\n * height). An inline drawer takes its place from your layout: `position` picks its inner edge\n * (the one facing the page content: the end edge of a `start` panel, the top edge of a `bottom`\n * one) and the axis `size` sets. Rendered as `data-position`.\n * @default 'end'\n */\n position?: DrawerPosition;\n /**\n * The panel's width at a side — `small` 320px, `medium` 592px, `large` 940px, `full` the\n * viewport's width — or its height at the bottom (the same values; `full` the viewport's height).\n * It never exceeds the viewport. An inline panel takes the same sizes, where `full` is its\n * container's width (height), and never grows past its container. A width class in `className`\n * (a height class for `bottom`) replaces it. Rendered as `data-size`. Fluent's `size`.\n * @default 'small'\n */\n size?: DrawerSize;\n /**\n * `modal`, `alert` or `non-modal`, as Dialog's `modalType`. `modal`: the page behind is `inert`\n * and does not scroll; a backdrop press, Escape, the Close button and `Drawer.Close` close it.\n * `alert`: `role=\"alertdialog\"` (a `role` you pass wins), and a backdrop press does not close it\n * (Escape still does). `non-modal`: no backdrop, and the page stays usable — no focus trap,\n * nothing inert, the page scrolls; Tab and Shift+Tab leave the drawer in the page's order right\n * after the element that opened it, Escape closes it while focus is inside it, presses on the\n * page never close it, and focus returns to the opener only when it was inside the drawer. A\n * non-modal drawer covers the page under it while Tab still reaches that page: reserve its width\n * (its height at the bottom) in your layout while it is open, or use `modal`, or, for a panel\n * beside the content, an inline drawer (`type=\"inline\"`) (with `size=\"full\"` it covers\n * everything, and a development warning says so). Every type moves focus to the first focusable\n * element on open. Rendered as `data-modal-type`. Ignored by an inline drawer, which is never\n * modal and renders no `data-modal-type`. Fluent's `modalType`.\n * @default 'modal'\n */\n modalType?: DrawerModalType;\n /**\n * The backdrop of a modal or alert drawer, as `Dialog.Content`'s `backdrop`: a `div` behind the\n * panel, `aria-hidden`. Shorthand content renders inside it; a slot object's `className` (merged\n * last), `style`, data attributes, `ref` and handlers go to it, and its `appearance`\n * (`'dimmed'` or `'transparent'`) overrides the automatic one: while another modal Dialog or\n * Drawer is open below this one the backdrop is transparent, so the page is dimmed once. `null`\n * renders no backdrop (the page stays inert, and a press outside still closes a modal drawer); a\n * boolean is no slot. Ignored with `modalType=\"non-modal\"` and by an inline drawer (a\n * development warning says so). Fluent's `backdrop`.\n */\n backdrop?: Slot<'div'> | (SlotObject<'div'> & { appearance?: BackdropAppearance });\n /**\n * Content of the built-in Close button, in the built-in header and in every\n * `Drawer.HeaderTitle`, as `Dialog.Content`'s `closeButton`: decorative content inside the button\n * (the dismiss glyph by default), so the button keeps the name `closeLabel`; a slot object's\n * `aria-label`, `aria-labelledby` or `title` names it instead, and its handlers run before the\n * close (`preventDefault()` keeps the drawer open). `null` hides them all (`Drawer.Close`, and\n * Escape on an overlay, still close); a boolean is no slot; content that renders nothing keeps the\n * default glyph. A `<button>` or Wave `Button` passed here is merged into the built-in button,\n * never nested (a development warning says so), and its text label names the button. Fluent's\n * `DrawerHeaderTitle` `action` holds Fluent's close button; WaveUI renders its own.\n */\n closeButton?: Slot<'span'>;\n /**\n * Header buttons for the `title` prop form, between the heading and the built-in Close button in\n * DOM and Tab order. Ignored, with a development warning, next to a `Drawer.Header` (use the\n * `action` of `Drawer.HeaderTitle`). Interactive: name icon-only buttons. Renders nothing when\n * empty. Fluent's `DrawerHeaderTitle` `action`, for the `title` prop form.\n */\n titleAction?: Slot<'span'>;\n /**\n * Title displayed in the built-in header; it names the drawer (`aria-labelledby`). Without it,\n * render a `Drawer.HeaderTitle` (in a `Drawer.Header`) or a `Drawer.Title`, or pass\n * `aria-label`/`aria-labelledby`. A title that renders nothing (`''`, `[]`, `true`) counts as\n * none. Ignored, with a development warning, when the children hold a `Drawer.Header`, which\n * replaces the built-in header. The heading is an `<h2>`; for another level use\n * `Drawer.HeaderTitle` with `headingLevel`. In the server HTML of an inline drawer only `title`\n * (or `aria-label`/`aria-labelledby`) names the panel: a `Drawer.HeaderTitle` or `Drawer.Title`\n * names it once the page has hydrated.\n */\n title?: React.ReactNode;\n /**\n * Accessible name of the built-in Close button (an icon-only button), in the built-in header and\n * in every `Drawer.HeaderTitle`. Localize it with the page's language. A text label of a button\n * merged into `closeButton` names it instead.\n * @default 'Close'\n */\n closeLabel?: string;\n /**\n * Where focus goes when the drawer closes, if it can take focus. Otherwise focus returns to the\n * element that had focus when the drawer opened, then to the trigger, then to an element next to\n * where that opener was. An inline or non-modal drawer moves focus on close only when focus was\n * inside it.\n */\n finalFocusRef?: React.RefObject<HTMLElement | null>;\n /**\n * Removes the panel and its content when the drawer closes. `false` keeps them mounted while\n * closed, `hidden` and `inert` (out of the layout, the Tab order and the accessibility tree), so\n * what was typed and the state of the components inside survive closing and opening again; the\n * content then mounts with the Drawer, closed, and an `autoFocus` inside it never applies (an\n * overlay focuses its first focusable element on each open). An overlay panel still renders only\n * in the browser; a kept inline panel is in the server HTML, hidden. Kept content still belongs\n * to its form: a `required` empty field in a closed inline drawer inside a page `<form>` blocks\n * its submission without a visible message. A popup opened inside that is still open when the\n * drawer closes stays open over the page (a development warning says so): close it first. A\n * `key` on the Drawer resets the kept content. Fluent's `unmountOnClose`.\n * @default true\n */\n unmountOnClose?: boolean;\n /**\n * The drawer's content, placed by the Drawer, also from a Fragment (`{isMobile && <>…</>}`) and\n * when written in a Server Component: `Drawer.Trigger` children render in place (outside the\n * panel); a `Drawer.Header` replaces the built-in header (the `title` and Close button row); a\n * `Drawer.Body` gives the scrolling body its props; `Drawer.Footer` renders below the scrolling\n * body, outside it, wherever it is written among the children; everything else renders in the\n * scrolling body. A part nested in another element (a `<form>`) or rendered by a component of\n * yours renders where it is, in the body (a development warning says so). A `Drawer.Trigger`\n * nested in another element, or rendered by a component, is panel content, so it is not rendered\n * (or, kept mounted, is hidden) while the drawer is closed (development warnings say so, also\n * when an uncontrolled drawer still has no direct trigger a second after it mounts and therefore\n * cannot open; a controlled drawer whose trigger a component such as a Tooltip wraps warns only\n * once it renders in the panel).\n * Put wrappers inside the trigger instead: see `Drawer.Trigger`.\n */\n children: React.ReactNode;\n /**\n * Ref to the panel: the `role=\"dialog\"` element of an overlay drawer (`alertdialog` with\n * `modalType=\"alert\"`), the `<aside>` of an inline one. A ref to a `div` still type-checks.\n */\n ref?: React.Ref<HTMLElement>;\n}\n\nconst UNREACHABLE_WARNING_KEY = 'Drawer:unreachable';\nconst UNREACHABLE_WARNING =\n 'Drawer has no way to open: a second after mounting it is still uncontrolled (no `open` prop), closed, and has no Drawer.Trigger as a direct child (or in a Fragment there). A Drawer.Trigger rendered by a component or nested in an element is panel content, which is not rendered or is hidden while the drawer is closed. Make the trigger a direct child of Drawer, or control the Drawer with `open`/`onOpenChange`.';\n\n/**\n * How long after mount (ms) the development check for a drawer without a trigger waits: long\n * enough for a trigger that a conditional Fragment renders once the page knows its layout.\n */\nconst REACHABILITY_CHECK_DELAY = 1000;\n\n/** Deepest element level the development check for nested triggers looks at. */\nconst NESTED_TRIGGER_MAX_DEPTH = 32;\n\n/**\n * Development check: whether the Drawer's children hold a `Drawer.Trigger` inside a host element\n * (at any depth, also through Fragments), which would become panel content; a trigger inside\n * Fragments only is direct (see `splitChildren`). Walks the element tree the consumer wrote, not\n * rendered output, so it descends only into host elements (`<div>`, `<span>`, …) and Fragments,\n * which render their `children` as written. A component's\n * output is unknown here — a wrapper that renders its own Drawer around its children, for one —\n * so components are not walked; a trigger rendered by a component is caught when it renders in the\n * open panel, or, while the drawer cannot open, by the unreachable-drawer check.\n */\nfunction hasNestedTrigger(children: React.ReactNode): boolean {\n // `depth` counts host elements only: a Fragment adds no level, as `splitChildren` flattens it.\n const visit = (node: unknown, depth: number, level: number): boolean => {\n if (level > NESTED_TRIGGER_MAX_DEPTH || typeof node !== 'object' || node === null) return false;\n if (Array.isArray(node)) return node.some((item) => visit(item, depth, level));\n if (!React.isValidElement(node)) return false;\n // A part written in a Server Component has a lazy type. The walk runs in effects, outside\n // render: a lazy part that is still loading must not throw its thenable there, so it counts\n // as no trigger (`suspend: false` returns the lazy itself, which matches nothing).\n const type = getElementType(node, { suspend: false });\n if (type === DrawerTrigger) return depth > 0;\n const isFragment = type === React.Fragment;\n if (typeof type !== 'string' && !isFragment) return false;\n const { children: nested } = node.props as { children?: unknown };\n return visit(nested, isFragment ? depth : depth + 1, level + 1);\n };\n return visit(children, 0, 0);\n}\n\nconst TITLE_IGNORED_WARNING_KEY = 'Drawer:title-ignored';\nconst TITLE_IGNORED_WARNING =\n 'Drawer: `title` and `titleAction` are ignored because a Drawer.Header is among the children. Put a Drawer.HeaderTitle (with its `action`) in the header instead.';\n\nconst BODY_DUPLICATE_WARNING_KEY = 'Drawer.Body:duplicate';\nconst BODY_DUPLICATE_WARNING =\n 'Drawer has more than one Drawer.Body: the props of the first one apply to the scrolling body, and the children of every one render in their place. Render one Drawer.Body.';\n\n/** How the Drawer sorts its direct children ({@link splitChildren}). */\ninterface DrawerPartition {\n /** The direct `Drawer.Trigger` elements, rendered in place. */\n triggers: React.ReactNode[];\n /** The direct `Drawer.Header` elements, rendered in the header area in written order. */\n headers: React.ReactNode[];\n /** The props of the first direct `Drawer.Body` (its `children` render in `content`). */\n bodyProps: DrawerBodyProps | undefined;\n /** How many direct `Drawer.Body` elements there are. */\n bodyCount: number;\n /** The body content in written order; a `Drawer.Body` is replaced by its children. */\n content: React.ReactNode[];\n /** The direct `Drawer.Footer` elements, rendered after the body in written order. */\n footers: React.ReactNode[];\n}\n\n/**\n * Sorts the Drawer's children: its direct `Drawer.Trigger`, `Drawer.Header`, `Drawer.Body` and\n * `Drawer.Footer` elements and the body content. Fragments are flattened (recursively), so a part\n * in a Fragment — `{isMobile && <><Drawer.Trigger>…</Drawer.Trigger><Filters /></>}` — counts as a\n * direct child. Every element keeps the key `flattenChildren` gives it: unique across Fragments and\n * stable when a sibling Fragment toggles, so body content keeps its state when a part appears. A\n * part is recognised also when it was written in a Server Component (a lazy type). Runs during\n * render, so the placement is the same on the server.\n */\nfunction splitChildren(children: React.ReactNode): DrawerPartition {\n const partition: DrawerPartition = {\n triggers: [],\n headers: [],\n bodyProps: undefined,\n bodyCount: 0,\n content: [],\n footers: [],\n };\n for (const { key, node } of flattenChildren(children)) {\n if (isElementOfType<DrawerBodyProps>(node, DrawerBody)) {\n // The first Body's props go on the scrolling body; every Body's children render in place.\n partition.bodyCount += 1;\n if (partition.bodyCount === 1) partition.bodyProps = node.props;\n partition.content.push(<React.Fragment key={key}>{node.props.children}</React.Fragment>);\n continue;\n }\n const keyed = React.isValidElement(node) ? React.cloneElement(node, { key }) : node;\n if (isElementOfType(node, DrawerTrigger)) partition.triggers.push(keyed);\n else if (isElementOfType(node, DrawerHeader)) partition.headers.push(keyed);\n else if (isElementOfType(node, DrawerFooter)) partition.footers.push(keyed);\n else partition.content.push(keyed);\n }\n return partition;\n}\n\n/** Properties of the built-in header ({@link DrawerBuiltInHeader}). */\ninterface DrawerBuiltInHeaderProps {\n /** The `title` prop, when it renders content. */\n title: React.ReactNode;\n /** Whether `title` renders content (else no heading renders). */\n hasTitle: boolean;\n /** The heading's id (the panel's `aria-labelledby`). */\n titleId: string;\n /** The `titleAction` slot. */\n titleAction: Slot<'span'> | undefined;\n requestOpen: ModalRequestOpen;\n closeLabel: string;\n /** The `closeButton` slot (`null`: no Close button). */\n closeButton: Slot<'span'> | undefined;\n}\n\n/**\n * The 0.10 header row of the `title` form (no `Drawer.Header` among the children): the `title`\n * heading, the `titleAction` content and the Close button as its direct children. The title action\n * takes the free room (`ms-auto`), so the Close button follows it through the row's gap; without\n * one the Close button does. It reads the body's scroll state for its separator. A row with\n * nothing in it (no title, no title action, `closeButton={null}`) renders no element.\n */\nfunction DrawerBuiltInHeader({\n title,\n hasTitle,\n titleId,\n titleAction,\n requestOpen,\n closeLabel,\n closeButton,\n}: DrawerBuiltInHeaderProps) {\n const scrollState = React.useContext(DrawerScrollStateContext) ?? 'none';\n const hasTitleAction = slotRendersContent(titleAction);\n if (!hasTitle && !hasTitleAction && closeButton === null) return null;\n return (\n <div\n data-scroll-state={scrollState}\n className={cn(\n drawerClassNames.header,\n 'flex shrink-0 items-center justify-between gap-2 p-4',\n scrollSeparatorClasses.header,\n )}\n >\n {hasTitle && (\n <h2\n id={titleId}\n className={cn(drawerTitleClassNames.root, 'text-subtitle-1 font-semibold')}\n >\n {title}\n </h2>\n )}\n {hasTitleAction\n ? renderSlot(\n titleAction,\n 'span',\n cn(drawerClassNames.titleAction, 'ms-auto flex shrink-0 items-center gap-1'),\n )\n : null}\n <DrawerCloseButton\n requestOpen={requestOpen}\n label={closeLabel}\n closeButton={closeButton}\n className={cn(!hasTitleAction && 'ms-auto', 'text-muted-foreground')}\n />\n </div>\n );\n}\nDrawerBuiltInHeader.displayName = 'DrawerBuiltInHeader';\n\n/** Properties of {@link DrawerLayout}. */\ninterface DrawerLayoutProps {\n /** The header area: the built-in header, or the placed `Drawer.Header` elements. */\n header: React.ReactNode;\n /** The props of the placed `Drawer.Body`, put on the scrolling body. */\n bodyProps: DrawerBodyProps | undefined;\n /** The body content. */\n content: React.ReactNode;\n /** The placed `Drawer.Footer` elements. */\n footers: React.ReactNode;\n}\n\n/**\n * The panel's layout (internal): the header area, the scrolling body and the footers. It owns the\n * body's scroll state (`useScrollState`), so a change of the state re-renders this component, the\n * body element and the parts that read the state (the header area and the footers), never the\n * consumer's content: the elements it receives as props are the same objects, so React skips them.\n */\nfunction DrawerLayout({ header, bodyProps, content, footers }: DrawerLayoutProps) {\n const [body, setBody] = React.useState<HTMLDivElement | null>(null);\n const scrollState = useScrollState(body);\n const { children: _children, className, ref, ...bodyRest } = bodyProps ?? {};\n const bodyRef = useMergedRefs<HTMLDivElement>(setBody, ref);\n return (\n <DrawerScrollStateContext.Provider value={scrollState}>\n <DrawerHeaderContext.Provider value={false}>\n <DrawerPartContext.Provider value=\"placed\">{header}</DrawerPartContext.Provider>\n <div\n data-scroll-state={scrollState}\n {...bodyRest}\n ref={bodyRef}\n className={cn(\n drawerClassNames.body,\n bodyProps && drawerBodyClassNames.root,\n 'min-h-0 flex-1 overflow-y-auto p-4',\n focusRingInset,\n className,\n )}\n >\n <DrawerPartContext.Provider value=\"content\">{content}</DrawerPartContext.Provider>\n </div>\n <DrawerPartContext.Provider value=\"placed\">{footers}</DrawerPartContext.Provider>\n </DrawerHeaderContext.Provider>\n </DrawerScrollStateContext.Provider>\n );\n}\nDrawerLayout.displayName = 'DrawerLayout';\n\n// The root of `Drawer` (documented on the export in Drawer.tsx).\nexport const DrawerRoot = ({\n open: openProp,\n defaultOpen,\n onOpenChange,\n type = 'overlay',\n separator = false,\n position = 'end',\n size = 'small',\n modalType = 'modal',\n backdrop,\n closeButton,\n titleAction,\n title,\n closeLabel = 'Close',\n finalFocusRef,\n unmountOnClose = true,\n children,\n id,\n ref,\n ...rest\n}: DrawerProps) => {\n const [openState, requestOpen] = useModalOpenState(openProp, defaultOpen, onOpenChange);\n // An overlay's panel lives in a portal, which renders only in the browser: until then (the\n // server HTML, hydration) it reports itself closed, so the trigger's aria-expanded and\n // aria-controls never describe a panel that is not there. An inline panel renders in place, also\n // on the server (D107).\n const open = useDrawerOpen(type, openState);\n const trigger = useModalTrigger();\n const generatedId = useId('wave-drawer');\n const panelId = id ?? generatedId;\n const propTitleId = useId('wave-drawer-title');\n const titles = useTitleRegistry();\n // The mounted panel (the shell's element of either type), for the unnamed-drawer check.\n const [panel, setPanel] = React.useState<HTMLElement | null>(null);\n const panelRef = useMergedRefs<HTMLElement>(ref, setPanel);\n useUnnamedModalWarning(\n open ? panel : null,\n titles.hasTitle,\n 'Drawer',\n 'Drawer.HeaderTitle or a Drawer.Title',\n );\n\n const { triggers, headers, bodyProps, bodyCount, content, footers } = splitChildren(children);\n const hasHeader = headers.length > 0;\n // A Drawer.Header replaces the built-in header, whose `title` it cannot show.\n const titleRendersContent = slotRendersContent(title);\n const hasTitle = titleRendersContent && !hasHeader;\n const titleIgnored = (titleRendersContent || slotRendersContent(titleAction)) && hasHeader;\n React.useEffect(() => {\n if (titleIgnored) warnOnce(TITLE_IGNORED_WARNING_KEY, TITLE_IGNORED_WARNING);\n }, [titleIgnored]);\n const duplicateBody = bodyCount > 1;\n React.useEffect(() => {\n if (duplicateBody) warnOnce(BODY_DUPLICATE_WARNING_KEY, BODY_DUPLICATE_WARNING);\n }, [duplicateBody]);\n\n // A trigger nested in the children is panel content: not rendered (or, kept mounted, hidden) while\n // the drawer is closed.\n // The children change on every parent render; once this drawer has warned, it stops walking.\n const nestedWarnedRef = React.useRef(false);\n React.useEffect(() => {\n if (!isDev || nestedWarnedRef.current || !hasNestedTrigger(children)) return;\n nestedWarnedRef.current = true;\n warnOnce(NESTED_TRIGGER_WARNING_KEY, NESTED_TRIGGER_WARNING);\n }, [children]);\n\n // An uncontrolled closed drawer without a direct trigger cannot open (e.g.\n // `<Drawer><FilterTrigger /></Drawer>`, whose trigger is panel content). Checked once, a moment\n // after mount, against the latest render: a trigger that a conditional Fragment adds right after\n // mount (`{isMobile && <>…</>}` with an SSR-safe media query) counts. A trigger nested in an\n // element already has the more specific warning above.\n const unreachable = openProp === undefined && !defaultOpen && triggers.length === 0;\n const latestRef = React.useRef({ unreachable, children });\n React.useLayoutEffect(() => {\n latestRef.current = { unreachable, children };\n });\n React.useEffect(() => {\n if (!isDev || !latestRef.current.unreachable) return;\n const timer = setTimeout(() => {\n const latest = latestRef.current;\n if (latest.unreachable && !hasNestedTrigger(latest.children)) {\n warnOnce(UNREACHABLE_WARNING_KEY, UNREACHABLE_WARNING);\n }\n }, REACHABILITY_CHECK_DELAY);\n return () => clearTimeout(timer);\n }, []);\n\n const context = React.useMemo<DrawerContextValue>(\n () => ({ open, requestOpen, trigger, panelId, type, inPanel: false, closeLabel, closeButton }),\n [open, requestOpen, trigger, panelId, type, closeLabel, closeButton],\n );\n const panelContext = React.useMemo<DrawerContextValue>(\n () => ({ ...context, inPanel: true }),\n [context],\n );\n\n // The panel's content: the header area, the scrolling body and the footers, for both types.\n const layout = (\n <DrawerContext.Provider value={panelContext}>\n <ModalSurfaceContext.Provider value={titles.context}>\n <DrawerLayout\n header={\n hasHeader ? (\n headers\n ) : (\n <DrawerBuiltInHeader\n title={title}\n hasTitle={hasTitle}\n titleId={propTitleId}\n titleAction={titleAction}\n requestOpen={requestOpen}\n closeLabel={closeLabel}\n closeButton={closeButton}\n />\n )\n }\n bodyProps={bodyProps}\n content={content}\n footers={footers}\n />\n </ModalSurfaceContext.Provider>\n </DrawerContext.Provider>\n );\n const labelledBy = hasTitle ? propTitleId : titles.titleId;\n\n // The panel and its machinery (portal, backdrop, presence, layer, trap, restore, Tab order) come\n // from the shell (D108); the root names it and fills it with its layout.\n const panelElement = (\n <DrawerPanel\n componentName=\"Drawer\"\n type={type}\n open={open}\n requestOpen={requestOpen}\n position={position}\n size={size}\n separator={separator}\n modalType={modalType}\n unmountOnClose={unmountOnClose}\n inlineAs=\"aside\"\n trigger={trigger}\n finalFocusRef={finalFocusRef}\n rootClassName={drawerClassNames.root}\n backdropClassName={drawerClassNames.backdrop}\n backdrop={backdrop}\n id={panelId}\n aria-labelledby={labelledBy}\n {...rest}\n ref={panelRef}\n >\n {layout}\n </DrawerPanel>\n );\n // After the shell's focus restores (its effects run before the root's), start the trigger\n // session, or end it and forget the trigger that opened it.\n useModalTriggerSession(trigger, open);\n\n return (\n <DrawerContext.Provider value={context}>\n {triggers}\n {panelElement}\n </DrawerContext.Provider>\n );\n};\nDrawerRoot.displayName = 'Drawer';\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"Drawer.root.cjs","names":["React","getElementType","DrawerTrigger","flattenChildren","isElementOfType","DrawerBody","DrawerHeader","DrawerFooter","DrawerScrollStateContext","slotRendersContent","cn","drawerClassNames","scrollSeparatorClasses","drawerTitleClassNames","renderSlot","DrawerCloseButton","useScrollState","useMergedRefs","DrawerHeaderContext","DrawerPartContext","drawerBodyClassNames","focusRingInset","useModalOpenState","useDrawerOpen","useModalTrigger","useId","useTitleRegistry","isDev","NESTED_TRIGGER_WARNING_KEY","NESTED_TRIGGER_WARNING","DrawerContext","ModalSurfaceContext","DrawerPanel","require_runtime","require_cn","require_children","require_dev","require_slot","require_classNames","require_useId","require_useMergedRefs","require_styles","require_Dialog_shared","require_Drawer_panel","require_Drawer_scroll","require_Drawer_context","require_Drawer_parts","react","react_jsx_runtime","UNREACHABLE_WARNING_KEY","UNREACHABLE_WARNING","REACHABILITY_CHECK_DELAY","NESTED_TRIGGER_MAX_DEPTH","hasNestedTrigger","visit","level","node","item","depth","type","isFragment","nested","children","TITLE_IGNORED_WARNING_KEY","TITLE_IGNORED_WARNING","BODY_DUPLICATE_WARNING_KEY","BODY_DUPLICATE_WARNING","splitChildren","partition","key","keyed","DrawerBuiltInHeader","scrollState","hasTitleAction","titleAction","hasTitle","closeButton","titleId","title","closeLabel","DrawerLayout","body","setBody","_children","bodyRest","bodyProps","bodyRef","ref","header","className","content","footers","DrawerRoot","openProp","rest","openState","requestOpen","defaultOpen","onOpenChange","open","trigger","generatedId","panelId","id","propTitleId","titles","panel","setPanel","panelRef","hasHeader","headers","titleRendersContent","titleIgnored","duplicateBody","bodyCount","nestedWarnedRef","unreachable","triggers","latestRef","timer","latest","context","panelContext","layout","labelledBy","panelElement"],"sources":["../../../src/components/overlays/Drawer.root.tsx"],"sourcesContent":["import * as React from 'react';\nimport { flattenChildren, getElementType, isElementOfType } from '../../lib/children';\nimport { cn } from '../../lib/cn';\nimport {\n drawerBodyClassNames,\n drawerClassNames,\n drawerTitleClassNames,\n} from '../../lib/classNames';\nimport { isDev, warnOnce } from '../../lib/dev';\nimport { renderSlot, slotRendersContent, type Slot, type SlotObject } from '../../lib/slot';\nimport { focusRingInset } from '../../lib/styles';\nimport type { BackdropAppearance, MotionSlot } from '../../lib/types';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport {\n ModalSurfaceContext,\n useModalOpenState,\n useModalTrigger,\n useModalTriggerSession,\n useTitleRegistry,\n useUnnamedModalWarning,\n type ModalRequestOpen,\n} from './Dialog.shared';\nimport {\n DrawerContext,\n DrawerHeaderContext,\n DrawerPartContext,\n DrawerScrollStateContext,\n type DrawerContextValue,\n type DrawerModalType,\n type DrawerOpenChangeDetails,\n type DrawerPosition,\n type DrawerSize,\n type DrawerType,\n} from './Drawer.context';\nimport { DrawerPanel, useDrawerOpen } from './Drawer.panel';\nimport {\n DrawerBody,\n DrawerCloseButton,\n DrawerFooter,\n DrawerHeader,\n DrawerTrigger,\n NESTED_TRIGGER_WARNING,\n NESTED_TRIGGER_WARNING_KEY,\n type DrawerBodyProps,\n} from './Drawer.parts';\nimport { scrollSeparatorClasses, useScrollState } from './Drawer.scroll';\n\n/*\n * The Drawer root: its props, the child scan, the layout and the development checks, on the drawer\n * panel shell (`DrawerPanel`), which renders the panel element and its machinery. Imports the\n * parts, panel, scroll and context modules (never `Drawer.tsx`, which holds the compound).\n */\n\n/** Properties for the Drawer component. */\nexport interface DrawerProps extends Omit<React.HTMLAttributes<HTMLElement>, 'title'> {\n /**\n * Controlled open state of the drawer. An overlay drawer's panel renders only in the browser:\n * open, it is closed in the server HTML and opens once it has hydrated. An inline drawer renders\n * in the server HTML: open, or hidden when kept mounted (`unmountOnClose={false}`).\n */\n open?: boolean;\n /**\n * Default open state for uncontrolled usage. An overlay drawer open by default is closed in the\n * server HTML and opens once it has hydrated; an inline one is open in the server HTML.\n * @default false\n */\n defaultOpen?: boolean;\n /**\n * Called with the new open state when it changes. `details.reason` tells how — `trigger`,\n * `close` (a `.Close` part), `close-button` (the built-in Close button), `escape` or\n * `outside-press` (the backdrop) — so a controlled drawer can refuse only some ways of closing\n * (for example keep a form with unsaved changes open on `outside-press`); `details.event` is the\n * DOM event behind the request. WaveUI always passes `details`; it is typed optional until 1.0\n * so that code which calls this prop itself keeps compiling. An inline drawer asks only with\n * `trigger` (its `Drawer.Trigger` toggles it), `close` and `close-button`: Escape and presses\n * outside it never close it.\n *\n * Fires only when the value changes; a controlled drawer stays as it is until the parent updates\n * `open`.\n */\n onOpenChange?: (open: boolean, details?: DrawerOpenChangeDetails) => void;\n /**\n * How the drawer sits on the page (Fluent's `type`).\n * - `overlay`: a panel over the page, rendered in a portal while open: modal by default (focus\n * moves in and stays there, toasts included; the rest of the page is `inert` and does not\n * scroll; Escape and a backdrop press close it), or `modalType=\"non-modal\"`.\n * - `inline`: a panel in the page layout, rendered where the Drawer is (after its direct\n * `Drawer.Trigger`s) as an `<aside>`, a complementary landmark named by its title. The page\n * stays usable around it: no backdrop, no focus trap, no portal, no scroll lock; Escape and\n * presses outside do not close it. Opening it leaves focus where it is; closing it while focus\n * is inside returns focus to `finalFocusRef`, else the element that opened it, else the\n * trigger. `position` and `size` pick its inner edge and its width (its height at the bottom);\n * where it sits is up to your layout (a flex row of panel and content, for example).\n * `modalType` and `backdrop` do not apply to it, and toasts do not move out of its way: it is\n * page content.\n *\n * Changing `type` remounts the panel and its content (what was typed in it is lost); focus\n * inside an overlay that becomes inline returns to the trigger, and focus inside an inline panel\n * that becomes an overlay moves into the overlay. Rendered as `data-type`.\n * @default 'overlay'\n */\n type?: DrawerType;\n /**\n * Inline drawers: draws a line on the panel's inner edge, the edge facing the page content\n * (`data-separator`). An overlay drawer always draws that edge and ignores this prop. In forced\n * colours an inline drawer's inner edge is always drawn. Fluent's `separator`.\n * @default false\n */\n separator?: boolean;\n /**\n * Side of the screen the drawer is attached to. `start`/`end` follow the text direction;\n * `left`/`right` are physical sides; `bottom` runs along the bottom edge (`size` sets its\n * height). An inline drawer takes its place from your layout: `position` picks its inner edge\n * (the one facing the page content: the end edge of a `start` panel, the top edge of a `bottom`\n * one) and the axis `size` sets. Rendered as `data-position`.\n * @default 'end'\n */\n position?: DrawerPosition;\n /**\n * The panel's width at a side — `small` 320px, `medium` 592px, `large` 940px, `full` the\n * viewport's width — or its height at the bottom (the same values; `full` the viewport's height).\n * It never exceeds the viewport. An inline panel takes the same sizes, where `full` is its\n * container's width (height), and never grows past its container. A width class in `className`\n * (a height class for `bottom`) replaces it. It also times the motion, an overlay's slide and an\n * inline drawer's collapse alike: 250 ms small, 300 ms medium, 400 ms large, 500 ms full (an\n * inline drawer at `full` has no motion; see `motion`). Rendered as `data-size`. Fluent's\n * `size`.\n * @default 'small'\n */\n size?: DrawerSize;\n /**\n * `modal`, `alert` or `non-modal`, as Dialog's `modalType`. `modal`: the page behind is `inert`\n * and does not scroll; a backdrop press, Escape, the Close button and `Drawer.Close` close it.\n * `alert`: `role=\"alertdialog\"` (a `role` you pass wins), and a backdrop press does not close it\n * (Escape still does). `non-modal`: no backdrop, and the page stays usable — no focus trap,\n * nothing inert, the page scrolls; Tab and Shift+Tab leave the drawer in the page's order right\n * after the element that opened it, Escape closes it while focus is inside it, presses on the\n * page never close it, and focus returns to the opener only when it was inside the drawer. A\n * non-modal drawer covers the page under it while Tab still reaches that page: reserve its width\n * (its height at the bottom) in your layout while it is open, or use `modal`, or, for a panel\n * beside the content, an inline drawer (`type=\"inline\"`) (with `size=\"full\"` it covers\n * everything, and a development warning says so). Every type moves focus to the first focusable\n * element on open. Rendered as `data-modal-type`. Ignored by an inline drawer, which is never\n * modal and renders no `data-modal-type`. Fluent's `modalType`.\n * @default 'modal'\n */\n modalType?: DrawerModalType;\n /**\n * The backdrop of a modal or alert drawer, as `Dialog.Content`'s `backdrop`: a `div` behind the\n * panel, `aria-hidden`. Shorthand content renders inside it; a slot object's `className` (merged\n * last), `style`, data attributes, `ref` and handlers go to it, and its `appearance`\n * (`'dimmed'` or `'transparent'`) overrides the automatic one: while another modal Dialog or\n * Drawer is open below this one the backdrop is transparent, so the page is dimmed once. `null`\n * renders no backdrop (the page stays inert, and a press outside still closes a modal drawer); a\n * boolean is no slot. Ignored with `modalType=\"non-modal\"` and by an inline drawer (a\n * development warning says so). Fluent's `backdrop`.\n */\n backdrop?: Slot<'div'> | (SlotObject<'div'> & { appearance?: BackdropAppearance });\n /**\n * The drawer's motion. By default an overlay panel slides in from beyond its edge and fades in\n * with a decelerating curve, and slides back out and fades out with an accelerating curve; the\n * `start` and `end` edges follow the text direction, `left` and `right` do not mirror, and a\n * `bottom` panel rises from below. An inline drawer by default opens the space it takes in your\n * layout from nothing (its width at a side, its height at the bottom) while its panel fades in,\n * held at its size against its inner edge, so it reads as sliding out from that edge, with a\n * decelerating curve; closing runs the same backwards with an accelerating curve. Both take a\n * duration that follows `size` both ways: 250 ms small, 300 ms medium, 400 ms large, 500 ms\n * full. An inline drawer at `full` has no motion, as its size is its container's (a value here\n * does not apply to it either), and an inline drawer whose width (height at the bottom) in\n * `className` is a percentage resizes oddly during the motion, correctly once open: give it a\n * length, or pass `null`. Under reduced motion the drawer appears and disappears at once.\n * `null` turns the motion off (the drawer still renders its `data-presence` phases, which then\n * end at once); a class string or `{ className }` replaces the default classes with yours (see\n * `MotionSlot`), also under a `WaveProvider` with `motion=\"none\"`, which otherwise turns the\n * default off. They go on the overlay panel, or on the element around an inline drawer's\n * `<aside>` (`wave-drawer__collapse`), whose phases the drawer waits for. A `className` that\n * holds `data-[presence=…]` classes while `motion` is unset keeps 0.14's behaviour: no default\n * motion, your classes animate the panel, and the drawer waits for the panel's motion (an\n * inline one's `<aside>`, not the element around it). Fluent's `OverlayDrawer` and\n * `InlineDrawer` `surfaceMotion`.\n * @default the slide (overlay) or the collapse (inline) above\n */\n motion?: MotionSlot | null;\n /**\n * The backdrop's motion (a modal or alert overlay). By default it fades in and out with a\n * linear curve over the panel's duration (250 to 500 ms, by `size`), so it ends with the panel;\n * under reduced motion it appears and disappears at once. `null` turns the motion off; a class\n * string or `{ className }` replaces the default classes with yours (see `MotionSlot`), also\n * under a `WaveProvider` with `motion=\"none\"`, which otherwise turns the default off. The\n * panel's motion decides when the drawer unmounts or hides: a replacement longer than the\n * panel's exit is cut off there. Ignored with `modalType=\"non-modal\"` and by an inline drawer\n * (a development warning says so). Fluent's `OverlayDrawer` `backdropMotion`.\n * @default the fade above\n */\n backdropMotion?: MotionSlot | null;\n /**\n * Content of the built-in Close button, in the built-in header and in every\n * `Drawer.HeaderTitle`, as `Dialog.Content`'s `closeButton`: decorative content inside the button\n * (the dismiss glyph by default), so the button keeps the name `closeLabel`; a slot object's\n * `aria-label`, `aria-labelledby` or `title` names it instead, and its handlers run before the\n * close (`preventDefault()` keeps the drawer open). `null` hides them all (`Drawer.Close`, and\n * Escape on an overlay, still close); a boolean is no slot; content that renders nothing keeps the\n * default glyph. A `<button>` or Wave `Button` passed here is merged into the built-in button,\n * never nested (a development warning says so), and its text label names the button. Fluent's\n * `DrawerHeaderTitle` `action` holds Fluent's close button; WaveUI renders its own.\n */\n closeButton?: Slot<'span'>;\n /**\n * Header buttons for the `title` prop form, between the heading and the built-in Close button in\n * DOM and Tab order. Ignored, with a development warning, next to a `Drawer.Header` (use the\n * `action` of `Drawer.HeaderTitle`). Interactive: name icon-only buttons. Renders nothing when\n * empty. Fluent's `DrawerHeaderTitle` `action`, for the `title` prop form.\n */\n titleAction?: Slot<'span'>;\n /**\n * Title displayed in the built-in header; it names the drawer (`aria-labelledby`). Without it,\n * render a `Drawer.HeaderTitle` (in a `Drawer.Header`) or a `Drawer.Title`, or pass\n * `aria-label`/`aria-labelledby`. A title that renders nothing (`''`, `[]`, `true`) counts as\n * none. Ignored, with a development warning, when the children hold a `Drawer.Header`, which\n * replaces the built-in header. The heading is an `<h2>`; for another level use\n * `Drawer.HeaderTitle` with `headingLevel`. In the server HTML of an inline drawer only `title`\n * (or `aria-label`/`aria-labelledby`) names the panel: a `Drawer.HeaderTitle` or `Drawer.Title`\n * names it once the page has hydrated.\n */\n title?: React.ReactNode;\n /**\n * Accessible name of the built-in Close button (an icon-only button), in the built-in header and\n * in every `Drawer.HeaderTitle`. Localize it with the page's language. A text label of a button\n * merged into `closeButton` names it instead.\n * @default 'Close'\n */\n closeLabel?: string;\n /**\n * Where focus goes when the drawer closes, if it can take focus. Otherwise focus returns to the\n * element that had focus when the drawer opened, then to the trigger, then to an element next to\n * where that opener was. An inline or non-modal drawer moves focus on close only when focus was\n * inside it.\n */\n finalFocusRef?: React.RefObject<HTMLElement | null>;\n /**\n * Removes the panel and its content when the drawer closes, once the panel's exit motion has\n * ended. `false` keeps them mounted while closed, `hidden` and `inert` (out of the layout, the\n * Tab order and the accessibility tree), so what was typed and the state of the components\n * inside survive closing and opening again; the content then mounts with the Drawer, closed, and\n * an `autoFocus` inside it never applies (an overlay focuses its first focusable element on each\n * open). An overlay panel still renders only in the browser; a kept inline panel is in the\n * server HTML, hidden. Kept content still belongs to its form: a `required` empty field in a\n * closed inline drawer inside a page `<form>` blocks its submission without a visible message. A\n * popup opened inside that is still open when the drawer closes stays open over the page (a\n * development warning says so): close it first. A `key` on the Drawer resets the kept content.\n * Fluent's `unmountOnClose`.\n * @default true\n */\n unmountOnClose?: boolean;\n /**\n * The drawer's content, placed by the Drawer, also from a Fragment (`{isMobile && <>…</>}`) and\n * when written in a Server Component: `Drawer.Trigger` children render in place (outside the\n * panel); a `Drawer.Header` replaces the built-in header (the `title` and Close button row); a\n * `Drawer.Body` gives the scrolling body its props; `Drawer.Footer` renders below the scrolling\n * body, outside it, wherever it is written among the children; everything else renders in the\n * scrolling body. A part nested in another element (a `<form>`) or rendered by a component of\n * yours renders where it is, in the body (a development warning says so). A `Drawer.Trigger`\n * nested in another element, or rendered by a component, is panel content, so it is not rendered\n * (or, kept mounted, is hidden) while the drawer is closed (development warnings say so, also\n * when an uncontrolled drawer still has no direct trigger a second after it mounts and therefore\n * cannot open; a controlled drawer whose trigger a component such as a Tooltip wraps warns only\n * once it renders in the panel).\n * Put wrappers inside the trigger instead: see `Drawer.Trigger`.\n */\n children: React.ReactNode;\n /**\n * Ref to the panel: the `role=\"dialog\"` element of an overlay drawer (`alertdialog` with\n * `modalType=\"alert\"`), the `<aside>` of an inline one. A ref to a `div` still type-checks.\n */\n ref?: React.Ref<HTMLElement>;\n}\n\nconst UNREACHABLE_WARNING_KEY = 'Drawer:unreachable';\nconst UNREACHABLE_WARNING =\n 'Drawer has no way to open: a second after mounting it is still uncontrolled (no `open` prop), closed, and has no Drawer.Trigger as a direct child (or in a Fragment there). A Drawer.Trigger rendered by a component or nested in an element is panel content, which is not rendered or is hidden while the drawer is closed. Make the trigger a direct child of Drawer, or control the Drawer with `open`/`onOpenChange`.';\n\n/**\n * How long after mount (ms) the development check for a drawer without a trigger waits: long\n * enough for a trigger that a conditional Fragment renders once the page knows its layout.\n */\nconst REACHABILITY_CHECK_DELAY = 1000;\n\n/** Deepest element level the development check for nested triggers looks at. */\nconst NESTED_TRIGGER_MAX_DEPTH = 32;\n\n/**\n * Development check: whether the Drawer's children hold a `Drawer.Trigger` inside a host element\n * (at any depth, also through Fragments), which would become panel content; a trigger inside\n * Fragments only is direct (see `splitChildren`). Walks the element tree the consumer wrote, not\n * rendered output, so it descends only into host elements (`<div>`, `<span>`, …) and Fragments,\n * which render their `children` as written. A component's\n * output is unknown here — a wrapper that renders its own Drawer around its children, for one —\n * so components are not walked; a trigger rendered by a component is caught when it renders in the\n * open panel, or, while the drawer cannot open, by the unreachable-drawer check.\n */\nfunction hasNestedTrigger(children: React.ReactNode): boolean {\n // `depth` counts host elements only: a Fragment adds no level, as `splitChildren` flattens it.\n const visit = (node: unknown, depth: number, level: number): boolean => {\n if (level > NESTED_TRIGGER_MAX_DEPTH || typeof node !== 'object' || node === null) return false;\n if (Array.isArray(node)) return node.some((item) => visit(item, depth, level));\n if (!React.isValidElement(node)) return false;\n // A part written in a Server Component has a lazy type. The walk runs in effects, outside\n // render: a lazy part that is still loading must not throw its thenable there, so it counts\n // as no trigger (`suspend: false` returns the lazy itself, which matches nothing).\n const type = getElementType(node, { suspend: false });\n if (type === DrawerTrigger) return depth > 0;\n const isFragment = type === React.Fragment;\n if (typeof type !== 'string' && !isFragment) return false;\n const { children: nested } = node.props as { children?: unknown };\n return visit(nested, isFragment ? depth : depth + 1, level + 1);\n };\n return visit(children, 0, 0);\n}\n\nconst TITLE_IGNORED_WARNING_KEY = 'Drawer:title-ignored';\nconst TITLE_IGNORED_WARNING =\n 'Drawer: `title` and `titleAction` are ignored because a Drawer.Header is among the children. Put a Drawer.HeaderTitle (with its `action`) in the header instead.';\n\nconst BODY_DUPLICATE_WARNING_KEY = 'Drawer.Body:duplicate';\nconst BODY_DUPLICATE_WARNING =\n 'Drawer has more than one Drawer.Body: the props of the first one apply to the scrolling body, and the children of every one render in their place. Render one Drawer.Body.';\n\n/** How the Drawer sorts its direct children ({@link splitChildren}). */\ninterface DrawerPartition {\n /** The direct `Drawer.Trigger` elements, rendered in place. */\n triggers: React.ReactNode[];\n /** The direct `Drawer.Header` elements, rendered in the header area in written order. */\n headers: React.ReactNode[];\n /** The props of the first direct `Drawer.Body` (its `children` render in `content`). */\n bodyProps: DrawerBodyProps | undefined;\n /** How many direct `Drawer.Body` elements there are. */\n bodyCount: number;\n /** The body content in written order; a `Drawer.Body` is replaced by its children. */\n content: React.ReactNode[];\n /** The direct `Drawer.Footer` elements, rendered after the body in written order. */\n footers: React.ReactNode[];\n}\n\n/**\n * Sorts the Drawer's children: its direct `Drawer.Trigger`, `Drawer.Header`, `Drawer.Body` and\n * `Drawer.Footer` elements and the body content. Fragments are flattened (recursively), so a part\n * in a Fragment — `{isMobile && <><Drawer.Trigger>…</Drawer.Trigger><Filters /></>}` — counts as a\n * direct child. Every element keeps the key `flattenChildren` gives it: unique across Fragments and\n * stable when a sibling Fragment toggles, so body content keeps its state when a part appears. A\n * part is recognised also when it was written in a Server Component (a lazy type). Runs during\n * render, so the placement is the same on the server.\n */\nfunction splitChildren(children: React.ReactNode): DrawerPartition {\n const partition: DrawerPartition = {\n triggers: [],\n headers: [],\n bodyProps: undefined,\n bodyCount: 0,\n content: [],\n footers: [],\n };\n for (const { key, node } of flattenChildren(children)) {\n if (isElementOfType<DrawerBodyProps>(node, DrawerBody)) {\n // The first Body's props go on the scrolling body; every Body's children render in place.\n partition.bodyCount += 1;\n if (partition.bodyCount === 1) partition.bodyProps = node.props;\n partition.content.push(<React.Fragment key={key}>{node.props.children}</React.Fragment>);\n continue;\n }\n const keyed = React.isValidElement(node) ? React.cloneElement(node, { key }) : node;\n if (isElementOfType(node, DrawerTrigger)) partition.triggers.push(keyed);\n else if (isElementOfType(node, DrawerHeader)) partition.headers.push(keyed);\n else if (isElementOfType(node, DrawerFooter)) partition.footers.push(keyed);\n else partition.content.push(keyed);\n }\n return partition;\n}\n\n/** Properties of the built-in header ({@link DrawerBuiltInHeader}). */\ninterface DrawerBuiltInHeaderProps {\n /** The `title` prop, when it renders content. */\n title: React.ReactNode;\n /** Whether `title` renders content (else no heading renders). */\n hasTitle: boolean;\n /** The heading's id (the panel's `aria-labelledby`). */\n titleId: string;\n /** The `titleAction` slot. */\n titleAction: Slot<'span'> | undefined;\n requestOpen: ModalRequestOpen;\n closeLabel: string;\n /** The `closeButton` slot (`null`: no Close button). */\n closeButton: Slot<'span'> | undefined;\n}\n\n/**\n * The 0.10 header row of the `title` form (no `Drawer.Header` among the children): the `title`\n * heading, the `titleAction` content and the Close button as its direct children. The title action\n * takes the free room (`ms-auto`), so the Close button follows it through the row's gap; without\n * one the Close button does. It reads the body's scroll state for its separator. A row with\n * nothing in it (no title, no title action, `closeButton={null}`) renders no element.\n */\nfunction DrawerBuiltInHeader({\n title,\n hasTitle,\n titleId,\n titleAction,\n requestOpen,\n closeLabel,\n closeButton,\n}: DrawerBuiltInHeaderProps) {\n const scrollState = React.useContext(DrawerScrollStateContext) ?? 'none';\n const hasTitleAction = slotRendersContent(titleAction);\n if (!hasTitle && !hasTitleAction && closeButton === null) return null;\n return (\n <div\n data-scroll-state={scrollState}\n className={cn(\n drawerClassNames.header,\n 'flex shrink-0 items-center justify-between gap-2 p-4',\n scrollSeparatorClasses.header,\n )}\n >\n {hasTitle && (\n <h2\n id={titleId}\n className={cn(drawerTitleClassNames.root, 'text-subtitle-1 font-semibold')}\n >\n {title}\n </h2>\n )}\n {hasTitleAction\n ? renderSlot(\n titleAction,\n 'span',\n cn(drawerClassNames.titleAction, 'ms-auto flex shrink-0 items-center gap-1'),\n )\n : null}\n <DrawerCloseButton\n requestOpen={requestOpen}\n label={closeLabel}\n closeButton={closeButton}\n className={cn(!hasTitleAction && 'ms-auto', 'text-muted-foreground')}\n />\n </div>\n );\n}\nDrawerBuiltInHeader.displayName = 'DrawerBuiltInHeader';\n\n/** Properties of {@link DrawerLayout}. */\ninterface DrawerLayoutProps {\n /** The header area: the built-in header, or the placed `Drawer.Header` elements. */\n header: React.ReactNode;\n /** The props of the placed `Drawer.Body`, put on the scrolling body. */\n bodyProps: DrawerBodyProps | undefined;\n /** The body content. */\n content: React.ReactNode;\n /** The placed `Drawer.Footer` elements. */\n footers: React.ReactNode;\n}\n\n/**\n * The panel's layout (internal): the header area, the scrolling body and the footers. It owns the\n * body's scroll state (`useScrollState`), so a change of the state re-renders this component, the\n * body element and the parts that read the state (the header area and the footers), never the\n * consumer's content: the elements it receives as props are the same objects, so React skips them.\n */\nfunction DrawerLayout({ header, bodyProps, content, footers }: DrawerLayoutProps) {\n const [body, setBody] = React.useState<HTMLDivElement | null>(null);\n const scrollState = useScrollState(body);\n const { children: _children, className, ref, ...bodyRest } = bodyProps ?? {};\n const bodyRef = useMergedRefs<HTMLDivElement>(setBody, ref);\n return (\n <DrawerScrollStateContext.Provider value={scrollState}>\n <DrawerHeaderContext.Provider value={false}>\n <DrawerPartContext.Provider value=\"placed\">{header}</DrawerPartContext.Provider>\n <div\n data-scroll-state={scrollState}\n {...bodyRest}\n ref={bodyRef}\n className={cn(\n drawerClassNames.body,\n bodyProps && drawerBodyClassNames.root,\n 'min-h-0 flex-1 overflow-y-auto p-4',\n focusRingInset,\n className,\n )}\n >\n <DrawerPartContext.Provider value=\"content\">{content}</DrawerPartContext.Provider>\n </div>\n <DrawerPartContext.Provider value=\"placed\">{footers}</DrawerPartContext.Provider>\n </DrawerHeaderContext.Provider>\n </DrawerScrollStateContext.Provider>\n );\n}\nDrawerLayout.displayName = 'DrawerLayout';\n\n// The root of `Drawer` (documented on the export in Drawer.tsx).\nexport const DrawerRoot = ({\n open: openProp,\n defaultOpen,\n onOpenChange,\n type = 'overlay',\n separator = false,\n position = 'end',\n size = 'small',\n modalType = 'modal',\n backdrop,\n motion,\n backdropMotion,\n closeButton,\n titleAction,\n title,\n closeLabel = 'Close',\n finalFocusRef,\n unmountOnClose = true,\n children,\n id,\n ref,\n ...rest\n}: DrawerProps) => {\n const [openState, requestOpen] = useModalOpenState(openProp, defaultOpen, onOpenChange);\n // An overlay's panel lives in a portal, which renders only in the browser: until then (the\n // server HTML, hydration) it reports itself closed, so the trigger's aria-expanded and\n // aria-controls never describe a panel that is not there. An inline panel renders in place, also\n // on the server (D107).\n const open = useDrawerOpen(type, openState);\n const trigger = useModalTrigger();\n const generatedId = useId('wave-drawer');\n const panelId = id ?? generatedId;\n const propTitleId = useId('wave-drawer-title');\n const titles = useTitleRegistry();\n // The mounted panel (the shell's element of either type), for the unnamed-drawer check.\n const [panel, setPanel] = React.useState<HTMLElement | null>(null);\n const panelRef = useMergedRefs<HTMLElement>(ref, setPanel);\n useUnnamedModalWarning(\n open ? panel : null,\n titles.hasTitle,\n 'Drawer',\n 'Drawer.HeaderTitle or a Drawer.Title',\n );\n\n const { triggers, headers, bodyProps, bodyCount, content, footers } = splitChildren(children);\n const hasHeader = headers.length > 0;\n // A Drawer.Header replaces the built-in header, whose `title` it cannot show.\n const titleRendersContent = slotRendersContent(title);\n const hasTitle = titleRendersContent && !hasHeader;\n const titleIgnored = (titleRendersContent || slotRendersContent(titleAction)) && hasHeader;\n React.useEffect(() => {\n if (titleIgnored) warnOnce(TITLE_IGNORED_WARNING_KEY, TITLE_IGNORED_WARNING);\n }, [titleIgnored]);\n const duplicateBody = bodyCount > 1;\n React.useEffect(() => {\n if (duplicateBody) warnOnce(BODY_DUPLICATE_WARNING_KEY, BODY_DUPLICATE_WARNING);\n }, [duplicateBody]);\n\n // A trigger nested in the children is panel content: not rendered (or, kept mounted, hidden) while\n // the drawer is closed.\n // The children change on every parent render; once this drawer has warned, it stops walking.\n const nestedWarnedRef = React.useRef(false);\n React.useEffect(() => {\n if (!isDev || nestedWarnedRef.current || !hasNestedTrigger(children)) return;\n nestedWarnedRef.current = true;\n warnOnce(NESTED_TRIGGER_WARNING_KEY, NESTED_TRIGGER_WARNING);\n }, [children]);\n\n // An uncontrolled closed drawer without a direct trigger cannot open (e.g.\n // `<Drawer><FilterTrigger /></Drawer>`, whose trigger is panel content). Checked once, a moment\n // after mount, against the latest render: a trigger that a conditional Fragment adds right after\n // mount (`{isMobile && <>…</>}` with an SSR-safe media query) counts. A trigger nested in an\n // element already has the more specific warning above.\n const unreachable = openProp === undefined && !defaultOpen && triggers.length === 0;\n const latestRef = React.useRef({ unreachable, children });\n React.useLayoutEffect(() => {\n latestRef.current = { unreachable, children };\n });\n React.useEffect(() => {\n if (!isDev || !latestRef.current.unreachable) return;\n const timer = setTimeout(() => {\n const latest = latestRef.current;\n if (latest.unreachable && !hasNestedTrigger(latest.children)) {\n warnOnce(UNREACHABLE_WARNING_KEY, UNREACHABLE_WARNING);\n }\n }, REACHABILITY_CHECK_DELAY);\n return () => clearTimeout(timer);\n }, []);\n\n const context = React.useMemo<DrawerContextValue>(\n () => ({ open, requestOpen, trigger, panelId, type, inPanel: false, closeLabel, closeButton }),\n [open, requestOpen, trigger, panelId, type, closeLabel, closeButton],\n );\n const panelContext = React.useMemo<DrawerContextValue>(\n () => ({ ...context, inPanel: true }),\n [context],\n );\n\n // The panel's content: the header area, the scrolling body and the footers, for both types.\n const layout = (\n <DrawerContext.Provider value={panelContext}>\n <ModalSurfaceContext.Provider value={titles.context}>\n <DrawerLayout\n header={\n hasHeader ? (\n headers\n ) : (\n <DrawerBuiltInHeader\n title={title}\n hasTitle={hasTitle}\n titleId={propTitleId}\n titleAction={titleAction}\n requestOpen={requestOpen}\n closeLabel={closeLabel}\n closeButton={closeButton}\n />\n )\n }\n bodyProps={bodyProps}\n content={content}\n footers={footers}\n />\n </ModalSurfaceContext.Provider>\n </DrawerContext.Provider>\n );\n const labelledBy = hasTitle ? propTitleId : titles.titleId;\n\n // The panel and its machinery (portal, backdrop, presence, layer, trap, restore, Tab order) come\n // from the shell (D108); the root names it and fills it with its layout.\n const panelElement = (\n <DrawerPanel\n componentName=\"Drawer\"\n type={type}\n open={open}\n requestOpen={requestOpen}\n position={position}\n size={size}\n separator={separator}\n modalType={modalType}\n unmountOnClose={unmountOnClose}\n inlineAs=\"aside\"\n trigger={trigger}\n finalFocusRef={finalFocusRef}\n rootClassName={drawerClassNames.root}\n backdropClassName={drawerClassNames.backdrop}\n collapseClassName={drawerClassNames.collapse}\n backdrop={backdrop}\n motion={motion}\n backdropMotion={backdropMotion}\n id={panelId}\n aria-labelledby={labelledBy}\n {...rest}\n ref={panelRef}\n >\n {layout}\n </DrawerPanel>\n );\n // After the shell's focus restores (its effects run before the root's), start the trigger\n // session, or end it and forget the trigger that opened it.\n useModalTriggerSession(trigger, open);\n\n return (\n <DrawerContext.Provider value={context}>\n {triggers}\n {panelElement}\n </DrawerContext.Provider>\n );\n};\nDrawerRoot.displayName = 'Drawer';\n"],"mappings":"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"}
|
|
@@ -102,29 +102,29 @@ function F({ header: t, bodyProps: n, content: r, footers: i }) {
|
|
|
102
102
|
});
|
|
103
103
|
}
|
|
104
104
|
F.displayName = "DrawerLayout";
|
|
105
|
-
var I = ({ open: e, defaultOpen: t, onOpenChange: n, type: r = "overlay", separator: o = !1, position: c = "end", size: u = "small", modalType: p = "modal", backdrop: v,
|
|
106
|
-
let [
|
|
107
|
-
te(R ?
|
|
108
|
-
let { triggers: U, headers: W, bodyProps:
|
|
105
|
+
var I = ({ open: e, defaultOpen: t, onOpenChange: n, type: r = "overlay", separator: o = !1, position: c = "end", size: u = "small", modalType: p = "modal", backdrop: v, motion: y, backdropMotion: x, closeButton: S, titleAction: C, title: w, closeLabel: T = "Close", finalFocusRef: E, unmountOnClose: D = !0, children: O, id: M, ref: I, ...me }) => {
|
|
106
|
+
let [he, L] = h(e, t, n), R = re(r, he), z = g(), ge = d("wave-drawer"), B = M ?? ge, V = d("wave-drawer-title"), H = ee(), [_e, ve] = k.useState(null), ye = f(I, ve);
|
|
107
|
+
te(R ? _e : null, H.hasTitle, "Drawer", "Drawer.HeaderTitle or a Drawer.Title");
|
|
108
|
+
let { triggers: U, headers: W, bodyProps: be, bodyCount: xe, content: Se, footers: Ce } = pe(O), G = W.length > 0, K = s(w), q = K && !G, J = (K || s(C)) && G;
|
|
109
109
|
k.useEffect(() => {
|
|
110
110
|
J && a(le, ue);
|
|
111
111
|
}, [J]);
|
|
112
|
-
let Y =
|
|
112
|
+
let Y = xe > 1;
|
|
113
113
|
k.useEffect(() => {
|
|
114
114
|
Y && a(de, fe);
|
|
115
115
|
}, [Y]);
|
|
116
116
|
let X = k.useRef(!1);
|
|
117
117
|
k.useEffect(() => {
|
|
118
|
-
i && !X.current && N(
|
|
119
|
-
}, [
|
|
118
|
+
i && !X.current && N(O) && (X.current = !0, a(ae, ie));
|
|
119
|
+
}, [O]);
|
|
120
120
|
let Z = e === void 0 && !t && U.length === 0, Q = k.useRef({
|
|
121
121
|
unreachable: Z,
|
|
122
|
-
children:
|
|
122
|
+
children: O
|
|
123
123
|
});
|
|
124
124
|
k.useLayoutEffect(() => {
|
|
125
125
|
Q.current = {
|
|
126
126
|
unreachable: Z,
|
|
127
|
-
children:
|
|
127
|
+
children: O
|
|
128
128
|
};
|
|
129
129
|
}), k.useEffect(() => {
|
|
130
130
|
if (!i || !Q.current.unreachable) return;
|
|
@@ -141,39 +141,39 @@ var I = ({ open: e, defaultOpen: t, onOpenChange: n, type: r = "overlay", separa
|
|
|
141
141
|
panelId: B,
|
|
142
142
|
type: r,
|
|
143
143
|
inPanel: !1,
|
|
144
|
-
closeLabel:
|
|
145
|
-
closeButton:
|
|
144
|
+
closeLabel: T,
|
|
145
|
+
closeButton: S
|
|
146
146
|
}), [
|
|
147
147
|
R,
|
|
148
148
|
L,
|
|
149
149
|
z,
|
|
150
150
|
B,
|
|
151
151
|
r,
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
]),
|
|
152
|
+
T,
|
|
153
|
+
S
|
|
154
|
+
]), we = k.useMemo(() => ({
|
|
155
155
|
...$,
|
|
156
156
|
inPanel: !0
|
|
157
|
-
}), [$]),
|
|
158
|
-
value:
|
|
157
|
+
}), [$]), Te = /* @__PURE__ */ A(b.Provider, {
|
|
158
|
+
value: we,
|
|
159
159
|
children: /* @__PURE__ */ A(m.Provider, {
|
|
160
160
|
value: H.context,
|
|
161
161
|
children: /* @__PURE__ */ A(F, {
|
|
162
162
|
header: G ? W : /* @__PURE__ */ A(P, {
|
|
163
|
-
title:
|
|
163
|
+
title: w,
|
|
164
164
|
hasTitle: q,
|
|
165
165
|
titleId: V,
|
|
166
|
-
titleAction:
|
|
166
|
+
titleAction: C,
|
|
167
167
|
requestOpen: L,
|
|
168
|
-
closeLabel:
|
|
169
|
-
closeButton:
|
|
168
|
+
closeLabel: T,
|
|
169
|
+
closeButton: S
|
|
170
170
|
}),
|
|
171
|
-
bodyProps:
|
|
172
|
-
content:
|
|
173
|
-
footers:
|
|
171
|
+
bodyProps: be,
|
|
172
|
+
content: Se,
|
|
173
|
+
footers: Ce
|
|
174
174
|
})
|
|
175
175
|
})
|
|
176
|
-
}),
|
|
176
|
+
}), Ee = q ? V : H.titleId, De = /* @__PURE__ */ A(ne, {
|
|
177
177
|
componentName: "Drawer",
|
|
178
178
|
type: r,
|
|
179
179
|
open: R,
|
|
@@ -182,22 +182,25 @@ var I = ({ open: e, defaultOpen: t, onOpenChange: n, type: r = "overlay", separa
|
|
|
182
182
|
size: u,
|
|
183
183
|
separator: o,
|
|
184
184
|
modalType: p,
|
|
185
|
-
unmountOnClose:
|
|
185
|
+
unmountOnClose: D,
|
|
186
186
|
inlineAs: "aside",
|
|
187
187
|
trigger: z,
|
|
188
|
-
finalFocusRef:
|
|
188
|
+
finalFocusRef: E,
|
|
189
189
|
rootClassName: l.root,
|
|
190
190
|
backdropClassName: l.backdrop,
|
|
191
|
+
collapseClassName: l.collapse,
|
|
191
192
|
backdrop: v,
|
|
193
|
+
motion: y,
|
|
194
|
+
backdropMotion: x,
|
|
192
195
|
id: B,
|
|
193
|
-
"aria-labelledby":
|
|
194
|
-
...
|
|
195
|
-
ref:
|
|
196
|
-
children:
|
|
196
|
+
"aria-labelledby": Ee,
|
|
197
|
+
...me,
|
|
198
|
+
ref: ye,
|
|
199
|
+
children: Te
|
|
197
200
|
});
|
|
198
201
|
return _(z, R), /* @__PURE__ */ j(b.Provider, {
|
|
199
202
|
value: $,
|
|
200
|
-
children: [U,
|
|
203
|
+
children: [U, De]
|
|
201
204
|
});
|
|
202
205
|
};
|
|
203
206
|
I.displayName = "Drawer";
|