@sovereignfs/ui 0.83.1 → 0.89.1
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/LICENSE +373 -661
- package/NOTICE +8 -0
- package/README.md +4 -6
- package/dist/AppsLauncher.module.css +6 -0
- package/dist/Button.module.css +5 -0
- package/dist/Card.module.css +6 -0
- package/dist/CardTile.module.css +6 -0
- package/dist/CheckableListRow.module.css +8 -0
- package/dist/Checkbox.module.css +8 -0
- package/dist/CodeTextarea.module.css +6 -0
- package/dist/ColorPicker.module.css +6 -0
- package/dist/Combobox.module.css +6 -0
- package/dist/Command.module.css +6 -0
- package/dist/ConfirmDialog.module.css +6 -0
- package/dist/DatePicker.module.css +6 -0
- package/dist/Dialog.module.css +1 -1
- package/dist/DragHandleRow.module.css +6 -0
- package/dist/FileDropzone.module.css +25 -1
- package/dist/Header.module.css +6 -0
- package/dist/IconPicker.module.css +14 -4
- package/dist/Input.module.css +6 -0
- package/dist/LegalLinks.module.css +9 -2
- package/dist/Markdown.module.css +5 -0
- package/dist/Message.module.css +9 -0
- package/dist/MobileAppsDrawer.module.css +9 -5
- package/dist/MobileFooter.module.css +6 -0
- package/dist/NavList.module.css +11 -2
- package/dist/NavTabs.module.css +7 -1
- package/dist/NotificationsPanel.module.css +10 -0
- package/dist/QrCode.module.css +17 -0
- package/dist/QuantityStepper.module.css +4 -2
- package/dist/RadioGroup.module.css +6 -0
- package/dist/SegmentedControl.module.css +6 -0
- package/dist/Select.module.css +6 -0
- package/dist/Sheet.module.css +16 -1
- package/dist/SplitPane.module.css +1 -1
- package/dist/StepStrip.module.css +5 -3
- package/dist/SuggestionInput.module.css +12 -1
- package/dist/SwipableMobileCarouselDots.module.css +6 -0
- package/dist/SystemBanner.module.css +6 -0
- package/dist/Tabs.module.css +6 -0
- package/dist/TagInput.module.css +6 -0
- package/dist/Textarea.module.css +6 -0
- package/dist/Toast.module.css +5 -0
- package/dist/Toggle.module.css +7 -0
- package/dist/Tooltip.module.css +6 -0
- package/dist/UserMenu.module.css +5 -0
- package/dist/fonts/OFL.txt +93 -0
- package/dist/fonts/hanken-grotesk-cyrillic-ext-wght-normal.woff2 +0 -0
- package/dist/fonts/hanken-grotesk-latin-ext-wght-normal.woff2 +0 -0
- package/dist/fonts/hanken-grotesk-latin-wght-normal.woff2 +0 -0
- package/dist/fonts/hanken-grotesk-vietnamese-wght-normal.woff2 +0 -0
- package/dist/index.d.ts +121 -43
- package/dist/index.js +1410 -1152
- package/dist/tokens/fonts.css +53 -0
- package/dist/tokens/primitives.css +12 -12
- package/dist/tokens.css +2 -1
- package/package.json +24 -13
- package/src/__tests__/motion.test.tsx +0 -105
- package/src/__tests__/package-json.test.ts +0 -8
- package/src/components/Accordion/Accordion.module.css +0 -3
- package/src/components/Accordion/Accordion.stories.tsx +0 -110
- package/src/components/Accordion/Accordion.tsx +0 -53
- package/src/components/Accordion/__tests__/Accordion.test.tsx +0 -61
- package/src/components/Alert/Alert.module.css +0 -62
- package/src/components/Alert/Alert.stories.tsx +0 -96
- package/src/components/Alert/Alert.tsx +0 -58
- package/src/components/Alert/__tests__/Alert.test.tsx +0 -75
- package/src/components/AppsLauncher/AppsLauncher.module.css +0 -96
- package/src/components/AppsLauncher/AppsLauncher.stories.tsx +0 -58
- package/src/components/AppsLauncher/AppsLauncher.tsx +0 -117
- package/src/components/AppsLauncher/__tests__/AppsLauncher.test.tsx +0 -52
- package/src/components/AspectRatio/AspectRatio.module.css +0 -15
- package/src/components/AspectRatio/AspectRatio.stories.tsx +0 -78
- package/src/components/AspectRatio/AspectRatio.tsx +0 -21
- package/src/components/AspectRatio/__tests__/AspectRatio.test.tsx +0 -27
- package/src/components/Avatar/Avatar.module.css +0 -38
- package/src/components/Avatar/Avatar.tsx +0 -42
- package/src/components/Badge/Badge.module.css +0 -177
- package/src/components/Badge/Badge.stories.tsx +0 -238
- package/src/components/Badge/Badge.tsx +0 -84
- package/src/components/Badge/__tests__/Badge.test.tsx +0 -90
- package/src/components/BalanceChip/BalanceChip.module.css +0 -32
- package/src/components/BalanceChip/BalanceChip.stories.tsx +0 -45
- package/src/components/BalanceChip/BalanceChip.tsx +0 -33
- package/src/components/Breadcrumb/Breadcrumb.module.css +0 -49
- package/src/components/Breadcrumb/Breadcrumb.stories.tsx +0 -47
- package/src/components/Breadcrumb/Breadcrumb.tsx +0 -57
- package/src/components/Breadcrumb/__tests__/Breadcrumb.test.tsx +0 -52
- package/src/components/Button/Button.module.css +0 -169
- package/src/components/Button/Button.stories.tsx +0 -83
- package/src/components/Button/Button.tsx +0 -52
- package/src/components/Button/__tests__/Button.test.tsx +0 -66
- package/src/components/ButtonGroup/ButtonGroup.module.css +0 -29
- package/src/components/ButtonGroup/ButtonGroup.stories.tsx +0 -57
- package/src/components/ButtonGroup/ButtonGroup.tsx +0 -27
- package/src/components/ButtonGroup/__tests__/ButtonGroup.test.tsx +0 -29
- package/src/components/Calendar/Calendar.module.css +0 -126
- package/src/components/Calendar/Calendar.tsx +0 -213
- package/src/components/Calendar/__tests__/Calendar.test.tsx +0 -98
- package/src/components/Calendar/dateUtils.ts +0 -97
- package/src/components/Card/Card.module.css +0 -42
- package/src/components/Card/Card.tsx +0 -34
- package/src/components/CardTile/CardTile.module.css +0 -181
- package/src/components/CardTile/CardTile.stories.tsx +0 -86
- package/src/components/CardTile/CardTile.tsx +0 -128
- package/src/components/CardTile/__tests__/CardTile.test.tsx +0 -56
- package/src/components/CheckableListRow/CheckableListRow.module.css +0 -95
- package/src/components/CheckableListRow/CheckableListRow.stories.tsx +0 -99
- package/src/components/CheckableListRow/CheckableListRow.tsx +0 -89
- package/src/components/Checkbox/Checkbox.module.css +0 -111
- package/src/components/Checkbox/Checkbox.tsx +0 -78
- package/src/components/CodeTextarea/CodeTextarea.module.css +0 -53
- package/src/components/CodeTextarea/CodeTextarea.stories.tsx +0 -77
- package/src/components/CodeTextarea/CodeTextarea.tsx +0 -36
- package/src/components/Collapsible/Collapsible.module.css +0 -70
- package/src/components/Collapsible/Collapsible.stories.tsx +0 -62
- package/src/components/Collapsible/Collapsible.tsx +0 -66
- package/src/components/Collapsible/__tests__/Collapsible.test.tsx +0 -71
- package/src/components/ColorPicker/ColorPicker.module.css +0 -132
- package/src/components/ColorPicker/ColorPicker.stories.tsx +0 -80
- package/src/components/ColorPicker/ColorPicker.tsx +0 -157
- package/src/components/ColorPicker/__tests__/ColorPicker.test.tsx +0 -117
- package/src/components/Combobox/Combobox.module.css +0 -122
- package/src/components/Combobox/Combobox.stories.tsx +0 -79
- package/src/components/Combobox/Combobox.tsx +0 -186
- package/src/components/Combobox/__tests__/Combobox.test.tsx +0 -158
- package/src/components/Command/Command.module.css +0 -80
- package/src/components/Command/Command.stories.tsx +0 -104
- package/src/components/Command/Command.tsx +0 -168
- package/src/components/Command/__tests__/Command.test.tsx +0 -162
- package/src/components/ConfirmDialog/ConfirmDialog.module.css +0 -113
- package/src/components/ConfirmDialog/ConfirmDialog.tsx +0 -150
- package/src/components/ConfirmDialog/__tests__/ConfirmDialog.test.tsx +0 -214
- package/src/components/ConsentPrompt/ConsentPrompt.module.css +0 -21
- package/src/components/ConsentPrompt/ConsentPrompt.stories.tsx +0 -31
- package/src/components/ConsentPrompt/ConsentPrompt.tsx +0 -66
- package/src/components/ContextMenu/ContextMenu.stories.tsx +0 -81
- package/src/components/ContextMenu/ContextMenu.tsx +0 -100
- package/src/components/ContextMenu/__tests__/ContextMenu.test.tsx +0 -87
- package/src/components/CurrencyInput/CurrencyInput.stories.tsx +0 -50
- package/src/components/CurrencyInput/CurrencyInput.tsx +0 -60
- package/src/components/DataTable/DataTable.module.css +0 -28
- package/src/components/DataTable/DataTable.stories.tsx +0 -74
- package/src/components/DataTable/DataTable.tsx +0 -154
- package/src/components/DataTable/__tests__/DataTable.test.tsx +0 -123
- package/src/components/DatePicker/DatePicker.module.css +0 -61
- package/src/components/DatePicker/DatePicker.tsx +0 -103
- package/src/components/DatePicker/__tests__/DatePicker.test.tsx +0 -89
- package/src/components/DeviceOnlyGate/DeviceOnlyGate.tsx +0 -58
- package/src/components/DeviceOnlyGate/__tests__/DeviceOnlyGate.test.tsx +0 -45
- package/src/components/DeviceStorageKeyGate/DeviceStorageKeyGate.tsx +0 -100
- package/src/components/DeviceStorageKeyGate/__tests__/DeviceStorageKeyGate.test.tsx +0 -119
- package/src/components/Dialog/Dialog.module.css +0 -335
- package/src/components/Dialog/Dialog.stories.tsx +0 -324
- package/src/components/Dialog/Dialog.tsx +0 -254
- package/src/components/Dialog/__tests__/Dialog.test.tsx +0 -318
- package/src/components/DragHandleRow/DragHandleRow.module.css +0 -57
- package/src/components/DragHandleRow/DragHandleRow.tsx +0 -42
- package/src/components/Drawer/Drawer.module.css +0 -121
- package/src/components/Drawer/Drawer.stories.tsx +0 -132
- package/src/components/Drawer/Drawer.tsx +0 -175
- package/src/components/Drawer/__tests__/Drawer.test.tsx +0 -226
- package/src/components/EmptyState/EmptyState.module.css +0 -27
- package/src/components/EmptyState/EmptyState.tsx +0 -27
- package/src/components/FileDropzone/FileDropzone.module.css +0 -63
- package/src/components/FileDropzone/FileDropzone.tsx +0 -109
- package/src/components/FileDropzone/__tests__/FileDropzone.test.tsx +0 -67
- package/src/components/FormField/FormField.module.css +0 -33
- package/src/components/FormField/FormField.tsx +0 -78
- package/src/components/FormField/__tests__/FormField.test.tsx +0 -83
- package/src/components/GripIcon/GripIcon.tsx +0 -27
- package/src/components/Header/Header.module.css +0 -62
- package/src/components/Header/Header.stories.tsx +0 -452
- package/src/components/Header/Header.tsx +0 -102
- package/src/components/Header/__tests__/Header.test.tsx +0 -104
- package/src/components/HeaderFooterLayout/HeaderFooterLayout.module.css +0 -21
- package/src/components/HeaderFooterLayout/HeaderFooterLayout.stories.tsx +0 -111
- package/src/components/HeaderFooterLayout/HeaderFooterLayout.tsx +0 -54
- package/src/components/HeaderFooterLayout/__tests__/HeaderFooterLayout.test.tsx +0 -58
- package/src/components/HoverCard/HoverCard.module.css +0 -3
- package/src/components/HoverCard/HoverCard.stories.tsx +0 -66
- package/src/components/HoverCard/HoverCard.tsx +0 -111
- package/src/components/HoverCard/__tests__/HoverCard.test.tsx +0 -99
- package/src/components/Icon/Icon.module.css +0 -27
- package/src/components/Icon/Icon.stories.tsx +0 -95
- package/src/components/Icon/Icon.tsx +0 -43
- package/src/components/Icon/__tests__/Icon.test.tsx +0 -40
- package/src/components/Icon/icons/activity.tsx +0 -20
- package/src/components/Icon/icons/alert-triangle.tsx +0 -22
- package/src/components/Icon/icons/apple.tsx +0 -21
- package/src/components/Icon/icons/arrow-left-right.tsx +0 -23
- package/src/components/Icon/icons/banana.tsx +0 -21
- package/src/components/Icon/icons/beef.tsx +0 -22
- package/src/components/Icon/icons/beer.tsx +0 -24
- package/src/components/Icon/icons/bell.tsx +0 -21
- package/src/components/Icon/icons/bold.tsx +0 -20
- package/src/components/Icon/icons/calendar.tsx +0 -23
- package/src/components/Icon/icons/candy.tsx +0 -24
- package/src/components/Icon/icons/carrot.tsx +0 -22
- package/src/components/Icon/icons/check.tsx +0 -20
- package/src/components/Icon/icons/chevron-down.tsx +0 -20
- package/src/components/Icon/icons/chevron-left.tsx +0 -20
- package/src/components/Icon/icons/chevron-right.tsx +0 -20
- package/src/components/Icon/icons/chevron-up.tsx +0 -20
- package/src/components/Icon/icons/circle-check.tsx +0 -21
- package/src/components/Icon/icons/circle-chevron-left.tsx +0 -21
- package/src/components/Icon/icons/circle-x.tsx +0 -22
- package/src/components/Icon/icons/code.tsx +0 -21
- package/src/components/Icon/icons/coffee.tsx +0 -23
- package/src/components/Icon/icons/cookie.tsx +0 -25
- package/src/components/Icon/icons/copy.tsx +0 -21
- package/src/components/Icon/icons/credit-card.tsx +0 -21
- package/src/components/Icon/icons/croissant.tsx +0 -24
- package/src/components/Icon/icons/cup-soda.tsx +0 -23
- package/src/components/Icon/icons/database.tsx +0 -22
- package/src/components/Icon/icons/download.tsx +0 -22
- package/src/components/Icon/icons/drumstick.tsx +0 -21
- package/src/components/Icon/icons/egg.tsx +0 -20
- package/src/components/Icon/icons/ellipsis-vertical.tsx +0 -22
- package/src/components/Icon/icons/external-link.tsx +0 -22
- package/src/components/Icon/icons/eye-off.tsx +0 -23
- package/src/components/Icon/icons/eye.tsx +0 -21
- package/src/components/Icon/icons/file-text.tsx +0 -24
- package/src/components/Icon/icons/file.tsx +0 -21
- package/src/components/Icon/icons/fish.tsx +0 -25
- package/src/components/Icon/icons/folder-closed.tsx +0 -21
- package/src/components/Icon/icons/folder-open.tsx +0 -20
- package/src/components/Icon/icons/folder.tsx +0 -20
- package/src/components/Icon/icons/folders.tsx +0 -21
- package/src/components/Icon/icons/grid-2x2.tsx +0 -22
- package/src/components/Icon/icons/hat-glasses.tsx +0 -24
- package/src/components/Icon/icons/history.tsx +0 -22
- package/src/components/Icon/icons/house.tsx +0 -21
- package/src/components/Icon/icons/inbox.tsx +0 -21
- package/src/components/Icon/icons/index.ts +0 -394
- package/src/components/Icon/icons/info.tsx +0 -22
- package/src/components/Icon/icons/italic.tsx +0 -22
- package/src/components/Icon/icons/layers.tsx +0 -22
- package/src/components/Icon/icons/layout-dashboard.tsx +0 -23
- package/src/components/Icon/icons/layout-grid.tsx +0 -23
- package/src/components/Icon/icons/link.tsx +0 -21
- package/src/components/Icon/icons/list-ordered.tsx +0 -25
- package/src/components/Icon/icons/list.tsx +0 -25
- package/src/components/Icon/icons/lock.tsx +0 -21
- package/src/components/Icon/icons/log-out.tsx +0 -22
- package/src/components/Icon/icons/luggage.tsx +0 -24
- package/src/components/Icon/icons/mail.tsx +0 -21
- package/src/components/Icon/icons/map-pin.tsx +0 -21
- package/src/components/Icon/icons/menu.tsx +0 -22
- package/src/components/Icon/icons/milk.tsx +0 -22
- package/src/components/Icon/icons/minus.tsx +0 -20
- package/src/components/Icon/icons/package.tsx +0 -23
- package/src/components/Icon/icons/paint-bucket.tsx +0 -23
- package/src/components/Icon/icons/panel-left.tsx +0 -21
- package/src/components/Icon/icons/pencil.tsx +0 -21
- package/src/components/Icon/icons/pin.tsx +0 -21
- package/src/components/Icon/icons/pizza.tsx +0 -24
- package/src/components/Icon/icons/plus.tsx +0 -21
- package/src/components/Icon/icons/rectangle-ellipsis.tsx +0 -23
- package/src/components/Icon/icons/refresh-cw.tsx +0 -23
- package/src/components/Icon/icons/rotate-ccw.tsx +0 -21
- package/src/components/Icon/icons/rotate-cw.tsx +0 -21
- package/src/components/Icon/icons/route.tsx +0 -22
- package/src/components/Icon/icons/salad.tsx +0 -24
- package/src/components/Icon/icons/search.tsx +0 -21
- package/src/components/Icon/icons/send.tsx +0 -21
- package/src/components/Icon/icons/settings.tsx +0 -21
- package/src/components/Icon/icons/share-2.tsx +0 -24
- package/src/components/Icon/icons/sheet.tsx +0 -24
- package/src/components/Icon/icons/shield.tsx +0 -20
- package/src/components/Icon/icons/shopping-basket.tsx +0 -26
- package/src/components/Icon/icons/sliders-horizontal.tsx +0 -28
- package/src/components/Icon/icons/smartphone.tsx +0 -21
- package/src/components/Icon/icons/snowflake.tsx +0 -31
- package/src/components/Icon/icons/spray-can.tsx +0 -29
- package/src/components/Icon/icons/square-kanban.tsx +0 -23
- package/src/components/Icon/icons/table.tsx +0 -23
- package/src/components/Icon/icons/trash-2.tsx +0 -24
- package/src/components/Icon/icons/upload.tsx +0 -22
- package/src/components/Icon/icons/user-round-plus.tsx +0 -23
- package/src/components/Icon/icons/user.tsx +0 -21
- package/src/components/Icon/icons/users.tsx +0 -23
- package/src/components/Icon/icons/wine.tsx +0 -23
- package/src/components/Icon/icons/x.tsx +0 -21
- package/src/components/IconPicker/IconPicker.module.css +0 -63
- package/src/components/IconPicker/IconPicker.stories.tsx +0 -84
- package/src/components/IconPicker/IconPicker.tsx +0 -90
- package/src/components/Input/Input.module.css +0 -52
- package/src/components/Input/Input.stories.tsx +0 -86
- package/src/components/Input/Input.tsx +0 -20
- package/src/components/Input/__tests__/Input.test.tsx +0 -22
- package/src/components/Item/Item.module.css +0 -70
- package/src/components/Item/Item.stories.tsx +0 -62
- package/src/components/Item/Item.tsx +0 -54
- package/src/components/Item/__tests__/Item.test.tsx +0 -39
- package/src/components/Kbd/Kbd.module.css +0 -14
- package/src/components/Kbd/Kbd.stories.tsx +0 -32
- package/src/components/Kbd/Kbd.tsx +0 -12
- package/src/components/Kbd/__tests__/Kbd.test.tsx +0 -14
- package/src/components/Label/Label.module.css +0 -11
- package/src/components/Label/Label.stories.tsx +0 -40
- package/src/components/Label/Label.tsx +0 -24
- package/src/components/Label/__tests__/Label.test.tsx +0 -32
- package/src/components/LegalLinks/LegalLinks.module.css +0 -24
- package/src/components/LegalLinks/LegalLinks.stories.tsx +0 -22
- package/src/components/LegalLinks/LegalLinks.tsx +0 -40
- package/src/components/Markdown/Markdown.module.css +0 -73
- package/src/components/Markdown/Markdown.stories.tsx +0 -40
- package/src/components/Markdown/Markdown.tsx +0 -305
- package/src/components/Markdown/__tests__/Markdown.test.tsx +0 -144
- package/src/components/Marker/Marker.module.css +0 -33
- package/src/components/Marker/Marker.stories.tsx +0 -39
- package/src/components/Marker/Marker.tsx +0 -34
- package/src/components/Marker/__tests__/Marker.test.tsx +0 -23
- package/src/components/MemberMultiSelect/MemberMultiSelect.module.css +0 -27
- package/src/components/MemberMultiSelect/MemberMultiSelect.stories.tsx +0 -74
- package/src/components/MemberMultiSelect/MemberMultiSelect.tsx +0 -67
- package/src/components/Menu/Menu.module.css +0 -90
- package/src/components/Menu/Menu.tsx +0 -209
- package/src/components/Menu/__tests__/Menu.test.tsx +0 -227
- package/src/components/Menubar/Menubar.stories.tsx +0 -52
- package/src/components/Menubar/Menubar.tsx +0 -42
- package/src/components/Menubar/__tests__/Menubar.test.tsx +0 -45
- package/src/components/Message/Message.module.css +0 -99
- package/src/components/Message/Message.stories.tsx +0 -79
- package/src/components/Message/Message.tsx +0 -41
- package/src/components/Message/__tests__/Message.test.tsx +0 -46
- package/src/components/MessageScroller/MessageScroller.module.css +0 -65
- package/src/components/MessageScroller/MessageScroller.stories.tsx +0 -84
- package/src/components/MessageScroller/MessageScroller.tsx +0 -84
- package/src/components/MessageScroller/__tests__/MessageScroller.test.tsx +0 -105
- package/src/components/MobileAppsDrawer/MobileAppsDrawer.module.css +0 -82
- package/src/components/MobileAppsDrawer/MobileAppsDrawer.tsx +0 -78
- package/src/components/MobileAppsDrawer/__tests__/MobileAppsDrawer.test.tsx +0 -80
- package/src/components/MobileFooter/MobileFooter.module.css +0 -73
- package/src/components/MobileFooter/MobileFooter.stories.tsx +0 -47
- package/src/components/MobileFooter/MobileFooter.tsx +0 -122
- package/src/components/MobileFooter/__tests__/MobileFooter.test.tsx +0 -129
- package/src/components/MobileHeader/MobileHeader.module.css +0 -76
- package/src/components/MobileHeader/MobileHeader.stories.tsx +0 -57
- package/src/components/MobileHeader/MobileHeader.tsx +0 -90
- package/src/components/MobileHeader/__tests__/MobileHeader.test.tsx +0 -113
- package/src/components/NavList/NavList.module.css +0 -130
- package/src/components/NavList/NavList.tsx +0 -136
- package/src/components/NavList/__tests__/NavList.test.tsx +0 -109
- package/src/components/NavTabs/NavTabs.module.css +0 -50
- package/src/components/NavTabs/NavTabs.tsx +0 -61
- package/src/components/NavigationMenu/NavigationMenu.module.css +0 -53
- package/src/components/NavigationMenu/NavigationMenu.stories.tsx +0 -58
- package/src/components/NavigationMenu/NavigationMenu.tsx +0 -125
- package/src/components/NavigationMenu/__tests__/NavigationMenu.test.tsx +0 -93
- package/src/components/NotificationsPanel/NotificationsPanel.module.css +0 -258
- package/src/components/NotificationsPanel/NotificationsPanel.stories.tsx +0 -61
- package/src/components/NotificationsPanel/NotificationsPanel.tsx +0 -187
- package/src/components/NotificationsPanel/__tests__/NotificationsPanel.test.tsx +0 -78
- package/src/components/OfflineGate/OfflineGate.tsx +0 -44
- package/src/components/OfflineGate/__tests__/OfflineGate.test.tsx +0 -66
- package/src/components/OverlayHeader/OverlayHeader.module.css +0 -98
- package/src/components/OverlayHeader/OverlayHeader.tsx +0 -77
- package/src/components/OverlayHeader/__tests__/OverlayHeader.test.tsx +0 -69
- package/src/components/PageContainer/PageContainer.module.css +0 -82
- package/src/components/PageContainer/PageContainer.tsx +0 -64
- package/src/components/PageContainer/__tests__/PageContainer.test.tsx +0 -70
- package/src/components/PageHeader/PageHeader.module.css +0 -86
- package/src/components/PageHeader/PageHeader.tsx +0 -176
- package/src/components/PageHeader/__tests__/PageHeader.test.tsx +0 -103
- package/src/components/PageLayout/PageLayout.module.css +0 -51
- package/src/components/PageLayout/PageLayout.stories.tsx +0 -73
- package/src/components/PageLayout/PageLayout.tsx +0 -51
- package/src/components/PageLayout/__tests__/PageLayout.test.tsx +0 -34
- package/src/components/Pagination/Pagination.module.css +0 -98
- package/src/components/Pagination/Pagination.stories.tsx +0 -49
- package/src/components/Pagination/Pagination.tsx +0 -87
- package/src/components/Pagination/__tests__/Pagination.test.tsx +0 -56
- package/src/components/Popover/Popover.module.css +0 -74
- package/src/components/Popover/Popover.stories.tsx +0 -357
- package/src/components/Popover/Popover.tsx +0 -290
- package/src/components/Popover/__tests__/Popover.test.tsx +0 -263
- package/src/components/Progress/Progress.module.css +0 -20
- package/src/components/Progress/Progress.stories.tsx +0 -40
- package/src/components/Progress/Progress.tsx +0 -35
- package/src/components/Progress/__tests__/Progress.test.tsx +0 -31
- package/src/components/QuantityStepper/QuantityStepper.module.css +0 -67
- package/src/components/QuantityStepper/QuantityStepper.stories.tsx +0 -79
- package/src/components/QuantityStepper/QuantityStepper.tsx +0 -107
- package/src/components/RadioGroup/RadioGroup.module.css +0 -88
- package/src/components/RadioGroup/RadioGroup.stories.tsx +0 -69
- package/src/components/RadioGroup/RadioGroup.tsx +0 -99
- package/src/components/RadioGroup/__tests__/RadioGroup.test.tsx +0 -59
- package/src/components/Resizable/Resizable.module.css +0 -70
- package/src/components/Resizable/Resizable.stories.tsx +0 -82
- package/src/components/Resizable/Resizable.tsx +0 -313
- package/src/components/Resizable/__tests__/Resizable.test.tsx +0 -128
- package/src/components/ResponsiveSurface/ResponsiveSurface.tsx +0 -24
- package/src/components/ResponsiveSurface/__tests__/ResponsiveSurface.test.tsx +0 -73
- package/src/components/RootLayout/RootLayout.module.css +0 -12
- package/src/components/RootLayout/RootLayout.stories.tsx +0 -125
- package/src/components/RootLayout/RootLayout.tsx +0 -185
- package/src/components/RootLayout/__tests__/RootLayout.test.tsx +0 -161
- package/src/components/ScrollArea/ScrollArea.module.css +0 -20
- package/src/components/ScrollArea/ScrollArea.stories.tsx +0 -57
- package/src/components/ScrollArea/ScrollArea.tsx +0 -27
- package/src/components/ScrollArea/__tests__/ScrollArea.test.tsx +0 -39
- package/src/components/SegmentedControl/SegmentedControl.module.css +0 -55
- package/src/components/SegmentedControl/SegmentedControl.stories.tsx +0 -118
- package/src/components/SegmentedControl/SegmentedControl.tsx +0 -56
- package/src/components/SegmentedControl/__tests__/SegmentedControl.test.tsx +0 -63
- package/src/components/Select/Select.module.css +0 -82
- package/src/components/Select/Select.stories.tsx +0 -115
- package/src/components/Select/Select.tsx +0 -48
- package/src/components/Select/__tests__/Select.test.tsx +0 -59
- package/src/components/Sheet/Sheet.module.css +0 -58
- package/src/components/Sheet/Sheet.tsx +0 -109
- package/src/components/Sheet/__tests__/Sheet.test.tsx +0 -99
- package/src/components/Slider/Slider.module.css +0 -95
- package/src/components/Slider/Slider.stories.tsx +0 -64
- package/src/components/Slider/Slider.tsx +0 -77
- package/src/components/Slider/__tests__/Slider.test.tsx +0 -45
- package/src/components/Spinner/Spinner.module.css +0 -39
- package/src/components/Spinner/Spinner.tsx +0 -23
- package/src/components/SplitMethodSelector/SplitMethodSelector.stories.tsx +0 -33
- package/src/components/SplitMethodSelector/SplitMethodSelector.tsx +0 -43
- package/src/components/SplitPane/SplitPane.module.css +0 -85
- package/src/components/SplitPane/SplitPane.stories.tsx +0 -160
- package/src/components/SplitPane/SplitPane.tsx +0 -149
- package/src/components/SplitPane/__tests__/SplitPane.test.tsx +0 -51
- package/src/components/StatusBadge/StatusBadge.module.css +0 -59
- package/src/components/StatusBadge/StatusBadge.stories.tsx +0 -74
- package/src/components/StatusBadge/StatusBadge.tsx +0 -65
- package/src/components/StepStrip/StepStrip.module.css +0 -53
- package/src/components/StepStrip/StepStrip.tsx +0 -74
- package/src/components/SuggestionInput/SuggestionInput.module.css +0 -103
- package/src/components/SuggestionInput/SuggestionInput.stories.tsx +0 -144
- package/src/components/SuggestionInput/SuggestionInput.tsx +0 -207
- package/src/components/SwipableMobileCarousel/SwipableMobileCarousel.module.css +0 -64
- package/src/components/SwipableMobileCarousel/SwipableMobileCarousel.tsx +0 -243
- package/src/components/SwipableMobileCarousel/SwipableMobileCarouselSlide.tsx +0 -35
- package/src/components/SwipableMobileCarousel/SwipableMobileCarouselSlideBody.tsx +0 -42
- package/src/components/SwipableMobileCarousel/SwipableMobileCarouselSlideFooter.tsx +0 -18
- package/src/components/SwipableMobileCarousel/SwipableMobileCarouselSlideHeader.tsx +0 -21
- package/src/components/SwipableMobileCarousel/SwipableMobileCarouselSlideParts.module.css +0 -29
- package/src/components/SwipableMobileCarousel/__tests__/SwipableMobileCarousel.test.tsx +0 -214
- package/src/components/SwipableMobileCarousel/__tests__/SwipableMobileCarouselDevGuard.test.tsx +0 -61
- package/src/components/SwipableMobileCarousel/context.ts +0 -13
- package/src/components/SwipableMobileCarouselDots/SwipableMobileCarouselDots.module.css +0 -64
- package/src/components/SwipableMobileCarouselDots/SwipableMobileCarouselDots.tsx +0 -73
- package/src/components/SwipableMobileCarouselDots/__tests__/SwipableMobileCarouselDots.test.tsx +0 -63
- package/src/components/SwipeStack/SwipeStack.module.css +0 -101
- package/src/components/SwipeStack/SwipeStack.tsx +0 -199
- package/src/components/SwipeStack/SwipeStackCard.tsx +0 -22
- package/src/components/SwipeStack/__tests__/SwipeStack.test.tsx +0 -169
- package/src/components/SystemBanner/SystemBanner.module.css +0 -79
- package/src/components/SystemBanner/SystemBanner.stories.tsx +0 -86
- package/src/components/SystemBanner/SystemBanner.tsx +0 -50
- package/src/components/SystemBanner/__tests__/SystemBanner.test.tsx +0 -50
- package/src/components/Table/Table.module.css +0 -45
- package/src/components/Table/Table.stories.tsx +0 -125
- package/src/components/Table/Table.tsx +0 -51
- package/src/components/Table/__tests__/Table.test.tsx +0 -50
- package/src/components/Tabs/Tabs.module.css +0 -56
- package/src/components/Tabs/Tabs.stories.tsx +0 -100
- package/src/components/Tabs/Tabs.tsx +0 -46
- package/src/components/Tabs/__tests__/Tabs.test.tsx +0 -45
- package/src/components/TagInput/TagInput.module.css +0 -141
- package/src/components/TagInput/TagInput.stories.tsx +0 -109
- package/src/components/TagInput/TagInput.tsx +0 -174
- package/src/components/TagInput/__tests__/TagInput.test.tsx +0 -69
- package/src/components/Textarea/Textarea.module.css +0 -47
- package/src/components/Textarea/Textarea.tsx +0 -38
- package/src/components/Textarea/__tests__/Textarea.test.tsx +0 -51
- package/src/components/ThreeColumnLayout/ThreeColumnLayout.module.css +0 -35
- package/src/components/ThreeColumnLayout/ThreeColumnLayout.stories.tsx +0 -152
- package/src/components/ThreeColumnLayout/ThreeColumnLayout.tsx +0 -87
- package/src/components/ThreeColumnLayout/__tests__/ThreeColumnLayout.test.tsx +0 -78
- package/src/components/Toast/Toast.module.css +0 -191
- package/src/components/Toast/Toast.stories.tsx +0 -191
- package/src/components/Toast/Toast.tsx +0 -139
- package/src/components/Toggle/Toggle.module.css +0 -57
- package/src/components/Toggle/Toggle.stories.tsx +0 -95
- package/src/components/Toggle/Toggle.tsx +0 -39
- package/src/components/Toggle/__tests__/Toggle.test.tsx +0 -47
- package/src/components/Tooltip/Tooltip.module.css +0 -56
- package/src/components/Tooltip/Tooltip.tsx +0 -30
- package/src/components/Typography/Typography.module.css +0 -47
- package/src/components/Typography/Typography.stories.tsx +0 -62
- package/src/components/Typography/Typography.tsx +0 -30
- package/src/components/Typography/__tests__/Typography.test.tsx +0 -34
- package/src/components/UserMenu/UserMenu.module.css +0 -90
- package/src/components/UserMenu/UserMenu.stories.tsx +0 -49
- package/src/components/UserMenu/UserMenu.tsx +0 -132
- package/src/components/UserMenu/__tests__/UserMenu.test.tsx +0 -77
- package/src/css-modules.d.ts +0 -4
- package/src/hooks/__tests__/useCarouselRouteSync.test.tsx +0 -126
- package/src/hooks/__tests__/useDoubleTap.test.tsx +0 -117
- package/src/hooks/__tests__/useIsMobile.test.tsx +0 -80
- package/src/hooks/__tests__/useIsOffline.test.tsx +0 -53
- package/src/hooks/__tests__/useLongPress.test.tsx +0 -158
- package/src/hooks/__tests__/useOfflineTileState.test.tsx +0 -69
- package/src/hooks/__tests__/usePublishShellChromeHeight.test.tsx +0 -118
- package/src/hooks/__tests__/useReorderSensors.test.ts +0 -26
- package/src/hooks/__tests__/useResponsiveLayout.test.tsx +0 -87
- package/src/hooks/__tests__/useSnapCarousel.test.tsx +0 -175
- package/src/hooks/__tests__/useSwipeReveal.test.tsx +0 -110
- package/src/hooks/__tests__/useSwipeStack.test.tsx +0 -155
- package/src/hooks/index.ts +0 -33
- package/src/hooks/useCarouselRouteSync.ts +0 -92
- package/src/hooks/useCommitOnEnterOrBlur.ts +0 -39
- package/src/hooks/useDoubleTap.ts +0 -91
- package/src/hooks/useIsMobile.ts +0 -33
- package/src/hooks/useIsOffline.ts +0 -41
- package/src/hooks/useLongPress.ts +0 -185
- package/src/hooks/useOfflineTileState.ts +0 -45
- package/src/hooks/usePublishShellChromeHeight.ts +0 -96
- package/src/hooks/useReorderSensors.ts +0 -88
- package/src/hooks/useResponsiveLayout.ts +0 -36
- package/src/hooks/useSnapCarousel.ts +0 -284
- package/src/hooks/useSwipeReveal.ts +0 -107
- package/src/hooks/useSwipeStack.ts +0 -235
- package/src/index.ts +0 -311
- package/src/motion.ts +0 -78
- package/src/overlay-shell.ts +0 -159
- package/src/scroll-lock.ts +0 -22
- package/src/stories/Avatar.stories.tsx +0 -44
- package/src/stories/Card.stories.tsx +0 -35
- package/src/stories/Checkbox.stories.tsx +0 -45
- package/src/stories/DesignSystemOverview.stories.tsx +0 -3793
- package/src/stories/DeviceOnlyGate.stories.tsx +0 -35
- package/src/stories/DeviceStorageKeyGate.stories.tsx +0 -57
- package/src/stories/DragHandleRow.stories.tsx +0 -41
- package/src/stories/EmptyState.stories.tsx +0 -33
- package/src/stories/FileDropzone.stories.tsx +0 -69
- package/src/stories/FormField.stories.tsx +0 -47
- package/src/stories/GripIcon.stories.tsx +0 -29
- package/src/stories/InteractionHooks.stories.tsx +0 -925
- package/src/stories/LayoutSystem.stories.tsx +0 -639
- package/src/stories/MenuEntries.stories.tsx +0 -86
- package/src/stories/MobilePatterns.stories.tsx +0 -1536
- package/src/stories/NavList.stories.tsx +0 -147
- package/src/stories/NavTabs.stories.tsx +0 -53
- package/src/stories/OfflineGate.stories.tsx +0 -42
- package/src/stories/PageContainer.stories.tsx +0 -82
- package/src/stories/PageHeader.stories.tsx +0 -95
- package/src/stories/ResponsiveSurface.stories.tsx +0 -47
- package/src/stories/Spinner.stories.tsx +0 -25
- package/src/stories/StepStrip.stories.tsx +0 -76
- package/src/stories/SwipableMobileCarousel.stories.tsx +0 -362
- package/src/stories/SwipeStack.stories.tsx +0 -200
- package/src/stories/Textarea.stories.tsx +0 -63
- package/src/stories/TokenGallery.stories.tsx +0 -652
- package/src/stories/Tooltip.stories.tsx +0 -59
- package/src/tokens/primitives.css +0 -168
- package/src/tokens/semantic.css +0 -162
- package/src/tokens/theme-presets.css +0 -33
- package/src/tokens/theme-presets.ts +0 -72
- package/src/tokens.css +0 -5
|
@@ -1,318 +0,0 @@
|
|
|
1
|
-
// @vitest-environment jsdom
|
|
2
|
-
import { afterEach, beforeEach, describe, expect, it, vi } from 'vitest';
|
|
3
|
-
import { useState } from 'react';
|
|
4
|
-
import { act, cleanup, fireEvent, render, screen } from '@testing-library/react';
|
|
5
|
-
import { ConfirmDialog } from '../../ConfirmDialog/ConfirmDialog';
|
|
6
|
-
import { Dialog, useOverlaySecondRow } from '../Dialog';
|
|
7
|
-
|
|
8
|
-
// Dialog's exit animation reads prefers-reduced-motion via matchMedia, which
|
|
9
|
-
// jsdom does not implement. `matches: false` (motion enabled) exercises the
|
|
10
|
-
// normal animated path; the actual reduced-motion behaviour is covered by
|
|
11
|
-
// motion.ts's own tests.
|
|
12
|
-
function installMatchMedia() {
|
|
13
|
-
vi.stubGlobal(
|
|
14
|
-
'matchMedia',
|
|
15
|
-
vi.fn().mockImplementation((query: string) => ({
|
|
16
|
-
matches: false,
|
|
17
|
-
media: query,
|
|
18
|
-
addEventListener: vi.fn(),
|
|
19
|
-
removeEventListener: vi.fn(),
|
|
20
|
-
addListener: vi.fn(),
|
|
21
|
-
removeListener: vi.fn(),
|
|
22
|
-
dispatchEvent: vi.fn(),
|
|
23
|
-
})),
|
|
24
|
-
);
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
describe('Dialog', () => {
|
|
28
|
-
beforeEach(installMatchMedia);
|
|
29
|
-
afterEach(() => {
|
|
30
|
-
vi.unstubAllGlobals();
|
|
31
|
-
cleanup();
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
it('renders nothing when closed', () => {
|
|
35
|
-
render(
|
|
36
|
-
<Dialog open={false} onClose={() => {}}>
|
|
37
|
-
Body
|
|
38
|
-
</Dialog>,
|
|
39
|
-
);
|
|
40
|
-
expect(screen.queryByRole('dialog')).toBeNull();
|
|
41
|
-
});
|
|
42
|
-
|
|
43
|
-
it('renders the panel with its accessible name when open', () => {
|
|
44
|
-
render(
|
|
45
|
-
<Dialog open onClose={() => {}} aria-label="Settings">
|
|
46
|
-
Body
|
|
47
|
-
</Dialog>,
|
|
48
|
-
);
|
|
49
|
-
const dialog = screen.getByRole('dialog', { name: 'Settings' });
|
|
50
|
-
expect(dialog.getAttribute('aria-modal')).toBe('true');
|
|
51
|
-
});
|
|
52
|
-
|
|
53
|
-
it('calls onClose exactly once on Escape with focus inside the panel', () => {
|
|
54
|
-
const onClose = vi.fn();
|
|
55
|
-
render(
|
|
56
|
-
<Dialog open onClose={onClose} aria-label="Panel">
|
|
57
|
-
<button>Focus me</button>
|
|
58
|
-
</Dialog>,
|
|
59
|
-
);
|
|
60
|
-
// Dispatched from the actually-focused element (matching real usage,
|
|
61
|
-
// where useOverlayFocusCapture moves focus into the panel on open) so the
|
|
62
|
-
// keydown bubbles through the scrim on its way to document — the exact
|
|
63
|
-
// path that used to trigger both the scrim's own (now-removed) Escape
|
|
64
|
-
// handler and useOverlayKeyboardTrap's document-level listener, double-
|
|
65
|
-
// firing onClose. Dispatching straight on `document` (the previous form
|
|
66
|
-
// of this test) skips that bubble path and would pass even if the bug
|
|
67
|
-
// were reintroduced.
|
|
68
|
-
const button = screen.getByRole('button', { name: 'Focus me' });
|
|
69
|
-
button.focus();
|
|
70
|
-
fireEvent.keyDown(button, { key: 'Escape' });
|
|
71
|
-
expect(onClose).toHaveBeenCalledOnce();
|
|
72
|
-
});
|
|
73
|
-
|
|
74
|
-
it('calls onClose on scrim click but not on panel click', () => {
|
|
75
|
-
const onClose = vi.fn();
|
|
76
|
-
render(
|
|
77
|
-
<Dialog open onClose={onClose} aria-label="Panel">
|
|
78
|
-
Body
|
|
79
|
-
</Dialog>,
|
|
80
|
-
);
|
|
81
|
-
fireEvent.click(screen.getByRole('dialog')); // panel — should not close
|
|
82
|
-
expect(onClose).not.toHaveBeenCalled();
|
|
83
|
-
const closeButtons = screen.getAllByRole('button', { name: 'Close' });
|
|
84
|
-
expect(closeButtons.length).toBeGreaterThan(0);
|
|
85
|
-
fireEvent.click(closeButtons[0] as HTMLElement);
|
|
86
|
-
expect(onClose).toHaveBeenCalledOnce();
|
|
87
|
-
});
|
|
88
|
-
|
|
89
|
-
it('applies the size class', () => {
|
|
90
|
-
render(
|
|
91
|
-
<Dialog open onClose={() => {}} size="lg" aria-label="Big">
|
|
92
|
-
Body
|
|
93
|
-
</Dialog>,
|
|
94
|
-
);
|
|
95
|
-
expect(screen.getByRole('dialog').className).toContain('lg');
|
|
96
|
-
});
|
|
97
|
-
|
|
98
|
-
it('supports the sm size', () => {
|
|
99
|
-
render(
|
|
100
|
-
<Dialog open onClose={() => {}} size="sm" aria-label="Small">
|
|
101
|
-
Body
|
|
102
|
-
</Dialog>,
|
|
103
|
-
);
|
|
104
|
-
expect(screen.getByRole('dialog').className).toContain('sm');
|
|
105
|
-
});
|
|
106
|
-
|
|
107
|
-
it('supports the auto size', () => {
|
|
108
|
-
render(
|
|
109
|
-
<Dialog open onClose={() => {}} size="auto" aria-label="Auto-sized">
|
|
110
|
-
Body
|
|
111
|
-
</Dialog>,
|
|
112
|
-
);
|
|
113
|
-
expect(screen.getByRole('dialog').className).toContain('auto');
|
|
114
|
-
});
|
|
115
|
-
|
|
116
|
-
it('supports the fixed size (epic task 14.5)', () => {
|
|
117
|
-
render(
|
|
118
|
-
<Dialog open onClose={() => {}} size="fixed" aria-label="Fixed-size">
|
|
119
|
-
Body
|
|
120
|
-
</Dialog>,
|
|
121
|
-
);
|
|
122
|
-
expect(screen.getByRole('dialog').className).toContain('fixed');
|
|
123
|
-
});
|
|
124
|
-
|
|
125
|
-
it('renders a descendant-supplied secondRow via useOverlaySecondRow', () => {
|
|
126
|
-
function TabStrip() {
|
|
127
|
-
useOverlaySecondRow(<nav>Tab strip</nav>);
|
|
128
|
-
return null;
|
|
129
|
-
}
|
|
130
|
-
render(
|
|
131
|
-
<Dialog open onClose={() => {}} title="Account" aria-label="Account">
|
|
132
|
-
<TabStrip />
|
|
133
|
-
</Dialog>,
|
|
134
|
-
);
|
|
135
|
-
expect(screen.getByText('Tab strip')).toBeTruthy();
|
|
136
|
-
});
|
|
137
|
-
|
|
138
|
-
it('removes the secondRow when the supplying descendant unmounts', () => {
|
|
139
|
-
function TabStrip() {
|
|
140
|
-
useOverlaySecondRow(<nav>Tab strip</nav>);
|
|
141
|
-
return null;
|
|
142
|
-
}
|
|
143
|
-
function Harness({ showTabs }: { showTabs: boolean }) {
|
|
144
|
-
return (
|
|
145
|
-
<Dialog open onClose={() => {}} title="Account" aria-label="Account">
|
|
146
|
-
{showTabs && <TabStrip />}
|
|
147
|
-
</Dialog>
|
|
148
|
-
);
|
|
149
|
-
}
|
|
150
|
-
const { rerender } = render(<Harness showTabs />);
|
|
151
|
-
expect(screen.getByText('Tab strip')).toBeTruthy();
|
|
152
|
-
rerender(<Harness showTabs={false} />);
|
|
153
|
-
expect(screen.queryByText('Tab strip')).toBeNull();
|
|
154
|
-
});
|
|
155
|
-
|
|
156
|
-
it('is a no-op when called outside a Dialog', () => {
|
|
157
|
-
function Standalone() {
|
|
158
|
-
useOverlaySecondRow(<nav>Tab strip</nav>);
|
|
159
|
-
return <span>Standalone content</span>;
|
|
160
|
-
}
|
|
161
|
-
render(<Standalone />);
|
|
162
|
-
expect(screen.getByText('Standalone content')).toBeTruthy();
|
|
163
|
-
expect(screen.queryByText('Tab strip')).toBeNull();
|
|
164
|
-
});
|
|
165
|
-
|
|
166
|
-
describe('Body only (default — no header/footer props)', () => {
|
|
167
|
-
it('renders exactly one close button and no footer', () => {
|
|
168
|
-
render(
|
|
169
|
-
<Dialog open onClose={() => {}} title="Settings" aria-label="Settings">
|
|
170
|
-
Body
|
|
171
|
-
</Dialog>,
|
|
172
|
-
);
|
|
173
|
-
// Both the mobile-only OverlayHeader's close button and the
|
|
174
|
-
// desktop-only floating one are always in the DOM (CSS toggles which
|
|
175
|
-
// is visible per breakpoint, not React) — unchanged from before this
|
|
176
|
-
// task, since this is the `header`-omitted branch.
|
|
177
|
-
expect(screen.getAllByRole('button', { name: 'Close' })).toHaveLength(2);
|
|
178
|
-
expect(screen.getByText('Settings')).toBeTruthy();
|
|
179
|
-
});
|
|
180
|
-
});
|
|
181
|
-
|
|
182
|
-
describe('Header + Body (header prop)', () => {
|
|
183
|
-
it('renders header content via a single OverlayHeader, on both breakpoints, instead of the mobile-only title bar', () => {
|
|
184
|
-
render(
|
|
185
|
-
<Dialog open onClose={() => {}} header={<span>Card detail</span>} aria-label="Card detail">
|
|
186
|
-
Body
|
|
187
|
-
</Dialog>,
|
|
188
|
-
);
|
|
189
|
-
expect(screen.getByText('Card detail')).toBeTruthy();
|
|
190
|
-
// Only one close button now — the header branch skips the separate
|
|
191
|
-
// desktop .close button entirely (see Dialog.tsx's own comment).
|
|
192
|
-
expect(screen.getAllByRole('button', { name: 'Close' })).toHaveLength(1);
|
|
193
|
-
});
|
|
194
|
-
|
|
195
|
-
it('supersedes title for visible content but keeps title as the aria-label fallback', () => {
|
|
196
|
-
render(
|
|
197
|
-
<Dialog open onClose={() => {}} title="Fallback name" header={<span>Visible header</span>}>
|
|
198
|
-
Body
|
|
199
|
-
</Dialog>,
|
|
200
|
-
);
|
|
201
|
-
expect(screen.getByText('Visible header')).toBeTruthy();
|
|
202
|
-
expect(screen.queryByText('Fallback name')).toBeNull();
|
|
203
|
-
expect(screen.getByRole('dialog', { name: 'Fallback name' })).toBeTruthy();
|
|
204
|
-
});
|
|
205
|
-
});
|
|
206
|
-
|
|
207
|
-
describe('Header + Body + Footer (header and footer props)', () => {
|
|
208
|
-
it('renders footer content as a non-scrolling sibling of the body', () => {
|
|
209
|
-
render(
|
|
210
|
-
<Dialog
|
|
211
|
-
open
|
|
212
|
-
onClose={() => {}}
|
|
213
|
-
header={<span>Card detail</span>}
|
|
214
|
-
footer={<button type="button">Save</button>}
|
|
215
|
-
aria-label="Card detail"
|
|
216
|
-
>
|
|
217
|
-
<p>Body content</p>
|
|
218
|
-
</Dialog>,
|
|
219
|
-
);
|
|
220
|
-
const footerButton = screen.getByRole('button', { name: 'Save' });
|
|
221
|
-
const bodyText = screen.getByText('Body content');
|
|
222
|
-
expect(footerButton).toBeTruthy();
|
|
223
|
-
// Footer is a sibling of .content (the scroll region), not nested
|
|
224
|
-
// inside it — it must never scroll away with the body.
|
|
225
|
-
expect(bodyText.closest('[class*="content"]')?.contains(footerButton)).toBe(false);
|
|
226
|
-
});
|
|
227
|
-
|
|
228
|
-
it('omits the footer row entirely when footer is not provided', () => {
|
|
229
|
-
render(
|
|
230
|
-
<Dialog open onClose={() => {}} header={<span>Card detail</span>} aria-label="Card detail">
|
|
231
|
-
Body
|
|
232
|
-
</Dialog>,
|
|
233
|
-
);
|
|
234
|
-
expect(screen.queryByRole('button', { name: 'Save' })).toBeNull();
|
|
235
|
-
});
|
|
236
|
-
});
|
|
237
|
-
});
|
|
238
|
-
|
|
239
|
-
describe('Dialog Escape precedence with a nested ConfirmDialog', () => {
|
|
240
|
-
beforeEach(() => {
|
|
241
|
-
installMatchMedia();
|
|
242
|
-
// jsdom does not implement HTMLDialogElement — see ConfirmDialog.test.tsx
|
|
243
|
-
// for the full rationale on the guard + deferred dispatch (both matter
|
|
244
|
-
// here too: without the guard, this file's own reuse of the mock across
|
|
245
|
-
// renders would double-dispatch; without deferring, ConfirmDialog's
|
|
246
|
-
// unregister-on-close wouldn't have run yet by the time this test reads
|
|
247
|
-
// the outer Dialog's response to a second Escape).
|
|
248
|
-
HTMLDialogElement.prototype.showModal = function (this: HTMLDialogElement) {
|
|
249
|
-
this.setAttribute('open', '');
|
|
250
|
-
};
|
|
251
|
-
HTMLDialogElement.prototype.close = function (this: HTMLDialogElement) {
|
|
252
|
-
if (!this.hasAttribute('open')) return;
|
|
253
|
-
this.removeAttribute('open');
|
|
254
|
-
queueMicrotask(() => this.dispatchEvent(new Event('close')));
|
|
255
|
-
};
|
|
256
|
-
});
|
|
257
|
-
afterEach(() => {
|
|
258
|
-
vi.unstubAllGlobals();
|
|
259
|
-
cleanup();
|
|
260
|
-
});
|
|
261
|
-
|
|
262
|
-
async function flush() {
|
|
263
|
-
await act(async () => {
|
|
264
|
-
await new Promise((resolve) => setTimeout(resolve, 0));
|
|
265
|
-
});
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
it('defers Escape to a nested open ConfirmDialog instead of closing the outer Dialog', async () => {
|
|
269
|
-
const outerOnClose = vi.fn();
|
|
270
|
-
|
|
271
|
-
function NestedHarness() {
|
|
272
|
-
// Starts closed and opens via a later click — matching the real
|
|
273
|
-
// sequence (CardDetailOverlay: the outer Dialog is already mounted and
|
|
274
|
-
// registered before the user ever triggers the nested confirm).
|
|
275
|
-
// Mounting both already-open in the same initial render would instead
|
|
276
|
-
// have React fire the child's (ConfirmDialog's) registration effect
|
|
277
|
-
// before the parent's (Dialog's) in that one shared commit — the one
|
|
278
|
-
// case this stack-order approach doesn't handle, and not the shape of
|
|
279
|
-
// the bug this task fixes.
|
|
280
|
-
const [confirmOpen, setConfirmOpen] = useState(false);
|
|
281
|
-
return (
|
|
282
|
-
<Dialog open onClose={outerOnClose} aria-label="Card detail">
|
|
283
|
-
<button onClick={() => setConfirmOpen(true)}>Delete card…</button>
|
|
284
|
-
<ConfirmDialog
|
|
285
|
-
open={confirmOpen}
|
|
286
|
-
onClose={() => setConfirmOpen(false)}
|
|
287
|
-
onConfirm={() => {}}
|
|
288
|
-
title="Delete card?"
|
|
289
|
-
message="This can't be undone."
|
|
290
|
-
/>
|
|
291
|
-
</Dialog>
|
|
292
|
-
);
|
|
293
|
-
}
|
|
294
|
-
|
|
295
|
-
render(<NestedHarness />);
|
|
296
|
-
fireEvent.click(screen.getByRole('button', { name: 'Delete card…' }));
|
|
297
|
-
await flush();
|
|
298
|
-
expect(screen.getByRole('button', { name: 'Cancel' })).toBeTruthy();
|
|
299
|
-
|
|
300
|
-
// The nested ConfirmDialog is topmost — the outer Dialog's document-level
|
|
301
|
-
// Escape listener must not act while it's open.
|
|
302
|
-
fireEvent.keyDown(document, { key: 'Escape' });
|
|
303
|
-
await flush();
|
|
304
|
-
expect(outerOnClose).not.toHaveBeenCalled();
|
|
305
|
-
expect(screen.getByRole('button', { name: 'Cancel' })).toBeTruthy();
|
|
306
|
-
|
|
307
|
-
// Dismiss the nested confirm (unregisters it from the open-overlay
|
|
308
|
-
// stack) — the outer Dialog is now topmost again.
|
|
309
|
-
fireEvent.click(screen.getByRole('button', { name: 'Cancel' }));
|
|
310
|
-
await flush();
|
|
311
|
-
expect(screen.queryByRole('button', { name: 'Cancel' })).toBeNull();
|
|
312
|
-
|
|
313
|
-
// A second Escape now reaches the outer Dialog.
|
|
314
|
-
fireEvent.keyDown(document, { key: 'Escape' });
|
|
315
|
-
await flush();
|
|
316
|
-
expect(outerOnClose).toHaveBeenCalledOnce();
|
|
317
|
-
});
|
|
318
|
-
});
|
|
@@ -1,57 +0,0 @@
|
|
|
1
|
-
.row {
|
|
2
|
-
display: flex;
|
|
3
|
-
align-items: flex-start;
|
|
4
|
-
gap: var(--sv-space-1);
|
|
5
|
-
position: relative;
|
|
6
|
-
}
|
|
7
|
-
|
|
8
|
-
/* Hover-reveal only where hover genuinely exists — on touch the handle would
|
|
9
|
-
otherwise never become visible (tap-generated hover doesn't count as a
|
|
10
|
-
sustained hover state, and :not(:hover) is always true with no hover
|
|
11
|
-
capability at all), so it stays visible by default there. */
|
|
12
|
-
@media (hover: hover) {
|
|
13
|
-
.row:not(:hover) .handle,
|
|
14
|
-
.row:not(:focus-within) .handle {
|
|
15
|
-
opacity: 0;
|
|
16
|
-
}
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
.handle {
|
|
20
|
-
flex-shrink: 0;
|
|
21
|
-
display: flex;
|
|
22
|
-
align-items: center;
|
|
23
|
-
justify-content: center;
|
|
24
|
-
width: 24px;
|
|
25
|
-
height: 24px;
|
|
26
|
-
margin-top: 2px;
|
|
27
|
-
border: none;
|
|
28
|
-
background: none;
|
|
29
|
-
padding: 0;
|
|
30
|
-
border-radius: var(--sv-radius-sm);
|
|
31
|
-
color: var(--sv-color-text-muted);
|
|
32
|
-
cursor: grab;
|
|
33
|
-
opacity: 1;
|
|
34
|
-
transition: opacity 0.1s ease;
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
.handle:focus-visible {
|
|
38
|
-
outline: 2px solid var(--sv-color-focus-ring);
|
|
39
|
-
outline-offset: 2px;
|
|
40
|
-
}
|
|
41
|
-
|
|
42
|
-
.handle:active {
|
|
43
|
-
cursor: grabbing;
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
.icon {
|
|
47
|
-
pointer-events: none;
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
.content {
|
|
51
|
-
flex: 1;
|
|
52
|
-
min-width: 0;
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
.dragging {
|
|
56
|
-
opacity: 0.5;
|
|
57
|
-
}
|
|
@@ -1,42 +0,0 @@
|
|
|
1
|
-
import type { HTMLAttributes, ReactNode } from 'react';
|
|
2
|
-
import { GripIcon } from '../GripIcon/GripIcon';
|
|
3
|
-
import styles from './DragHandleRow.module.css';
|
|
4
|
-
|
|
5
|
-
export interface DragHandleRowProps extends HTMLAttributes<HTMLDivElement> {
|
|
6
|
-
children: ReactNode;
|
|
7
|
-
/** Pass drag-listener and drag-control props from dnd-kit here. */
|
|
8
|
-
handleProps?: HTMLAttributes<HTMLButtonElement>;
|
|
9
|
-
isDragging?: boolean;
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
/**
|
|
13
|
-
* A row wrapper that surfaces a drag handle on the left.
|
|
14
|
-
* Consumers attach dnd-kit's useSortable listeners to `handleProps`.
|
|
15
|
-
*/
|
|
16
|
-
export function DragHandleRow({
|
|
17
|
-
children,
|
|
18
|
-
handleProps,
|
|
19
|
-
isDragging,
|
|
20
|
-
className,
|
|
21
|
-
...rest
|
|
22
|
-
}: DragHandleRowProps) {
|
|
23
|
-
return (
|
|
24
|
-
<div
|
|
25
|
-
{...rest}
|
|
26
|
-
className={[styles.row, isDragging ? styles.dragging : '', className]
|
|
27
|
-
.filter(Boolean)
|
|
28
|
-
.join(' ')}
|
|
29
|
-
>
|
|
30
|
-
<button
|
|
31
|
-
type="button"
|
|
32
|
-
aria-label="Drag to reorder"
|
|
33
|
-
className={styles.handle}
|
|
34
|
-
tabIndex={-1}
|
|
35
|
-
{...handleProps}
|
|
36
|
-
>
|
|
37
|
-
<GripIcon className={styles.icon} />
|
|
38
|
-
</button>
|
|
39
|
-
<div className={styles.content}>{children}</div>
|
|
40
|
-
</div>
|
|
41
|
-
);
|
|
42
|
-
}
|
|
@@ -1,121 +0,0 @@
|
|
|
1
|
-
/* Drawer — bottom-sheet surface (RFC 0013). Shares scrim/shadow tokens with
|
|
2
|
-
* Dialog but slides up from the bottom instead of centering. The panel has no
|
|
3
|
-
* fixed height — it sizes to content, capped at 80dvh so some page context
|
|
4
|
-
* remains visible above. Safe-area-aware: bottom padding clears the home
|
|
5
|
-
* indicator in standalone/fullscreen mode. */
|
|
6
|
-
|
|
7
|
-
.scrim {
|
|
8
|
-
position: fixed;
|
|
9
|
-
inset: 0;
|
|
10
|
-
/* When --sv-shell-footer-height is set (mobile nav bar — by the platform
|
|
11
|
-
shell, or by a self-rendered MobileFooter via usePublishShellChromeHeight
|
|
12
|
-
for a shellConfig.mobileFooter: false plugin), stop the scrim above the
|
|
13
|
-
footer so the panel never hides behind it. */
|
|
14
|
-
bottom: var(--sv-shell-footer-height, 0);
|
|
15
|
-
z-index: 100;
|
|
16
|
-
display: flex;
|
|
17
|
-
align-items: flex-end;
|
|
18
|
-
background: var(--sv-color-scrim);
|
|
19
|
-
/* Entrance/exit fade — same two-phase-mount pattern as Dialog (see motion.ts
|
|
20
|
-
and Drawer.tsx). */
|
|
21
|
-
opacity: 0;
|
|
22
|
-
transition: opacity var(--sv-motion-duration-base) var(--sv-motion-ease-out);
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
.scrimOpen {
|
|
26
|
-
opacity: 1;
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
.panel {
|
|
30
|
-
width: 100%;
|
|
31
|
-
max-height: 80dvh;
|
|
32
|
-
/* The panel itself no longer scrolls — see .body below. display: flex
|
|
33
|
-
(column) lets .handle (and OverlayHeader, when title is set) stay
|
|
34
|
-
fixed while .body's own overflow-y handles content taller than the
|
|
35
|
-
80dvh cap, the same fixed-header/scrollable-body split Sheet.module.css
|
|
36
|
-
already establishes (its .panel/.content pair). Before this, the whole
|
|
37
|
-
.panel scrolled as one block, so a tall drawer (e.g. many installed
|
|
38
|
-
plugins in the Apps grid) scrolled the grab handle itself out of view
|
|
39
|
-
along with the content — reachable in the DOM, invisible on screen. */
|
|
40
|
-
display: flex;
|
|
41
|
-
flex-direction: column;
|
|
42
|
-
overflow: hidden;
|
|
43
|
-
background: var(--sv-color-surface-raised);
|
|
44
|
-
border-top: var(--sv-border-width-hairline) solid var(--sv-color-border);
|
|
45
|
-
border-radius: var(--sv-radius-3xl) var(--sv-radius-3xl) 0 0;
|
|
46
|
-
box-shadow: var(--sv-shadow-overlay);
|
|
47
|
-
outline: none;
|
|
48
|
-
/* Slide up from below the viewport. Always a bottom sheet, so unlike Dialog
|
|
49
|
-
there's no desktop-vs-mobile fork here. */
|
|
50
|
-
transform: translateY(100%);
|
|
51
|
-
transition: transform var(--sv-motion-duration-base) var(--sv-motion-ease-out);
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
/* The scroll container — everything below the fixed handle/OverlayHeader.
|
|
55
|
-
Scrollbar hidden (not overflow removed) the same way Tabs.module.css's
|
|
56
|
-
.tablist already does for this design system; scroll-driven UI here reads
|
|
57
|
-
as a native swipe list, not a document needing a visible scroll affordance. */
|
|
58
|
-
.body {
|
|
59
|
-
flex: 1 1 auto;
|
|
60
|
-
min-height: 0;
|
|
61
|
-
overflow-y: auto;
|
|
62
|
-
overscroll-behavior: contain;
|
|
63
|
-
scrollbar-width: none;
|
|
64
|
-
/* Pull content above the home indicator / bottom bar in standalone mode —
|
|
65
|
-
moved here from .panel now that this is the element whose bottom edge
|
|
66
|
-
is the actual scrollable content boundary. */
|
|
67
|
-
padding-bottom: env(safe-area-inset-bottom);
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
.body::-webkit-scrollbar {
|
|
71
|
-
display: none;
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
.panelOpen {
|
|
75
|
-
transform: translateY(0);
|
|
76
|
-
}
|
|
77
|
-
|
|
78
|
-
/* 'half' snapHeight — a fixed height instead of the default content-sized cap
|
|
79
|
-
* above. Per the design-system's "half screen or less" convention for
|
|
80
|
-
* Drawer; content taller than this belongs in Sheet instead. */
|
|
81
|
-
.panelHalf {
|
|
82
|
-
height: 50dvh;
|
|
83
|
-
max-height: 50dvh;
|
|
84
|
-
}
|
|
85
|
-
|
|
86
|
-
/* See Dialog.module.css's identical rule for why 0.01ms rather than 0. */
|
|
87
|
-
@media (prefers-reduced-motion: reduce) {
|
|
88
|
-
.scrim,
|
|
89
|
-
.panel {
|
|
90
|
-
transition-duration: 0.01ms;
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
/* Grab handle — the sole drag-initiation region for swipe-down-to-dismiss
|
|
95
|
-
* (see Drawer.tsx's doc comment for why not the whole panel). The visual bar
|
|
96
|
-
* (::before) stays the small, established 36x4px size; only the hit area
|
|
97
|
-
* grows to a comfortable touch target. */
|
|
98
|
-
.handle {
|
|
99
|
-
display: flex;
|
|
100
|
-
align-items: center;
|
|
101
|
-
justify-content: center;
|
|
102
|
-
width: 100%;
|
|
103
|
-
height: var(--sv-touch-target-min, 44px);
|
|
104
|
-
flex-shrink: 0;
|
|
105
|
-
cursor: grab;
|
|
106
|
-
/* JS-driven drag — the browser must not treat a press here as a
|
|
107
|
-
scroll/pan gesture that would fight it. */
|
|
108
|
-
touch-action: none;
|
|
109
|
-
}
|
|
110
|
-
|
|
111
|
-
.handle:active {
|
|
112
|
-
cursor: grabbing;
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
.handle::before {
|
|
116
|
-
content: '';
|
|
117
|
-
width: 36px;
|
|
118
|
-
height: 4px;
|
|
119
|
-
border-radius: var(--sv-radius-full);
|
|
120
|
-
background: var(--sv-color-border-strong);
|
|
121
|
-
}
|
|
@@ -1,132 +0,0 @@
|
|
|
1
|
-
import type { Meta, StoryObj } from '@storybook/react-vite';
|
|
2
|
-
import { expect, userEvent, within } from 'storybook/test';
|
|
3
|
-
import { useState } from 'react';
|
|
4
|
-
import { Button } from '../Button/Button';
|
|
5
|
-
import { Icon } from '../Icon/Icon';
|
|
6
|
-
import { Drawer } from './Drawer';
|
|
7
|
-
|
|
8
|
-
function DrawerDemo({ label = 'Navigation' }: { label?: string }) {
|
|
9
|
-
const [open, setOpen] = useState(false);
|
|
10
|
-
return (
|
|
11
|
-
<>
|
|
12
|
-
<Button onClick={() => setOpen(true)}>Open drawer</Button>
|
|
13
|
-
<Drawer open={open} onClose={() => setOpen(false)} aria-label={label}>
|
|
14
|
-
<ul style={{ listStyle: 'none', margin: 0, padding: '8px 0' }}>
|
|
15
|
-
{(['house', 'grid-2x2', 'settings', 'user'] as const).map((icon) => (
|
|
16
|
-
<li key={icon}>
|
|
17
|
-
<button
|
|
18
|
-
onClick={() => setOpen(false)}
|
|
19
|
-
style={{
|
|
20
|
-
display: 'flex',
|
|
21
|
-
alignItems: 'center',
|
|
22
|
-
gap: 12,
|
|
23
|
-
width: '100%',
|
|
24
|
-
padding: '12px 20px',
|
|
25
|
-
background: 'none',
|
|
26
|
-
border: 'none',
|
|
27
|
-
cursor: 'pointer',
|
|
28
|
-
fontSize: 15,
|
|
29
|
-
color: 'var(--sv-color-text-primary)',
|
|
30
|
-
fontFamily: 'system-ui',
|
|
31
|
-
}}
|
|
32
|
-
>
|
|
33
|
-
<Icon name={icon} size="md" aria-hidden />
|
|
34
|
-
{icon.replace(/-/g, ' ')}
|
|
35
|
-
</button>
|
|
36
|
-
</li>
|
|
37
|
-
))}
|
|
38
|
-
</ul>
|
|
39
|
-
</Drawer>
|
|
40
|
-
</>
|
|
41
|
-
);
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
const meta = {
|
|
45
|
-
title: 'Components/Drawer',
|
|
46
|
-
component: Drawer,
|
|
47
|
-
parameters: {
|
|
48
|
-
layout: 'centered',
|
|
49
|
-
docs: {
|
|
50
|
-
description: {
|
|
51
|
-
component:
|
|
52
|
-
'Dismissable bottom-sheet panel. Used by the mobile shell for plugin navigation. Supports Esc, scrim-click, focus trap. Respects `env(safe-area-inset-bottom)`. Use the viewport addon at 375px to see the intended mobile context.',
|
|
53
|
-
},
|
|
54
|
-
},
|
|
55
|
-
viewport: { defaultViewport: 'mobile' },
|
|
56
|
-
},
|
|
57
|
-
} satisfies Meta<typeof Drawer>;
|
|
58
|
-
|
|
59
|
-
export default meta;
|
|
60
|
-
type Story = StoryObj<typeof meta>;
|
|
61
|
-
|
|
62
|
-
// ---------------------------------------------------------------------------
|
|
63
|
-
|
|
64
|
-
export const Default: Story = {
|
|
65
|
-
args: { open: false, onClose: () => {}, children: null },
|
|
66
|
-
render: (_args) => <DrawerDemo />,
|
|
67
|
-
};
|
|
68
|
-
|
|
69
|
-
export const Closed: Story = {
|
|
70
|
-
args: { open: false, onClose: () => {}, children: null },
|
|
71
|
-
render: (_args) => (
|
|
72
|
-
<Drawer open={false} onClose={() => {}} aria-label="Closed drawer">
|
|
73
|
-
<p>Never seen</p>
|
|
74
|
-
</Drawer>
|
|
75
|
-
),
|
|
76
|
-
};
|
|
77
|
-
|
|
78
|
-
function DrawerWithTitleDemo() {
|
|
79
|
-
const [open, setOpen] = useState(false);
|
|
80
|
-
return (
|
|
81
|
-
<>
|
|
82
|
-
<Button onClick={() => setOpen(true)}>Open drawer</Button>
|
|
83
|
-
<Drawer open={open} onClose={() => setOpen(false)} title="Apps">
|
|
84
|
-
<ul style={{ listStyle: 'none', margin: 0, padding: '8px 0' }}>
|
|
85
|
-
{(['house', 'grid-2x2', 'settings', 'user'] as const).map((icon) => (
|
|
86
|
-
<li key={icon}>
|
|
87
|
-
<button
|
|
88
|
-
onClick={() => setOpen(false)}
|
|
89
|
-
style={{
|
|
90
|
-
display: 'flex',
|
|
91
|
-
alignItems: 'center',
|
|
92
|
-
gap: 12,
|
|
93
|
-
width: '100%',
|
|
94
|
-
padding: '12px 20px',
|
|
95
|
-
background: 'none',
|
|
96
|
-
border: 'none',
|
|
97
|
-
cursor: 'pointer',
|
|
98
|
-
fontSize: 15,
|
|
99
|
-
color: 'var(--sv-color-text-primary)',
|
|
100
|
-
fontFamily: 'system-ui',
|
|
101
|
-
}}
|
|
102
|
-
>
|
|
103
|
-
<Icon name={icon} size="md" aria-hidden />
|
|
104
|
-
{icon.replace(/-/g, ' ')}
|
|
105
|
-
</button>
|
|
106
|
-
</li>
|
|
107
|
-
))}
|
|
108
|
-
</ul>
|
|
109
|
-
</Drawer>
|
|
110
|
-
</>
|
|
111
|
-
);
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
/** Opt-in `title` prop renders a built-in `OverlayHeader` (title + close)
|
|
115
|
-
* below the grab handle — hidden by default (see the `Default` story), for
|
|
116
|
-
* consumers that want one instead of building their own header markup. */
|
|
117
|
-
export const WithTitle: Story = {
|
|
118
|
-
args: { open: false, onClose: () => {}, children: null },
|
|
119
|
-
render: (_args) => <DrawerWithTitleDemo />,
|
|
120
|
-
};
|
|
121
|
-
|
|
122
|
-
/** Play function opens the drawer and asserts its list items are visible. */
|
|
123
|
-
export const OpenViaInteraction: Story = {
|
|
124
|
-
args: { open: false, onClose: () => {}, children: null },
|
|
125
|
-
render: (_args) => <DrawerDemo label="Navigation menu" />,
|
|
126
|
-
play: async ({ canvasElement }) => {
|
|
127
|
-
const canvas = within(canvasElement);
|
|
128
|
-
await userEvent.click(canvas.getByRole('button', { name: /open drawer/i }));
|
|
129
|
-
const drawer = canvas.getByRole('navigation');
|
|
130
|
-
await expect(drawer).toBeVisible();
|
|
131
|
-
},
|
|
132
|
-
};
|