@astryxdesign/core 0.1.1 → 0.1.2-canary.04e71b2
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/CHANGELOG.md +105 -0
- package/README.md +131 -13
- package/dist/Avatar/Avatar.d.ts.map +1 -1
- package/dist/Avatar/Avatar.js +11 -5
- package/dist/AvatarGroup/AvatarGroupOverflow.d.ts +1 -1
- package/dist/AvatarGroup/AvatarGroupOverflow.d.ts.map +1 -1
- package/dist/AvatarGroup/AvatarGroupOverflow.js +4 -1
- package/dist/Banner/Banner.d.ts +7 -0
- package/dist/Banner/Banner.d.ts.map +1 -1
- package/dist/Banner/Banner.js +9 -2
- package/dist/Breadcrumbs/BreadcrumbItem.d.ts +1 -1
- package/dist/Breadcrumbs/BreadcrumbItem.d.ts.map +1 -1
- package/dist/Breadcrumbs/BreadcrumbItem.js +24 -5
- package/dist/Button/Button.d.ts +12 -2
- package/dist/Button/Button.d.ts.map +1 -1
- package/dist/Button/Button.js +53 -17
- package/dist/Calendar/Calendar.d.ts +5 -4
- package/dist/Calendar/Calendar.d.ts.map +1 -1
- package/dist/Calendar/Calendar.js +82 -43
- package/dist/Calendar/hooks/index.d.ts +0 -2
- package/dist/Calendar/hooks/index.d.ts.map +1 -1
- package/dist/Calendar/hooks/index.js +1 -2
- package/dist/Calendar/index.d.ts +3 -3
- package/dist/Calendar/index.d.ts.map +1 -1
- package/dist/Calendar/index.js +1 -1
- package/dist/Calendar/styles.d.ts +3 -9
- package/dist/Calendar/styles.d.ts.map +1 -1
- package/dist/Calendar/styles.js +3 -11
- package/dist/Carousel/Carousel.d.ts.map +1 -1
- package/dist/Carousel/Carousel.js +17 -3
- package/dist/Center/Center.d.ts +11 -1
- package/dist/Center/Center.d.ts.map +1 -1
- package/dist/Center/Center.js +9 -3
- package/dist/Chat/ChatMessageList.d.ts +14 -1
- package/dist/Chat/ChatMessageList.d.ts.map +1 -1
- package/dist/Chat/ChatMessageList.js +2 -0
- package/dist/Chat/useTriggerMenu.d.ts.map +1 -1
- package/dist/Chat/useTriggerMenu.js +4 -1
- package/dist/CheckboxInput/CheckboxInput.d.ts +23 -2
- package/dist/CheckboxInput/CheckboxInput.d.ts.map +1 -1
- package/dist/CheckboxInput/CheckboxInput.js +51 -9
- package/dist/CheckboxList/CheckboxList.d.ts +13 -1
- package/dist/CheckboxList/CheckboxList.d.ts.map +1 -1
- package/dist/CheckboxList/CheckboxList.js +39 -9
- package/dist/CheckboxList/CheckboxListContext.d.ts +7 -0
- package/dist/CheckboxList/CheckboxListContext.d.ts.map +1 -1
- package/dist/Citation/Citation.d.ts.map +1 -1
- package/dist/Citation/Citation.js +3 -3
- package/dist/CodeBlock/CodeBlock.d.ts.map +1 -1
- package/dist/CodeBlock/CodeBlock.js +49 -37
- package/dist/CommandPalette/CommandPalette.d.ts.map +1 -1
- package/dist/CommandPalette/CommandPalette.js +5 -5
- package/dist/ContextMenu/ContextMenu.d.ts +4 -5
- package/dist/ContextMenu/ContextMenu.d.ts.map +1 -1
- package/dist/ContextMenu/ContextMenu.js +93 -11
- package/dist/DateInput/DateInput.d.ts +23 -1
- package/dist/DateInput/DateInput.d.ts.map +1 -1
- package/dist/DateInput/DateInput.js +59 -8
- package/dist/DateRangeInput/DateRangeInput.d.ts +23 -1
- package/dist/DateRangeInput/DateRangeInput.d.ts.map +1 -1
- package/dist/DateRangeInput/DateRangeInput.js +42 -9
- package/dist/DateTimeInput/DateTimeInput.d.ts +35 -2
- package/dist/DateTimeInput/DateTimeInput.d.ts.map +1 -1
- package/dist/DateTimeInput/DateTimeInput.js +78 -15
- package/dist/Dialog/Dialog.d.ts.map +1 -1
- package/dist/Dialog/Dialog.js +12 -0
- package/dist/DropdownMenu/DropdownMenu.d.ts +1 -8
- package/dist/DropdownMenu/DropdownMenu.d.ts.map +1 -1
- package/dist/DropdownMenu/DropdownMenu.js +42 -14
- package/dist/EmptyState/EmptyState.d.ts.map +1 -1
- package/dist/EmptyState/EmptyState.js +7 -1
- package/dist/Field/Field.d.ts +19 -2
- package/dist/Field/Field.d.ts.map +1 -1
- package/dist/Field/Field.js +4 -0
- package/dist/Field/FieldLabel.d.ts +21 -2
- package/dist/Field/FieldLabel.d.ts.map +1 -1
- package/dist/Field/FieldLabel.js +41 -26
- package/dist/FileInput/FileInput.d.ts +22 -1
- package/dist/FileInput/FileInput.d.ts.map +1 -1
- package/dist/FileInput/FileInput.js +56 -10
- package/dist/Grid/Grid.d.ts +11 -1
- package/dist/Grid/Grid.d.ts.map +1 -1
- package/dist/Grid/Grid.js +8 -0
- package/dist/HoverCard/HoverCard.d.ts +2 -2
- package/dist/HoverCard/HoverCard.d.ts.map +1 -1
- package/dist/HoverCard/HoverCard.js +18 -6
- package/dist/HoverCard/useHoverCard.d.ts.map +1 -1
- package/dist/HoverCard/useHoverCard.js +7 -3
- package/dist/InputGroup/InputGroup.d.ts +2 -2
- package/dist/InputGroup/InputGroup.d.ts.map +1 -1
- package/dist/InputGroup/InputGroup.js +14 -5
- package/dist/InputGroup/InputGroupContext.d.ts +4 -0
- package/dist/InputGroup/InputGroupContext.d.ts.map +1 -1
- package/dist/InputGroup/InputGroupContext.js +2 -2
- package/dist/InputGroup/index.d.ts +1 -0
- package/dist/InputGroup/index.d.ts.map +1 -1
- package/dist/Kbd/Kbd.d.ts.map +1 -1
- package/dist/Kbd/Kbd.js +34 -2
- package/dist/Layer/anchorName.d.ts +20 -0
- package/dist/Layer/anchorName.d.ts.map +1 -0
- package/dist/Layer/anchorName.js +36 -0
- package/dist/Layer/layerAnimations.stylex.d.ts +4 -0
- package/dist/Layer/layerAnimations.stylex.d.ts.map +1 -1
- package/dist/Layer/layerAnimations.stylex.js +8 -4
- package/dist/Layer/useLayer.d.ts +29 -0
- package/dist/Layer/useLayer.d.ts.map +1 -1
- package/dist/Layer/useLayer.js +55 -11
- package/dist/Layout/Layout.d.ts +4 -11
- package/dist/Layout/Layout.d.ts.map +1 -1
- package/dist/Layout/Layout.js +10 -11
- package/dist/Layout/LayoutFooter.d.ts +2 -2
- package/dist/Layout/LayoutFooter.d.ts.map +1 -1
- package/dist/Layout/LayoutHeader.d.ts +2 -2
- package/dist/Layout/LayoutHeader.d.ts.map +1 -1
- package/dist/Layout/LayoutPanel.d.ts +2 -2
- package/dist/Layout/LayoutPanel.d.ts.map +1 -1
- package/dist/Layout/padding.stylex.d.ts +51 -0
- package/dist/Layout/padding.stylex.d.ts.map +1 -1
- package/dist/Layout/padding.stylex.js +63 -0
- package/dist/Lightbox/Lightbox.d.ts.map +1 -1
- package/dist/Lightbox/Lightbox.js +4 -2
- package/dist/Link/Link.d.ts +17 -2
- package/dist/Link/Link.d.ts.map +1 -1
- package/dist/Link/Link.js +20 -9
- package/dist/Link/LinkProvider.d.ts +1 -0
- package/dist/Link/LinkProvider.d.ts.map +1 -1
- package/dist/Link/LinkProvider.js +1 -0
- package/dist/Markdown/Markdown.d.ts.map +1 -1
- package/dist/Markdown/Markdown.js +18 -3
- package/dist/MobileNav/MobileNav.d.ts.map +1 -1
- package/dist/MobileNav/MobileNav.js +13 -0
- package/dist/MoreMenu/MoreMenu.d.ts +1 -7
- package/dist/MoreMenu/MoreMenu.d.ts.map +1 -1
- package/dist/MoreMenu/MoreMenu.js +0 -2
- package/dist/MultiSelector/MultiSelector.d.ts +25 -2
- package/dist/MultiSelector/MultiSelector.d.ts.map +1 -1
- package/dist/MultiSelector/MultiSelector.js +103 -22
- package/dist/MultiSelector/hooks.d.ts +12 -1
- package/dist/MultiSelector/hooks.d.ts.map +1 -1
- package/dist/MultiSelector/hooks.js +14 -1
- package/dist/NavMenu/NavHeadingMenu.d.ts.map +1 -1
- package/dist/NavMenu/NavHeadingMenu.js +34 -3
- package/dist/NumberInput/NumberInput.d.ts +23 -2
- package/dist/NumberInput/NumberInput.d.ts.map +1 -1
- package/dist/NumberInput/NumberInput.js +62 -12
- package/dist/Pagination/Pagination.d.ts +1 -1
- package/dist/Pagination/Pagination.d.ts.map +1 -1
- package/dist/Pagination/Pagination.js +46 -28
- package/dist/Popover/usePopover.d.ts +25 -2
- package/dist/Popover/usePopover.d.ts.map +1 -1
- package/dist/Popover/usePopover.js +18 -6
- package/dist/PowerSearch/PowerSearch.d.ts +11 -1
- package/dist/PowerSearch/PowerSearch.d.ts.map +1 -1
- package/dist/PowerSearch/PowerSearch.js +6 -1
- package/dist/ProgressBar/ProgressBar.d.ts.map +1 -1
- package/dist/ProgressBar/ProgressBar.js +3 -5
- package/dist/RadioList/RadioList.d.ts +20 -2
- package/dist/RadioList/RadioList.d.ts.map +1 -1
- package/dist/RadioList/RadioList.js +105 -9
- package/dist/RadioList/RadioListItem.d.ts.map +1 -1
- package/dist/RadioList/RadioListItem.js +13 -2
- package/dist/SegmentedControl/SegmentedControl.d.ts +13 -2
- package/dist/SegmentedControl/SegmentedControl.d.ts.map +1 -1
- package/dist/SegmentedControl/SegmentedControl.js +78 -44
- package/dist/SegmentedControl/SegmentedControlContext.d.ts +7 -0
- package/dist/SegmentedControl/SegmentedControlContext.d.ts.map +1 -1
- package/dist/SegmentedControl/SegmentedControlItem.d.ts.map +1 -1
- package/dist/SegmentedControl/SegmentedControlItem.js +13 -2
- package/dist/Selector/Selector.d.ts +22 -1
- package/dist/Selector/Selector.d.ts.map +1 -1
- package/dist/Selector/Selector.js +84 -23
- package/dist/Selector/hooks.d.ts +8 -1
- package/dist/Selector/hooks.d.ts.map +1 -1
- package/dist/Selector/hooks.js +14 -1
- package/dist/SideNav/SideNavItem.d.ts.map +1 -1
- package/dist/SideNav/SideNavItem.js +1 -1
- package/dist/Skeleton/Skeleton.d.ts.map +1 -1
- package/dist/Skeleton/Skeleton.js +8 -2
- package/dist/Slider/Slider.d.ts +21 -0
- package/dist/Slider/Slider.d.ts.map +1 -1
- package/dist/Slider/Slider.js +38 -11
- package/dist/Spinner/Spinner.d.ts.map +1 -1
- package/dist/Spinner/Spinner.js +1 -1
- package/dist/Stack/Stack.d.ts +38 -23
- package/dist/Stack/Stack.d.ts.map +1 -1
- package/dist/Stack/Stack.js +25 -1
- package/dist/Stack/StackItem.d.ts +12 -23
- package/dist/Stack/StackItem.d.ts.map +1 -1
- package/dist/Stack/StackItem.js +8 -1
- package/dist/Switch/Switch.d.ts +23 -2
- package/dist/Switch/Switch.d.ts.map +1 -1
- package/dist/Switch/Switch.js +41 -11
- package/dist/TabList/Tab.d.ts.map +1 -1
- package/dist/TabList/Tab.js +6 -0
- package/dist/TabList/TabList.d.ts +16 -4
- package/dist/TabList/TabList.d.ts.map +1 -1
- package/dist/TabList/TabList.js +86 -10
- package/dist/TabList/TabListContext.d.ts +5 -0
- package/dist/TabList/TabListContext.d.ts.map +1 -1
- package/dist/TabList/TabListContext.js +5 -0
- package/dist/TabList/TabMenu.d.ts.map +1 -1
- package/dist/TabList/TabMenu.js +6 -1
- package/dist/Table/BaseTable.d.ts.map +1 -1
- package/dist/Table/BaseTable.js +38 -16
- package/dist/Table/Table.d.ts.map +1 -1
- package/dist/Table/Table.js +36 -7
- package/dist/Table/TableCell.d.ts +8 -1
- package/dist/Table/TableCell.d.ts.map +1 -1
- package/dist/Table/TableCell.js +10 -10
- package/dist/Table/TableHeaderCell.d.ts +8 -1
- package/dist/Table/TableHeaderCell.d.ts.map +1 -1
- package/dist/Table/TableHeaderCell.js +16 -16
- package/dist/Table/TableRow.d.ts +6 -1
- package/dist/Table/TableRow.d.ts.map +1 -1
- package/dist/Table/TableRow.js +15 -7
- package/dist/Table/index.d.ts +4 -1
- package/dist/Table/index.d.ts.map +1 -1
- package/dist/Table/index.js +3 -2
- package/dist/Table/plugins/pagination/paginateData.d.ts +2 -1
- package/dist/Table/plugins/pagination/paginateData.d.ts.map +1 -1
- package/dist/Table/plugins/pagination/paginateData.js +8 -3
- package/dist/Table/plugins/pagination/useTablePagination.d.ts.map +1 -1
- package/dist/Table/plugins/pagination/useTablePagination.js +6 -1
- package/dist/Table/plugins/sortable/useTableSortable.d.ts.map +1 -1
- package/dist/Table/plugins/sortable/useTableSortable.js +59 -3
- package/dist/Table/plugins/stickyColumns/index.d.ts +3 -0
- package/dist/Table/plugins/stickyColumns/index.d.ts.map +1 -0
- package/dist/Table/plugins/stickyColumns/index.js +3 -0
- package/dist/Table/plugins/stickyColumns/useTableStickyColumns.d.ts +25 -0
- package/dist/Table/plugins/stickyColumns/useTableStickyColumns.d.ts.map +1 -0
- package/dist/Table/plugins/stickyColumns/useTableStickyColumns.js +369 -0
- package/dist/Table/tableContextMenu.d.ts +33 -0
- package/dist/Table/tableContextMenu.d.ts.map +1 -0
- package/dist/Table/tableContextMenu.js +133 -0
- package/dist/Table/types.d.ts +161 -5
- package/dist/Table/types.d.ts.map +1 -1
- package/dist/Table/useBaseTablePlugins.d.ts.map +1 -1
- package/dist/Table/useBaseTablePlugins.js +1 -1
- package/dist/Text/text.stylex.d.ts +2 -2
- package/dist/Text/text.stylex.js +2 -2
- package/dist/TextArea/TextArea.d.ts +22 -1
- package/dist/TextArea/TextArea.d.ts.map +1 -1
- package/dist/TextArea/TextArea.js +41 -9
- package/dist/TextInput/TextInput.d.ts +23 -2
- package/dist/TextInput/TextInput.d.ts.map +1 -1
- package/dist/TextInput/TextInput.js +55 -10
- package/dist/TimeInput/TimeInput.d.ts +23 -1
- package/dist/TimeInput/TimeInput.d.ts.map +1 -1
- package/dist/TimeInput/TimeInput.js +53 -10
- package/dist/Timestamp/Timestamp.d.ts +1 -1
- package/dist/Timestamp/Timestamp.d.ts.map +1 -1
- package/dist/Timestamp/Timestamp.js +28 -3
- package/dist/Toast/Toast.d.ts.map +1 -1
- package/dist/Toast/Toast.js +14 -0
- package/dist/Toast/ToastViewport.d.ts.map +1 -1
- package/dist/Toast/ToastViewport.js +132 -3
- package/dist/ToggleButton/ToggleButton.d.ts +7 -9
- package/dist/ToggleButton/ToggleButton.d.ts.map +1 -1
- package/dist/ToggleButton/ToggleButton.js +34 -57
- package/dist/Tokenizer/Tokenizer.d.ts +12 -1
- package/dist/Tokenizer/Tokenizer.d.ts.map +1 -1
- package/dist/Tokenizer/Tokenizer.js +27 -5
- package/dist/Toolbar/Toolbar.d.ts +3 -3
- package/dist/Toolbar/Toolbar.d.ts.map +1 -1
- package/dist/Toolbar/Toolbar.js +51 -7
- package/dist/Tooltip/useTooltip.d.ts.map +1 -1
- package/dist/Tooltip/useTooltip.js +57 -9
- package/dist/TreeList/TreeList.d.ts +1 -1
- package/dist/TreeList/TreeList.d.ts.map +1 -1
- package/dist/TreeList/TreeList.js +72 -2
- package/dist/TreeList/TreeListItem.d.ts +11 -1
- package/dist/TreeList/TreeListItem.d.ts.map +1 -1
- package/dist/TreeList/TreeListItem.js +51 -12
- package/dist/TreeList/treeListItem.markers.stylex.d.ts +16 -0
- package/dist/TreeList/treeListItem.markers.stylex.d.ts.map +1 -0
- package/dist/TreeList/treeListItem.markers.stylex.js +22 -0
- package/dist/Typeahead/BaseTypeahead.d.ts +9 -0
- package/dist/Typeahead/BaseTypeahead.d.ts.map +1 -1
- package/dist/Typeahead/BaseTypeahead.js +67 -6
- package/dist/Typeahead/Typeahead.d.ts +24 -1
- package/dist/Typeahead/Typeahead.d.ts.map +1 -1
- package/dist/Typeahead/Typeahead.js +29 -5
- package/dist/VisuallyHidden/VisuallyHidden.d.ts +61 -0
- package/dist/VisuallyHidden/VisuallyHidden.d.ts.map +1 -0
- package/dist/VisuallyHidden/VisuallyHidden.js +65 -0
- package/dist/VisuallyHidden/index.d.ts +11 -0
- package/dist/VisuallyHidden/index.d.ts.map +1 -0
- package/dist/VisuallyHidden/index.js +13 -0
- package/dist/astryx.css +40 -1
- package/dist/astryx.umd.js +147 -0
- package/dist/astryx.umd.js.map +7 -0
- package/dist/hooks/focusableSelector.d.ts +22 -0
- package/dist/hooks/focusableSelector.d.ts.map +1 -0
- package/dist/hooks/focusableSelector.js +24 -0
- package/dist/hooks/index.d.ts +12 -2
- package/dist/hooks/index.d.ts.map +1 -1
- package/dist/hooks/index.js +7 -2
- package/dist/hooks/useAnnounce.d.ts +40 -0
- package/dist/hooks/useAnnounce.d.ts.map +1 -0
- package/dist/hooks/useAnnounce.js +142 -0
- package/dist/hooks/useClickableContainer.d.ts +16 -1
- package/dist/hooks/useClickableContainer.d.ts.map +1 -1
- package/dist/hooks/useClickableContainer.js +16 -4
- package/dist/hooks/useEntryAnimation.d.ts.map +1 -1
- package/dist/hooks/useEntryAnimation.js +4 -4
- package/dist/hooks/useFocusTrap.d.ts +18 -0
- package/dist/hooks/useFocusTrap.d.ts.map +1 -1
- package/dist/hooks/useFocusTrap.js +87 -3
- package/dist/hooks/useGridFocus.d.ts +88 -1
- package/dist/hooks/useGridFocus.d.ts.map +1 -1
- package/dist/hooks/useGridFocus.js +261 -62
- package/dist/hooks/useKeyboardHint.d.ts +82 -0
- package/dist/hooks/useKeyboardHint.d.ts.map +1 -0
- package/dist/hooks/useKeyboardHint.js +220 -0
- package/dist/hooks/useListFocus.d.ts +78 -7
- package/dist/hooks/useListFocus.d.ts.map +1 -1
- package/dist/hooks/useListFocus.js +305 -52
- package/dist/hooks/useLongPress.d.ts +21 -0
- package/dist/hooks/useLongPress.d.ts.map +1 -0
- package/dist/hooks/useLongPress.js +89 -0
- package/dist/hooks/useTreeFocus.d.ts +157 -0
- package/dist/hooks/useTreeFocus.d.ts.map +1 -0
- package/dist/hooks/useTreeFocus.js +337 -0
- package/dist/hooks/useTypeahead.d.ts +63 -0
- package/dist/hooks/useTypeahead.d.ts.map +1 -0
- package/dist/hooks/useTypeahead.js +117 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/theme/generateThemeRules.js +1 -1
- package/dist/theme/syntax/SyntaxTheme.d.ts +1 -1
- package/dist/theme/syntax/SyntaxTheme.js +1 -1
- package/dist/theme/syntax/defineSyntaxTheme.d.ts.map +1 -1
- package/dist/theme/syntax/defineSyntaxTheme.js +2 -2
- package/dist/theme/syntax/presets.d.ts +1 -1
- package/dist/theme/syntax/presets.d.ts.map +1 -1
- package/dist/theme/syntax/presets.js +1 -1
- package/dist/theme/syntax/tokens.d.ts +1 -1
- package/dist/theme/syntax/tokens.js +1 -1
- package/dist/theme/types.d.ts +1 -1
- package/dist/utils/dateTypes.d.ts +12 -0
- package/dist/utils/dateTypes.d.ts.map +1 -1
- package/dist/utils/dateTypes.js +41 -1
- package/dist/utils/index.d.ts +4 -0
- package/dist/utils/index.d.ts.map +1 -1
- package/dist/utils/index.js +3 -1
- package/dist/utils/inputAria.d.ts +29 -0
- package/dist/utils/inputAria.d.ts.map +1 -0
- package/dist/utils/inputAria.js +30 -0
- package/dist/utils/timeParser.d.ts.map +1 -1
- package/dist/utils/timeParser.js +5 -2
- package/package.json +15 -5
- package/src/Avatar/Avatar.test.tsx +37 -0
- package/src/Avatar/Avatar.tsx +10 -5
- package/src/AvatarGroup/AvatarGroupOverflow.tsx +3 -0
- package/src/Banner/Banner.doc.mjs +8 -0
- package/src/Banner/Banner.test.tsx +16 -7
- package/src/Banner/Banner.tsx +9 -2
- package/src/Breadcrumbs/BreadcrumbItem.tsx +25 -7
- package/src/Breadcrumbs/Breadcrumbs.test.tsx +31 -10
- package/src/Button/Button.doc.mjs +6 -0
- package/src/Button/Button.test.tsx +105 -11
- package/src/Button/Button.tsx +76 -21
- package/src/Calendar/Calendar.doc.mjs +4 -4
- package/src/Calendar/Calendar.test.tsx +168 -30
- package/src/Calendar/Calendar.tsx +121 -66
- package/src/Calendar/hooks/index.ts +0 -6
- package/src/Calendar/index.ts +1 -3
- package/src/Calendar/styles.ts +4 -9
- package/src/Carousel/Carousel.doc.mjs +7 -1
- package/src/Carousel/Carousel.test.tsx +20 -0
- package/src/Carousel/Carousel.tsx +16 -1
- package/src/Center/Center.doc.mjs +12 -2
- package/src/Center/Center.tsx +28 -3
- package/src/Chat/ChatComposer.doc.mjs +3 -0
- package/src/Chat/ChatComposerDrawer.doc.mjs +12 -0
- package/src/Chat/ChatMessageList.doc.mjs +8 -0
- package/src/Chat/ChatMessageList.test.tsx +18 -0
- package/src/Chat/ChatMessageList.tsx +16 -0
- package/src/Chat/useTriggerMenu.tsx +3 -0
- package/src/CheckboxInput/CheckboxInput.doc.mjs +18 -0
- package/src/CheckboxInput/CheckboxInput.test.tsx +172 -27
- package/src/CheckboxInput/CheckboxInput.tsx +78 -6
- package/src/CheckboxList/CheckboxList.doc.mjs +9 -0
- package/src/CheckboxList/CheckboxList.test.tsx +169 -16
- package/src/CheckboxList/CheckboxList.tsx +56 -3
- package/src/CheckboxList/CheckboxListContext.tsx +7 -0
- package/src/Citation/Citation.doc.mjs +10 -0
- package/src/Citation/Citation.test.tsx +117 -0
- package/src/Citation/Citation.tsx +9 -1
- package/src/ClickableCard/ClickableCard.doc.mjs +15 -0
- package/src/CodeBlock/CodeBlock.test.tsx +115 -0
- package/src/CodeBlock/CodeBlock.tsx +61 -33
- package/src/CommandPalette/CommandPalette.test.tsx +47 -1
- package/src/CommandPalette/CommandPalette.tsx +9 -21
- package/src/ContextMenu/ContextMenu.doc.mjs +4 -4
- package/src/ContextMenu/ContextMenu.test.tsx +155 -1
- package/src/ContextMenu/ContextMenu.tsx +113 -16
- package/src/DateInput/DateInput.doc.mjs +281 -56
- package/src/DateInput/DateInput.test.tsx +188 -2
- package/src/DateInput/DateInput.tsx +89 -10
- package/src/DateRangeInput/DateRangeInput.doc.mjs +251 -46
- package/src/DateRangeInput/DateRangeInput.test.tsx +182 -20
- package/src/DateRangeInput/DateRangeInput.tsx +63 -5
- package/src/DateTimeInput/DateTimeInput.doc.mjs +368 -67
- package/src/DateTimeInput/DateTimeInput.test.tsx +279 -11
- package/src/DateTimeInput/DateTimeInput.tsx +125 -17
- package/src/Dialog/Dialog.doc.mjs +2 -2
- package/src/Dialog/Dialog.tsx +12 -0
- package/src/DropdownMenu/DropdownMenu.doc.mjs +1 -8
- package/src/DropdownMenu/DropdownMenu.test.tsx +56 -42
- package/src/DropdownMenu/DropdownMenu.tsx +52 -18
- package/src/EmptyState/EmptyState.test.tsx +4 -2
- package/src/EmptyState/EmptyState.tsx +6 -2
- package/src/Field/Field.test.tsx +32 -0
- package/src/Field/Field.tsx +23 -5
- package/src/Field/FieldLabel.tsx +55 -17
- package/src/FileInput/FileInput.doc.mjs +17 -0
- package/src/FileInput/FileInput.test.tsx +283 -49
- package/src/FileInput/FileInput.tsx +76 -4
- package/src/Grid/Grid.doc.mjs +14 -4
- package/src/Grid/Grid.tsx +20 -0
- package/src/HoverCard/HoverCard.doc.mjs +3 -0
- package/src/HoverCard/HoverCard.test.tsx +189 -2
- package/src/HoverCard/HoverCard.tsx +20 -16
- package/src/HoverCard/useHoverCard.tsx +13 -10
- package/src/Icon/Icon.doc.mjs +8 -0
- package/src/InputGroup/InputGroup.doc.mjs +2 -2
- package/src/InputGroup/InputGroup.test.tsx +98 -60
- package/src/InputGroup/InputGroup.tsx +21 -4
- package/src/InputGroup/InputGroupContext.ts +9 -4
- package/src/InputGroup/index.ts +1 -0
- package/src/Kbd/Kbd.test.tsx +22 -4
- package/src/Kbd/Kbd.tsx +37 -12
- package/src/Layer/anchorName.test.ts +146 -0
- package/src/Layer/anchorName.ts +46 -0
- package/src/Layer/layerAnimations.stylex.ts +20 -4
- package/src/Layer/useLayer.doc.mjs +12 -2
- package/src/Layer/useLayer.tsx +100 -15
- package/src/Layout/Layout.doc.mjs +1 -1
- package/src/Layout/Layout.tsx +8 -16
- package/src/Layout/LayoutFooter.doc.mjs +4 -4
- package/src/Layout/LayoutFooter.tsx +3 -3
- package/src/Layout/LayoutHeader.doc.mjs +4 -4
- package/src/Layout/LayoutHeader.tsx +3 -3
- package/src/Layout/LayoutPanel.tsx +3 -3
- package/src/Layout/padding.stylex.ts +52 -0
- package/src/Lightbox/Lightbox.doc.mjs +9 -2
- package/src/Lightbox/Lightbox.test.tsx +53 -5
- package/src/Lightbox/Lightbox.tsx +9 -4
- package/src/Link/Link.doc.mjs +14 -0
- package/src/Link/Link.test.tsx +52 -2
- package/src/Link/Link.tsx +42 -7
- package/src/Link/LinkProvider.tsx +1 -0
- package/src/List/List.doc.mjs +7 -0
- package/src/Markdown/Markdown.doc.mjs +2 -0
- package/src/Markdown/Markdown.test.tsx +28 -26
- package/src/Markdown/Markdown.tsx +21 -6
- package/src/MetadataList/MetadataListItem.doc.mjs +4 -0
- package/src/MobileNav/MobileNav.doc.mjs +8 -8
- package/src/MobileNav/MobileNav.tsx +13 -0
- package/src/MobileNav/MobileNavReopen.test.tsx +118 -0
- package/src/MoreMenu/MoreMenu.doc.mjs +2 -17
- package/src/MoreMenu/MoreMenu.tsx +0 -9
- package/src/MultiSelector/MultiSelector.doc.mjs +25 -0
- package/src/MultiSelector/MultiSelector.test.tsx +375 -8
- package/src/MultiSelector/MultiSelector.tsx +145 -21
- package/src/MultiSelector/hooks.ts +27 -0
- package/src/NavMenu/NavHeadingMenu.test.tsx +77 -1
- package/src/NavMenu/NavHeadingMenu.tsx +50 -3
- package/src/NumberInput/NumberInput.doc.mjs +17 -0
- package/src/NumberInput/NumberInput.test.tsx +242 -40
- package/src/NumberInput/NumberInput.tsx +89 -11
- package/src/OverflowList/OverflowList.doc.mjs +17 -0
- package/src/Pagination/Pagination.doc.mjs +3 -3
- package/src/Pagination/Pagination.test.tsx +250 -14
- package/src/Pagination/Pagination.tsx +54 -29
- package/src/Popover/usePopover.doc.mjs +7 -3
- package/src/Popover/usePopover.tsx +49 -6
- package/src/PowerSearch/PowerSearch.doc.mjs +15 -0
- package/src/PowerSearch/PowerSearch.test.tsx +97 -1
- package/src/PowerSearch/PowerSearch.tsx +16 -3
- package/src/ProgressBar/ProgressBar.test.tsx +45 -27
- package/src/ProgressBar/ProgressBar.tsx +3 -4
- package/src/RadioList/RadioList.doc.mjs +9 -0
- package/src/RadioList/RadioList.test.tsx +252 -16
- package/src/RadioList/RadioList.tsx +166 -10
- package/src/RadioList/RadioListItem.tsx +14 -2
- package/src/Resizable/Resizable.doc.mjs +1 -1
- package/src/Section/Section.doc.mjs +11 -0
- package/src/SegmentedControl/SegmentedControl.doc.mjs +9 -0
- package/src/SegmentedControl/SegmentedControl.test.tsx +214 -42
- package/src/SegmentedControl/SegmentedControl.tsx +102 -54
- package/src/SegmentedControl/SegmentedControlContext.ts +7 -0
- package/src/SegmentedControl/SegmentedControlItem.tsx +14 -1
- package/src/SelectableCard/SelectableCard.doc.mjs +15 -0
- package/src/Selector/Selector.doc.mjs +25 -0
- package/src/Selector/Selector.test.tsx +322 -15
- package/src/Selector/Selector.tsx +126 -40
- package/src/Selector/hooks.ts +23 -0
- package/src/SideNav/SideNav.test.tsx +16 -0
- package/src/SideNav/SideNavItem.tsx +2 -4
- package/src/Skeleton/Skeleton.doc.mjs +11 -1
- package/src/Skeleton/Skeleton.test.tsx +25 -0
- package/src/Skeleton/Skeleton.tsx +11 -1
- package/src/Slider/Slider.doc.mjs +19 -0
- package/src/Slider/Slider.test.tsx +158 -18
- package/src/Slider/Slider.tsx +54 -6
- package/src/Spinner/Spinner.tsx +7 -1
- package/src/Stack/Stack.doc.mjs +77 -0
- package/src/Stack/Stack.test.tsx +55 -5
- package/src/Stack/Stack.tsx +73 -24
- package/src/Stack/StackItem.test.tsx +23 -0
- package/src/Stack/StackItem.tsx +20 -23
- package/src/Switch/Switch.doc.mjs +15 -0
- package/src/Switch/Switch.test.tsx +162 -27
- package/src/Switch/Switch.tsx +61 -21
- package/src/TabList/Tab.tsx +6 -0
- package/src/TabList/TabList.doc.mjs +12 -0
- package/src/TabList/TabList.test.tsx +208 -0
- package/src/TabList/TabList.tsx +102 -12
- package/src/TabList/TabListContext.ts +7 -3
- package/src/TabList/TabMenu.tsx +6 -3
- package/src/Table/BaseTable.tsx +72 -41
- package/src/Table/Table.doc.mjs +14 -0
- package/src/Table/Table.test.tsx +39 -30
- package/src/Table/Table.tsx +27 -1
- package/src/Table/TableCell.tsx +25 -23
- package/src/Table/TableHeaderCell.tsx +28 -29
- package/src/Table/TableRow.tsx +37 -7
- package/src/Table/index.ts +6 -2
- package/src/Table/plugins/pagination/paginateData.ts +10 -3
- package/src/Table/plugins/pagination/useTablePagination.test.tsx +16 -0
- package/src/Table/plugins/pagination/useTablePagination.tsx +8 -1
- package/src/Table/plugins/sortable/useTableSortable.test.tsx +91 -2
- package/src/Table/plugins/sortable/useTableSortable.tsx +53 -1
- package/src/Table/plugins/stickyColumns/index.ts +4 -0
- package/src/Table/plugins/stickyColumns/useTableStickyColumns.test.tsx +163 -0
- package/src/Table/plugins/stickyColumns/useTableStickyColumns.tsx +407 -0
- package/src/Table/tableContextMenu.test.tsx +157 -0
- package/src/Table/tableContextMenu.tsx +142 -0
- package/src/Table/types.ts +175 -4
- package/src/Table/useBaseTablePlugins.ts +1 -0
- package/src/Table/useTableColumnResize.doc.mjs +96 -0
- package/src/Table/useTableStickyColumns.doc.mjs +59 -0
- package/src/Text/Heading.doc.mjs +15 -2
- package/src/Text/Text.doc.mjs +7 -1
- package/src/Text/text.stylex.ts +2 -2
- package/src/TextArea/TextArea.doc.mjs +17 -0
- package/src/TextArea/TextArea.test.tsx +167 -35
- package/src/TextArea/TextArea.tsx +62 -15
- package/src/TextInput/TextInput.doc.mjs +17 -0
- package/src/TextInput/TextInput.test.tsx +168 -34
- package/src/TextInput/TextInput.tsx +77 -9
- package/src/TimeInput/TimeInput.doc.mjs +335 -60
- package/src/TimeInput/TimeInput.test.tsx +144 -7
- package/src/TimeInput/TimeInput.tsx +74 -5
- package/src/Timestamp/Timestamp.doc.mjs +9 -0
- package/src/Timestamp/Timestamp.test.tsx +44 -18
- package/src/Timestamp/Timestamp.tsx +30 -10
- package/src/Toast/Toast.tsx +14 -0
- package/src/Toast/ToastViewport.test.tsx +204 -0
- package/src/Toast/ToastViewport.tsx +167 -21
- package/src/ToggleButton/ToggleButton.doc.mjs +9 -3
- package/src/ToggleButton/ToggleButton.test.tsx +39 -18
- package/src/ToggleButton/ToggleButton.tsx +46 -83
- package/src/Tokenizer/Tokenizer.doc.mjs +15 -0
- package/src/Tokenizer/Tokenizer.test.tsx +105 -1
- package/src/Tokenizer/Tokenizer.tsx +41 -2
- package/src/Toolbar/Toolbar.doc.mjs +65 -5
- package/src/Toolbar/Toolbar.test.tsx +109 -6
- package/src/Toolbar/Toolbar.tsx +59 -5
- package/src/Tooltip/Tooltip.test.tsx +81 -0
- package/src/Tooltip/useTooltip.tsx +57 -11
- package/src/TreeList/TreeList.test.tsx +295 -6
- package/src/TreeList/TreeList.tsx +73 -1
- package/src/TreeList/TreeListItem.tsx +51 -5
- package/src/TreeList/treeListItem.markers.stylex.ts +20 -0
- package/src/Typeahead/BaseTypeahead.tsx +86 -9
- package/src/Typeahead/Typeahead.doc.mjs +136 -30
- package/src/Typeahead/Typeahead.test.tsx +331 -1
- package/src/Typeahead/Typeahead.tsx +52 -1
- package/src/VisuallyHidden/VisuallyHidden.doc.mjs +80 -0
- package/src/VisuallyHidden/VisuallyHidden.test.tsx +76 -0
- package/src/VisuallyHidden/VisuallyHidden.tsx +113 -0
- package/src/VisuallyHidden/index.ts +15 -0
- package/src/hooks/focusableSelector.ts +25 -0
- package/src/hooks/index.ts +28 -2
- package/src/hooks/useAnnounce.test.tsx +101 -0
- package/src/hooks/useAnnounce.ts +168 -0
- package/src/hooks/useClickableContainer.ts +16 -4
- package/src/hooks/useEntryAnimation.ts +16 -4
- package/src/hooks/useFocusTrap.test.tsx +132 -0
- package/src/hooks/useFocusTrap.ts +98 -4
- package/src/hooks/useGridFocus.doc.mjs +40 -2
- package/src/hooks/useGridFocus.test.tsx +132 -0
- package/src/hooks/useGridFocus.ts +343 -67
- package/src/hooks/useImageMode.test.ts +133 -0
- package/src/hooks/useKeyboardHint.doc.mjs +101 -0
- package/src/hooks/useKeyboardHint.test.tsx +70 -0
- package/src/hooks/useKeyboardHint.tsx +332 -0
- package/src/hooks/useListFocus.doc.mjs +50 -10
- package/src/hooks/useListFocus.test.tsx +375 -0
- package/src/hooks/useListFocus.ts +395 -57
- package/src/hooks/useLongPress.test.tsx +134 -0
- package/src/hooks/useLongPress.ts +119 -0
- package/src/hooks/useTreeFocus.doc.mjs +140 -0
- package/src/hooks/useTreeFocus.test.tsx +214 -0
- package/src/hooks/useTreeFocus.ts +559 -0
- package/src/hooks/useTypeahead.test.tsx +109 -0
- package/src/hooks/useTypeahead.ts +183 -0
- package/src/index.ts +1 -0
- package/src/theme/derivedVarRegistry.test.ts +4 -0
- package/src/theme/generateThemeRules.test.ts +7 -8
- package/src/theme/generateThemeRules.ts +1 -1
- package/src/theme/syntax/SyntaxTheme.tsx +1 -1
- package/src/theme/syntax/defineSyntaxTheme.ts +20 -11
- package/src/theme/syntax/presets.ts +5 -2
- package/src/theme/syntax/tokens.ts +1 -1
- package/src/theme/types.ts +1 -1
- package/src/utils/dateTypes.test.ts +40 -0
- package/src/utils/dateTypes.ts +40 -0
- package/src/utils/index.ts +9 -0
- package/src/utils/inputAria.test.ts +39 -0
- package/src/utils/inputAria.ts +58 -0
- package/src/utils/timeParser.test.ts +10 -0
- package/src/utils/timeParser.ts +5 -2
- package/dist/Calendar/hooks/useCalendarRovingTabindex.d.ts +0 -57
- package/dist/Calendar/hooks/useCalendarRovingTabindex.d.ts.map +0 -1
- package/dist/Calendar/hooks/useCalendarRovingTabindex.js +0 -96
- package/src/Calendar/hooks/useCalendarRovingTabindex.ts +0 -118
|
@@ -9,10 +9,26 @@
|
|
|
9
9
|
* SYNC: When Pagination.tsx changes, update tests to match new behavior
|
|
10
10
|
*/
|
|
11
11
|
|
|
12
|
-
import {describe, it, expect, vi} from 'vitest';
|
|
13
|
-
import {
|
|
12
|
+
import {describe, it, expect, vi, afterEach} from 'vitest';
|
|
13
|
+
import {
|
|
14
|
+
render,
|
|
15
|
+
screen,
|
|
16
|
+
within,
|
|
17
|
+
fireEvent,
|
|
18
|
+
act,
|
|
19
|
+
waitFor,
|
|
20
|
+
} from '@testing-library/react';
|
|
14
21
|
import userEvent from '@testing-library/user-event';
|
|
15
22
|
import {Pagination, generatePageRange} from './Pagination';
|
|
23
|
+
import {__resetLiveRegionsForTest} from '../hooks/useAnnounce';
|
|
24
|
+
|
|
25
|
+
afterEach(() => {
|
|
26
|
+
__resetLiveRegionsForTest();
|
|
27
|
+
});
|
|
28
|
+
|
|
29
|
+
function politeRegion(): HTMLElement | null {
|
|
30
|
+
return document.querySelector('[data-astryx-live-region="polite"]');
|
|
31
|
+
}
|
|
16
32
|
|
|
17
33
|
// =============================================================================
|
|
18
34
|
// generatePageRange helper
|
|
@@ -239,6 +255,65 @@ describe('Pagination', () => {
|
|
|
239
255
|
});
|
|
240
256
|
});
|
|
241
257
|
|
|
258
|
+
// ---------------------------------------------------------------------------
|
|
259
|
+
// pageSize guarding
|
|
260
|
+
// ---------------------------------------------------------------------------
|
|
261
|
+
|
|
262
|
+
describe('pageSize guarding', () => {
|
|
263
|
+
it('does not crash the dots variant when pageSize is 0', () => {
|
|
264
|
+
render(
|
|
265
|
+
<Pagination
|
|
266
|
+
page={1}
|
|
267
|
+
onChange={() => {}}
|
|
268
|
+
totalItems={5}
|
|
269
|
+
pageSize={0}
|
|
270
|
+
variant="dots"
|
|
271
|
+
/>,
|
|
272
|
+
);
|
|
273
|
+
const group = screen.getByRole('group', {name: 'Page indicators'});
|
|
274
|
+
expect(within(group).getAllByRole('button')).toHaveLength(5);
|
|
275
|
+
});
|
|
276
|
+
|
|
277
|
+
it('treats NaN pageSize as the default', () => {
|
|
278
|
+
render(
|
|
279
|
+
<Pagination
|
|
280
|
+
page={1}
|
|
281
|
+
onChange={() => {}}
|
|
282
|
+
totalItems={50}
|
|
283
|
+
pageSize={NaN}
|
|
284
|
+
variant="compact"
|
|
285
|
+
/>,
|
|
286
|
+
);
|
|
287
|
+
expect(screen.getByText('Page 1 of 5')).toBeInTheDocument();
|
|
288
|
+
});
|
|
289
|
+
|
|
290
|
+
it('clamps negative pageSize to 1', () => {
|
|
291
|
+
render(
|
|
292
|
+
<Pagination
|
|
293
|
+
page={1}
|
|
294
|
+
onChange={() => {}}
|
|
295
|
+
totalItems={5}
|
|
296
|
+
pageSize={-10}
|
|
297
|
+
variant="compact"
|
|
298
|
+
/>,
|
|
299
|
+
);
|
|
300
|
+
expect(screen.getByText('Page 1 of 5')).toBeInTheDocument();
|
|
301
|
+
});
|
|
302
|
+
|
|
303
|
+
it('floors fractional pageSize', () => {
|
|
304
|
+
render(
|
|
305
|
+
<Pagination
|
|
306
|
+
page={1}
|
|
307
|
+
onChange={() => {}}
|
|
308
|
+
totalItems={50}
|
|
309
|
+
pageSize={2.5}
|
|
310
|
+
variant="compact"
|
|
311
|
+
/>,
|
|
312
|
+
);
|
|
313
|
+
expect(screen.getByText('Page 1 of 25')).toBeInTheDocument();
|
|
314
|
+
});
|
|
315
|
+
});
|
|
316
|
+
|
|
242
317
|
// ---------------------------------------------------------------------------
|
|
243
318
|
// Variant: dots
|
|
244
319
|
// ---------------------------------------------------------------------------
|
|
@@ -304,6 +379,38 @@ describe('Pagination', () => {
|
|
|
304
379
|
// ---------------------------------------------------------------------------
|
|
305
380
|
|
|
306
381
|
describe('page change callbacks', () => {
|
|
382
|
+
it('does not announce on initial mount', () => {
|
|
383
|
+
render(<Pagination page={1} onChange={() => {}} totalPages={10} />);
|
|
384
|
+
expect(politeRegion()).toBeNull();
|
|
385
|
+
});
|
|
386
|
+
|
|
387
|
+
it('announces the new page politely when navigating', async () => {
|
|
388
|
+
const user = userEvent.setup();
|
|
389
|
+
render(<Pagination page={2} onChange={() => {}} totalPages={10} />);
|
|
390
|
+
await user.click(screen.getByRole('button', {name: 'Go to page 3'}));
|
|
391
|
+
await waitFor(() => {
|
|
392
|
+
expect(politeRegion()).toHaveTextContent('Page 3 of 10');
|
|
393
|
+
});
|
|
394
|
+
});
|
|
395
|
+
|
|
396
|
+
it('announces the next page when clicking next', async () => {
|
|
397
|
+
const user = userEvent.setup();
|
|
398
|
+
render(<Pagination page={2} onChange={() => {}} totalPages={5} />);
|
|
399
|
+
await user.click(screen.getByRole('button', {name: 'Go to next page'}));
|
|
400
|
+
await waitFor(() => {
|
|
401
|
+
expect(politeRegion()).toHaveTextContent('Page 3 of 5');
|
|
402
|
+
});
|
|
403
|
+
});
|
|
404
|
+
|
|
405
|
+
it('announces without a total when only hasMore is known', async () => {
|
|
406
|
+
const user = userEvent.setup();
|
|
407
|
+
render(<Pagination page={1} onChange={() => {}} hasMore />);
|
|
408
|
+
await user.click(screen.getByRole('button', {name: 'Go to next page'}));
|
|
409
|
+
await waitFor(() => {
|
|
410
|
+
expect(politeRegion()).toHaveTextContent('Page 2');
|
|
411
|
+
});
|
|
412
|
+
});
|
|
413
|
+
|
|
307
414
|
it('calls onChange when clicking a page button', async () => {
|
|
308
415
|
const user = userEvent.setup();
|
|
309
416
|
const onChange = vi.fn();
|
|
@@ -346,6 +453,145 @@ describe('Pagination', () => {
|
|
|
346
453
|
});
|
|
347
454
|
});
|
|
348
455
|
|
|
456
|
+
// ---------------------------------------------------------------------------
|
|
457
|
+
// changeAction (interruptible, optimistic)
|
|
458
|
+
// ---------------------------------------------------------------------------
|
|
459
|
+
|
|
460
|
+
describe('changeAction', () => {
|
|
461
|
+
it('fires onChange then changeAction with the new page', async () => {
|
|
462
|
+
const user = userEvent.setup();
|
|
463
|
+
const order: string[] = [];
|
|
464
|
+
const onChange = vi.fn(() => order.push('onChange'));
|
|
465
|
+
const changeAction = vi.fn(() => {
|
|
466
|
+
order.push('changeAction');
|
|
467
|
+
});
|
|
468
|
+
render(
|
|
469
|
+
<Pagination
|
|
470
|
+
page={1}
|
|
471
|
+
onChange={onChange}
|
|
472
|
+
changeAction={changeAction}
|
|
473
|
+
totalPages={5}
|
|
474
|
+
/>,
|
|
475
|
+
);
|
|
476
|
+
await user.click(screen.getByRole('button', {name: 'Go to next page'}));
|
|
477
|
+
expect(onChange).toHaveBeenCalledWith(2);
|
|
478
|
+
expect(changeAction).toHaveBeenCalledWith(2);
|
|
479
|
+
expect(order).toEqual(['onChange', 'changeAction']);
|
|
480
|
+
});
|
|
481
|
+
|
|
482
|
+
it('shows the optimistic page while changeAction is pending', async () => {
|
|
483
|
+
const user = userEvent.setup();
|
|
484
|
+
let resolveAction: (() => void) | undefined;
|
|
485
|
+
const changeAction = vi.fn(
|
|
486
|
+
async () =>
|
|
487
|
+
new Promise<void>(resolve => {
|
|
488
|
+
resolveAction = resolve;
|
|
489
|
+
}),
|
|
490
|
+
);
|
|
491
|
+
render(
|
|
492
|
+
<Pagination
|
|
493
|
+
page={1}
|
|
494
|
+
onChange={() => {}}
|
|
495
|
+
changeAction={changeAction}
|
|
496
|
+
totalPages={5}
|
|
497
|
+
variant="compact"
|
|
498
|
+
/>,
|
|
499
|
+
);
|
|
500
|
+
|
|
501
|
+
// The committed `page` prop stays at 1, but the indicator optimistically
|
|
502
|
+
// reflects the page being navigated to.
|
|
503
|
+
await user.click(screen.getByRole('button', {name: 'Go to next page'}));
|
|
504
|
+
expect(changeAction).toHaveBeenCalledWith(2);
|
|
505
|
+
expect(
|
|
506
|
+
within(screen.getByRole('navigation')).getByText('Page 2 of 5'),
|
|
507
|
+
).toBeInTheDocument();
|
|
508
|
+
|
|
509
|
+
await act(async () => {
|
|
510
|
+
resolveAction?.();
|
|
511
|
+
await Promise.resolve();
|
|
512
|
+
});
|
|
513
|
+
});
|
|
514
|
+
|
|
515
|
+
it('interrupts an in-flight action on rapid next clicks', async () => {
|
|
516
|
+
// Each click derives its target from the optimistic page, so clicking
|
|
517
|
+
// next twice before the action settles advances 1 -> 2 -> 3 instead of
|
|
518
|
+
// being dropped by a re-entry guard.
|
|
519
|
+
const resolvers: (() => void)[] = [];
|
|
520
|
+
const changeAction = vi.fn(
|
|
521
|
+
async () =>
|
|
522
|
+
new Promise<void>(resolve => {
|
|
523
|
+
resolvers.push(resolve);
|
|
524
|
+
}),
|
|
525
|
+
);
|
|
526
|
+
render(
|
|
527
|
+
<Pagination
|
|
528
|
+
page={1}
|
|
529
|
+
onChange={() => {}}
|
|
530
|
+
changeAction={changeAction}
|
|
531
|
+
totalPages={5}
|
|
532
|
+
variant="compact"
|
|
533
|
+
/>,
|
|
534
|
+
);
|
|
535
|
+
|
|
536
|
+
const next = screen.getByRole('button', {name: 'Go to next page'});
|
|
537
|
+
const nav = screen.getByRole('navigation');
|
|
538
|
+
await act(async () => {
|
|
539
|
+
fireEvent.click(next);
|
|
540
|
+
});
|
|
541
|
+
// Scope to the nav landmark: the live region on document.body also
|
|
542
|
+
// carries the announced page text.
|
|
543
|
+
expect(within(nav).getByText('Page 2 of 5')).toBeInTheDocument();
|
|
544
|
+
await act(async () => {
|
|
545
|
+
fireEvent.click(next);
|
|
546
|
+
});
|
|
547
|
+
expect(within(nav).getByText('Page 3 of 5')).toBeInTheDocument();
|
|
548
|
+
|
|
549
|
+
expect(changeAction).toHaveBeenCalledTimes(2);
|
|
550
|
+
expect(changeAction).toHaveBeenNthCalledWith(1, 2);
|
|
551
|
+
expect(changeAction).toHaveBeenNthCalledWith(2, 3);
|
|
552
|
+
|
|
553
|
+
await act(async () => {
|
|
554
|
+
resolvers.forEach(resolve => resolve());
|
|
555
|
+
await Promise.resolve();
|
|
556
|
+
});
|
|
557
|
+
});
|
|
558
|
+
|
|
559
|
+
it('supports a synchronous changeAction', async () => {
|
|
560
|
+
const user = userEvent.setup();
|
|
561
|
+
const changeAction = vi.fn((_page: number) => {});
|
|
562
|
+
const onChange = vi.fn();
|
|
563
|
+
render(
|
|
564
|
+
<Pagination
|
|
565
|
+
page={2}
|
|
566
|
+
onChange={onChange}
|
|
567
|
+
changeAction={changeAction}
|
|
568
|
+
totalPages={5}
|
|
569
|
+
/>,
|
|
570
|
+
);
|
|
571
|
+
await user.click(
|
|
572
|
+
screen.getByRole('button', {name: 'Go to previous page'}),
|
|
573
|
+
);
|
|
574
|
+
expect(onChange).toHaveBeenCalledWith(1);
|
|
575
|
+
expect(changeAction).toHaveBeenCalledWith(1);
|
|
576
|
+
});
|
|
577
|
+
|
|
578
|
+
it('does not fire changeAction when disabled', async () => {
|
|
579
|
+
const user = userEvent.setup();
|
|
580
|
+
const changeAction = vi.fn();
|
|
581
|
+
render(
|
|
582
|
+
<Pagination
|
|
583
|
+
page={1}
|
|
584
|
+
onChange={() => {}}
|
|
585
|
+
changeAction={changeAction}
|
|
586
|
+
totalPages={5}
|
|
587
|
+
isDisabled
|
|
588
|
+
/>,
|
|
589
|
+
);
|
|
590
|
+
await user.click(screen.getByRole('button', {name: 'Go to next page'}));
|
|
591
|
+
expect(changeAction).not.toHaveBeenCalled();
|
|
592
|
+
});
|
|
593
|
+
});
|
|
594
|
+
|
|
349
595
|
// ---------------------------------------------------------------------------
|
|
350
596
|
// Boundary states
|
|
351
597
|
// ---------------------------------------------------------------------------
|
|
@@ -459,12 +705,7 @@ describe('Pagination', () => {
|
|
|
459
705
|
describe('disabled state', () => {
|
|
460
706
|
it('disables all page buttons when isDisabled', () => {
|
|
461
707
|
render(
|
|
462
|
-
<Pagination
|
|
463
|
-
page={3}
|
|
464
|
-
onChange={() => {}}
|
|
465
|
-
totalPages={5}
|
|
466
|
-
isDisabled
|
|
467
|
-
/>,
|
|
708
|
+
<Pagination page={3} onChange={() => {}} totalPages={5} isDisabled />,
|
|
468
709
|
);
|
|
469
710
|
expect(
|
|
470
711
|
screen.getByRole('button', {name: 'Go to previous page'}),
|
|
@@ -480,12 +721,7 @@ describe('Pagination', () => {
|
|
|
480
721
|
const user = userEvent.setup();
|
|
481
722
|
const onChange = vi.fn();
|
|
482
723
|
render(
|
|
483
|
-
<Pagination
|
|
484
|
-
page={3}
|
|
485
|
-
onChange={onChange}
|
|
486
|
-
totalPages={5}
|
|
487
|
-
isDisabled
|
|
488
|
-
/>,
|
|
724
|
+
<Pagination page={3} onChange={onChange} totalPages={5} isDisabled />,
|
|
489
725
|
);
|
|
490
726
|
// Disabled buttons can't be clicked
|
|
491
727
|
await user.click(screen.getByRole('button', {name: 'Go to page 1'}));
|
|
@@ -19,7 +19,7 @@
|
|
|
19
19
|
* label, data-testid, xstyle
|
|
20
20
|
*/
|
|
21
21
|
|
|
22
|
-
import {useTransition} from 'react';
|
|
22
|
+
import {useOptimistic, useTransition} from 'react';
|
|
23
23
|
import * as stylex from '@stylexjs/stylex';
|
|
24
24
|
import {
|
|
25
25
|
colorVars,
|
|
@@ -34,6 +34,7 @@ import {Button} from '../Button';
|
|
|
34
34
|
import {Icon} from '../Icon';
|
|
35
35
|
import {Selector} from '../Selector';
|
|
36
36
|
import {Text} from '../Text';
|
|
37
|
+
import {useAnnounce} from '../hooks/useAnnounce';
|
|
37
38
|
import {mergeProps} from '../utils';
|
|
38
39
|
import type {BaseProps} from '../BaseProps';
|
|
39
40
|
import {themeProps} from '../utils/themeProps';
|
|
@@ -335,7 +336,7 @@ export function Pagination({
|
|
|
335
336
|
totalItems,
|
|
336
337
|
totalPages: totalPagesProp,
|
|
337
338
|
hasMore,
|
|
338
|
-
pageSize = 10,
|
|
339
|
+
pageSize: pageSizeProp = 10,
|
|
339
340
|
pageSizeOptions,
|
|
340
341
|
onPageSizeChange,
|
|
341
342
|
variant = 'pages',
|
|
@@ -349,16 +350,36 @@ export function Pagination({
|
|
|
349
350
|
style,
|
|
350
351
|
ref,
|
|
351
352
|
}: PaginationProps) {
|
|
352
|
-
const [
|
|
353
|
+
const [, startTransition] = useTransition();
|
|
354
|
+
|
|
355
|
+
// pageSize is typed as number, so 0, NaN, and negatives are valid at the
|
|
356
|
+
// type level but yield Infinity/NaN page counts, and
|
|
357
|
+
// Array.from({length: Infinity}) crashes the dots variant. Coerce to a
|
|
358
|
+
// positive integer; non-finite values fall back to the default.
|
|
359
|
+
const pageSize = Number.isFinite(pageSizeProp)
|
|
360
|
+
? Math.max(1, Math.floor(pageSizeProp))
|
|
361
|
+
: 10;
|
|
362
|
+
|
|
363
|
+
// Announce page changes politely (navigation-10). The controls carry no
|
|
364
|
+
// live region, so page transitions were previously silent to screen readers.
|
|
365
|
+
// Only user-driven changes go through handlePageChange, so initial mount is
|
|
366
|
+
// never announced.
|
|
367
|
+
const announce = useAnnounce();
|
|
368
|
+
|
|
369
|
+
// Track the page optimistically so rapid prev/next clicks advance from the
|
|
370
|
+
// in-flight target instead of stalling on the last committed page.
|
|
371
|
+
const [optimisticPage, setOptimisticPage] = useOptimistic(page);
|
|
353
372
|
|
|
354
373
|
// Compute pagination state
|
|
355
374
|
const computedTotalPages =
|
|
356
375
|
totalPagesProp ??
|
|
357
376
|
(totalItems != null ? Math.ceil(totalItems / pageSize) : undefined);
|
|
358
377
|
|
|
359
|
-
const hasPrevious =
|
|
378
|
+
const hasPrevious = optimisticPage > 1;
|
|
360
379
|
const hasNext =
|
|
361
|
-
computedTotalPages != null
|
|
380
|
+
computedTotalPages != null
|
|
381
|
+
? optimisticPage < computedTotalPages
|
|
382
|
+
: (hasMore ?? false);
|
|
362
383
|
|
|
363
384
|
// Return null for empty state
|
|
364
385
|
if (totalItems != null && totalItems <= 0) {
|
|
@@ -368,48 +389,52 @@ export function Pagination({
|
|
|
368
389
|
return null;
|
|
369
390
|
}
|
|
370
391
|
|
|
392
|
+
// Interruptible: re-clicking before the transition settles starts a fresh one
|
|
393
|
+
// with the next optimistic page rather than being dropped, so there is no
|
|
394
|
+
// re-entry guard.
|
|
371
395
|
const handlePageChange = (newPage: number) => {
|
|
372
|
-
if (isDisabled
|
|
396
|
+
if (isDisabled) {
|
|
373
397
|
return;
|
|
374
398
|
}
|
|
399
|
+
// Keep onChange urgent so controlled page state updates in the same commit
|
|
400
|
+
// as the click; only the optimistic indicator and changeAction defer.
|
|
375
401
|
onChange(newPage);
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
402
|
+
announce(
|
|
403
|
+
computedTotalPages != null
|
|
404
|
+
? `Page ${newPage} of ${computedTotalPages}`
|
|
405
|
+
: `Page ${newPage}`,
|
|
406
|
+
);
|
|
407
|
+
startTransition(async () => {
|
|
408
|
+
setOptimisticPage(newPage);
|
|
409
|
+
await changeAction?.(newPage);
|
|
410
|
+
});
|
|
381
411
|
};
|
|
382
412
|
|
|
383
413
|
const handlePrevious = () => {
|
|
384
414
|
if (hasPrevious) {
|
|
385
|
-
handlePageChange(
|
|
415
|
+
handlePageChange(optimisticPage - 1);
|
|
386
416
|
}
|
|
387
417
|
};
|
|
388
418
|
|
|
389
419
|
const handleNext = () => {
|
|
390
420
|
if (hasNext) {
|
|
391
|
-
handlePageChange(
|
|
421
|
+
handlePageChange(optimisticPage + 1);
|
|
392
422
|
}
|
|
393
423
|
};
|
|
394
424
|
|
|
395
425
|
const handlePageSizeChange = (value: string) => {
|
|
396
426
|
const newSize = Number(value);
|
|
397
427
|
onPageSizeChange?.(newSize);
|
|
398
|
-
// Reset to page 1 when page size changes
|
|
399
|
-
|
|
400
|
-
if (changeAction) {
|
|
401
|
-
startTransition(async () => {
|
|
402
|
-
await changeAction(1);
|
|
403
|
-
});
|
|
404
|
-
}
|
|
428
|
+
// Reset to page 1 when page size changes.
|
|
429
|
+
handlePageChange(1);
|
|
405
430
|
};
|
|
406
431
|
|
|
407
432
|
// Item range for count display
|
|
408
|
-
const rangeStart = (
|
|
433
|
+
const rangeStart = (optimisticPage - 1) * pageSize + 1;
|
|
409
434
|
const rangeEnd =
|
|
410
435
|
totalItems != null
|
|
411
|
-
? Math.min(
|
|
412
|
-
:
|
|
436
|
+
? Math.min(optimisticPage * pageSize, totalItems)
|
|
437
|
+
: optimisticPage * pageSize;
|
|
413
438
|
|
|
414
439
|
const buttonSize = size === 'sm' ? 'sm' : 'md';
|
|
415
440
|
const isSm = size === 'sm';
|
|
@@ -421,7 +446,7 @@ export function Pagination({
|
|
|
421
446
|
return null;
|
|
422
447
|
}
|
|
423
448
|
const pageRange = generatePageRange(
|
|
424
|
-
|
|
449
|
+
optimisticPage,
|
|
425
450
|
computedTotalPages,
|
|
426
451
|
siblingCount,
|
|
427
452
|
);
|
|
@@ -443,7 +468,7 @@ export function Pagination({
|
|
|
443
468
|
</span>
|
|
444
469
|
);
|
|
445
470
|
}
|
|
446
|
-
const isActive = item ===
|
|
471
|
+
const isActive = item === optimisticPage;
|
|
447
472
|
return (
|
|
448
473
|
<Button
|
|
449
474
|
key={item}
|
|
@@ -483,7 +508,7 @@ export function Pagination({
|
|
|
483
508
|
return (
|
|
484
509
|
<span {...stylex.props(styles.infoText)}>
|
|
485
510
|
<Text type="body" size="sm" color="secondary">
|
|
486
|
-
{`Page ${
|
|
511
|
+
{`Page ${optimisticPage} of ${computedTotalPages}`}
|
|
487
512
|
</Text>
|
|
488
513
|
</span>
|
|
489
514
|
);
|
|
@@ -503,18 +528,18 @@ export function Pagination({
|
|
|
503
528
|
key={i + 1}
|
|
504
529
|
type="button"
|
|
505
530
|
aria-label={`Go to page ${i + 1}`}
|
|
506
|
-
aria-current={i + 1 ===
|
|
531
|
+
aria-current={i + 1 === optimisticPage ? 'page' : undefined}
|
|
507
532
|
onClick={() => handlePageChange(i + 1)}
|
|
508
533
|
disabled={isDisabled}
|
|
509
534
|
{...mergeProps(
|
|
510
535
|
themeProps('pagination-dot', {
|
|
511
|
-
active: i + 1 ===
|
|
536
|
+
active: i + 1 === optimisticPage ? 'active' : null,
|
|
512
537
|
size,
|
|
513
538
|
}),
|
|
514
539
|
stylex.props(
|
|
515
540
|
styles.dot,
|
|
516
541
|
isSm && styles.dotSm,
|
|
517
|
-
i + 1 ===
|
|
542
|
+
i + 1 === optimisticPage && styles.dotActive,
|
|
518
543
|
isDisabled && styles.dotDisabled,
|
|
519
544
|
),
|
|
520
545
|
)}
|
|
@@ -14,7 +14,9 @@ export const docs = {
|
|
|
14
14
|
{name: 'hasAutoFocus', type: 'boolean', description: 'Whether to automatically focus the first focusable element when opened.', default: 'true'},
|
|
15
15
|
{name: 'hasCloseButton', type: 'boolean', description: 'Whether to include a hidden close button that appears for keyboard users.', default: 'true'},
|
|
16
16
|
{name: 'closeButtonLabel', type: 'string', description: 'Accessible label for the hidden close button.', default: "'Close popover'"},
|
|
17
|
-
{name: 'dialogLabel', type: 'string', description: 'Accessible label for the popover dialog. Provide one when there is no visible title.'},
|
|
17
|
+
{name: 'dialogLabel', type: 'string', description: 'Accessible label for the popover dialog (only applies when role is "dialog"). Provide one when there is no visible title.'},
|
|
18
|
+
{name: 'role', type: "'dialog' | 'none'", description: 'ARIA role on the content wrapper. Use "dialog" for genuine dialog content; use "none" for listbox/menu popups whose own content role should be exposed and whose trigger keeps DOM focus.', default: "'dialog'"},
|
|
19
|
+
{name: 'isModal', type: 'boolean', description: 'Whether a dialog-role popover is modal (aria-modal). Only applies when role is "dialog".', default: 'true'},
|
|
18
20
|
{name: 'hasSurface', type: 'boolean', description: 'Whether to apply the default popover surface background, radius, and shadow.', default: 'true'},
|
|
19
21
|
],
|
|
20
22
|
returns: [
|
|
@@ -27,7 +29,7 @@ export const docs = {
|
|
|
27
29
|
{name: 'isOpen', type: 'boolean', description: 'Whether the popover is currently open.'},
|
|
28
30
|
{name: 'id', type: 'string', description: 'Unique ID for aria-describedby or aria-controls.'},
|
|
29
31
|
{name: 'render', type: '(children: ReactNode, props?: ContextRenderProps) => ReactNode', description: 'Render function for anchor-positioned popover content. Pass placement and alignment here.'},
|
|
30
|
-
{name: 'triggerProps', type: '{aria-haspopup: "dialog"; aria-expanded: boolean; aria-controls: string}', description: 'ARIA attributes to spread onto the trigger element.'},
|
|
32
|
+
{name: 'triggerProps', type: '{aria-haspopup: "dialog" | "true"; aria-expanded: boolean; aria-controls: string}', description: 'ARIA attributes to spread onto the trigger element. aria-haspopup reflects the popover role.'},
|
|
31
33
|
],
|
|
32
34
|
usage: {
|
|
33
35
|
description: 'Headless hook for click-triggered popovers with focus trapping. Combines useLayer with useFocusTrap, auto-focus, light dismiss, Escape handling, and an optional hidden close button for accessible dialog-like popover behavior. Use for custom interactive floating content that needs keyboard navigation.',
|
|
@@ -54,7 +56,9 @@ export const docsDense = {
|
|
|
54
56
|
hasAutoFocus: 'whether first focusable element receives focus on open.',
|
|
55
57
|
hasCloseButton: 'whether hidden keyboard close button is included.',
|
|
56
58
|
closeButtonLabel: 'label for hidden close button.',
|
|
57
|
-
dialogLabel: 'accessible label for popover dialog.',
|
|
59
|
+
dialogLabel: 'accessible label for popover dialog (role="dialog" only).',
|
|
60
|
+
role: 'content wrapper ARIA role; "none" for listbox/menu popups.',
|
|
61
|
+
isModal: 'whether a dialog-role popover is modal (aria-modal).',
|
|
58
62
|
hasSurface: 'apply default surface background/radius/shadow.',
|
|
59
63
|
},
|
|
60
64
|
returnDescriptions: {
|
|
@@ -130,10 +130,35 @@ export interface UsePopoverOptions {
|
|
|
130
130
|
|
|
131
131
|
/**
|
|
132
132
|
* Accessible label for the dialog.
|
|
133
|
-
* Required for screen readers to announce the dialog purpose
|
|
133
|
+
* Required for screen readers to announce the dialog purpose
|
|
134
|
+
* (only applies when `role` is `'dialog'`).
|
|
134
135
|
*/
|
|
135
136
|
dialogLabel?: string;
|
|
136
137
|
|
|
138
|
+
/**
|
|
139
|
+
* ARIA role stamped on the popover content wrapper.
|
|
140
|
+
*
|
|
141
|
+
* - `'dialog'` (default): the wrapper is a `role="dialog"` and, when
|
|
142
|
+
* `isModal` is true, carries `aria-modal`. Use for genuine dialog content.
|
|
143
|
+
* - `'none'`: the wrapper carries no role or `aria-modal`, so the popup's own
|
|
144
|
+
* content role (e.g. a child `role="listbox"` or `role="menu"`) is the
|
|
145
|
+
* exposed semantics. Use for comboboxes, listboxes, and menus — their
|
|
146
|
+
* trigger keeps DOM focus, so announcing an unnamed modal dialog around
|
|
147
|
+
* them is incorrect.
|
|
148
|
+
*
|
|
149
|
+
* @default 'dialog'
|
|
150
|
+
*/
|
|
151
|
+
role?: 'dialog' | 'none';
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Whether the dialog is modal (`aria-modal`). Only applies when `role` is
|
|
155
|
+
* `'dialog'`. Set to `false` for non-modal dialogs that do not inert the rest
|
|
156
|
+
* of the page.
|
|
157
|
+
*
|
|
158
|
+
* @default true
|
|
159
|
+
*/
|
|
160
|
+
isModal?: boolean;
|
|
161
|
+
|
|
137
162
|
/**
|
|
138
163
|
* Whether to apply the default popover surface (background, border-radius,
|
|
139
164
|
* box-shadow) to the content wrapper.
|
|
@@ -215,7 +240,7 @@ export interface UsePopoverReturn {
|
|
|
215
240
|
* ARIA attributes to spread on the trigger element
|
|
216
241
|
*/
|
|
217
242
|
triggerProps: {
|
|
218
|
-
'aria-haspopup': 'dialog';
|
|
243
|
+
'aria-haspopup': 'dialog' | 'true';
|
|
219
244
|
'aria-expanded': boolean;
|
|
220
245
|
'aria-controls': string;
|
|
221
246
|
};
|
|
@@ -274,6 +299,8 @@ export function usePopover(
|
|
|
274
299
|
hasCloseButton = true,
|
|
275
300
|
closeButtonLabel = 'Close popover',
|
|
276
301
|
dialogLabel,
|
|
302
|
+
role = 'dialog',
|
|
303
|
+
isModal = true,
|
|
277
304
|
} = options;
|
|
278
305
|
|
|
279
306
|
// Track the trigger element for returning focus
|
|
@@ -339,20 +366,34 @@ export function usePopover(
|
|
|
339
366
|
|
|
340
367
|
// ARIA attributes for the trigger
|
|
341
368
|
const triggerProps = {
|
|
342
|
-
'aria-haspopup': 'dialog' as const,
|
|
369
|
+
'aria-haspopup': role === 'dialog' ? ('dialog' as const) : ('true' as const),
|
|
343
370
|
'aria-expanded': layer.isOpen,
|
|
344
371
|
'aria-controls': layer.id,
|
|
345
372
|
};
|
|
346
373
|
|
|
374
|
+
// Dev-time guardrail: a dialog popover should always be labeled. Warn once
|
|
375
|
+
// per hook instance (in an effect) rather than on every render.
|
|
376
|
+
const warnedUnnamedDialogRef = useRef(false);
|
|
377
|
+
useEffect(() => {
|
|
378
|
+
if (role === 'dialog' && !dialogLabel && !warnedUnnamedDialogRef.current) {
|
|
379
|
+
warnedUnnamedDialogRef.current = true;
|
|
380
|
+
console.warn(
|
|
381
|
+
'usePopover: role="dialog" without a `dialogLabel` renders an unnamed ' +
|
|
382
|
+
'dialog. Pass `dialogLabel`, or use `role: "none"` for listbox/menu ' +
|
|
383
|
+
'popups whose content already carries its own role.',
|
|
384
|
+
);
|
|
385
|
+
}
|
|
386
|
+
}, [role, dialogLabel]);
|
|
387
|
+
|
|
347
388
|
// Wrapped render function that includes surface styles and optional hidden close button
|
|
348
389
|
const render = useCallback(
|
|
349
390
|
(children: ReactNode, props?: ContextRenderProps): ReactNode => {
|
|
350
391
|
return layer.render(
|
|
351
392
|
<div
|
|
352
393
|
ref={contentRef}
|
|
353
|
-
role=
|
|
354
|
-
aria-modal=
|
|
355
|
-
aria-label={dialogLabel}
|
|
394
|
+
role={role === 'dialog' ? 'dialog' : undefined}
|
|
395
|
+
aria-modal={role === 'dialog' && isModal ? true : undefined}
|
|
396
|
+
aria-label={role === 'dialog' ? dialogLabel : undefined}
|
|
356
397
|
{...stylex.props(
|
|
357
398
|
styles.contentWrapper,
|
|
358
399
|
hasSurface && styles.surface,
|
|
@@ -379,6 +420,8 @@ export function usePopover(
|
|
|
379
420
|
closeButtonLabel,
|
|
380
421
|
contentRef,
|
|
381
422
|
dialogLabel,
|
|
423
|
+
role,
|
|
424
|
+
isModal,
|
|
382
425
|
xstyle,
|
|
383
426
|
],
|
|
384
427
|
);
|
|
@@ -71,6 +71,12 @@ export const docs = {
|
|
|
71
71
|
description: 'Disables the entire component.',
|
|
72
72
|
default: 'false',
|
|
73
73
|
},
|
|
74
|
+
{
|
|
75
|
+
name: 'disabledMessage',
|
|
76
|
+
type: 'string',
|
|
77
|
+
description:
|
|
78
|
+
'Explains why the search is disabled. With isDisabled, shows a tooltip on hover/keyboard focus and keeps the input focusable via aria-disabled (input stays blocked). Use this instead of wrapping a disabled PowerSearch in Tooltip — disabled controls swallow the hover events an external Tooltip needs.',
|
|
79
|
+
},
|
|
74
80
|
{
|
|
75
81
|
name: 'status',
|
|
76
82
|
type: 'InputStatus',
|
|
@@ -136,6 +142,7 @@ export const docs = {
|
|
|
136
142
|
{ guidance: true, description: 'Define clear, descriptive field names and aliases so users can quickly find the filter they need.' },
|
|
137
143
|
{ guidance: true, description: 'Provide a result count to give users feedback on how their filters affect the data set.' },
|
|
138
144
|
{ guidance: false, description: 'Use PowerSearch for simple keyword searches; a standard text input is more appropriate for single-field lookups.' },
|
|
145
|
+
{ guidance: false, description: 'Wrap a disabled PowerSearch in Tooltip to explain why it is disabled; disabled controls swallow the hover events the wrapper needs. Use the disabledMessage prop instead.' },
|
|
139
146
|
],
|
|
140
147
|
},
|
|
141
148
|
};
|
|
@@ -212,6 +219,12 @@ export const docsZh = {
|
|
|
212
219
|
description: '禁用整个组件。',
|
|
213
220
|
default: 'false',
|
|
214
221
|
},
|
|
222
|
+
{
|
|
223
|
+
name: 'disabledMessage',
|
|
224
|
+
type: 'string',
|
|
225
|
+
description:
|
|
226
|
+
'Explains why the search is disabled. With isDisabled, shows a tooltip on hover/keyboard focus and keeps the input focusable via aria-disabled (input stays blocked). Use this instead of wrapping a disabled PowerSearch in Tooltip — disabled controls swallow the hover events an external Tooltip needs.',
|
|
227
|
+
},
|
|
215
228
|
{
|
|
216
229
|
name: 'status',
|
|
217
230
|
type: 'InputStatus',
|
|
@@ -269,6 +282,7 @@ export const docsZh = {
|
|
|
269
282
|
{ guidance: true, description: 'Define clear, descriptive field names and aliases so users can quickly find the filter they need.' },
|
|
270
283
|
{ guidance: true, description: 'Provide a result count to give users feedback on how their filters affect the data set.' },
|
|
271
284
|
{ guidance: false, description: 'Use PowerSearch for simple keyword searches; a standard text input is more appropriate for single-field lookups.' },
|
|
285
|
+
{ guidance: false, description: 'Wrap a disabled PowerSearch in Tooltip to explain why it is disabled; disabled controls swallow the hover events the wrapper needs. Use the disabledMessage prop instead.' },
|
|
272
286
|
],
|
|
273
287
|
},
|
|
274
288
|
};
|
|
@@ -284,6 +298,7 @@ export const docsDense = {
|
|
|
284
298
|
{ guidance: true, description: 'Define clear, descriptive field names and aliases so users can quickly find the filter they need.' },
|
|
285
299
|
{ guidance: true, description: 'Provide a result count to give users feedback on how their filters affect the data set.' },
|
|
286
300
|
{ guidance: false, description: 'Use PowerSearch for simple keyword searches; a standard text input is more appropriate for single-field lookups.' },
|
|
301
|
+
{ guidance: false, description: 'Wrap a disabled PowerSearch in Tooltip to explain why it is disabled; disabled controls swallow the hover events the wrapper needs. Use the disabledMessage prop instead.' },
|
|
287
302
|
],
|
|
288
303
|
},
|
|
289
304
|
propDescriptions: {
|