@mortenbrudvik/waveui 0.7.0 → 0.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +395 -132
- package/dist/components/button/Button.cjs +1 -1
- package/dist/components/button/Button.cjs.map +1 -1
- package/dist/components/button/Button.mjs +36 -35
- package/dist/components/button/Button.mjs.map +1 -1
- package/dist/components/button/Button.slots.cjs +1 -1
- package/dist/components/button/Button.slots.cjs.map +1 -1
- package/dist/components/button/Button.slots.mjs +31 -21
- package/dist/components/button/Button.slots.mjs.map +1 -1
- package/dist/components/button/CompoundButton.cjs +1 -1
- package/dist/components/button/CompoundButton.cjs.map +1 -1
- package/dist/components/button/CompoundButton.mjs +31 -29
- package/dist/components/button/CompoundButton.mjs.map +1 -1
- package/dist/components/button/Link.cjs +1 -1
- package/dist/components/button/Link.cjs.map +1 -1
- package/dist/components/button/Link.mjs +24 -23
- package/dist/components/button/Link.mjs.map +1 -1
- package/dist/components/button/MenuButton.cjs +1 -1
- package/dist/components/button/MenuButton.cjs.map +1 -1
- package/dist/components/button/MenuButton.mjs +29 -28
- package/dist/components/button/MenuButton.mjs.map +1 -1
- package/dist/components/button/SplitButton.cjs +1 -1
- package/dist/components/button/SplitButton.cjs.map +1 -1
- package/dist/components/button/SplitButton.mjs +46 -45
- package/dist/components/button/SplitButton.mjs.map +1 -1
- package/dist/components/button/ToggleButton.cjs +1 -1
- package/dist/components/button/ToggleButton.cjs.map +1 -1
- package/dist/components/button/ToggleButton.mjs +38 -35
- package/dist/components/button/ToggleButton.mjs.map +1 -1
- package/dist/components/button/Toolbar.cjs +1 -1
- package/dist/components/button/Toolbar.cjs.map +1 -1
- package/dist/components/button/Toolbar.mjs +43 -42
- package/dist/components/button/Toolbar.mjs.map +1 -1
- package/dist/components/button/Toolbar.parts.cjs +1 -1
- package/dist/components/button/Toolbar.parts.cjs.map +1 -1
- package/dist/components/button/Toolbar.parts.mjs +76 -81
- package/dist/components/button/Toolbar.parts.mjs.map +1 -1
- package/dist/components/data-display/Avatar.cjs +1 -1
- package/dist/components/data-display/Avatar.cjs.map +1 -1
- package/dist/components/data-display/Avatar.mjs +72 -67
- package/dist/components/data-display/Avatar.mjs.map +1 -1
- package/dist/components/data-display/AvatarGroup.cjs +1 -1
- package/dist/components/data-display/AvatarGroup.cjs.map +1 -1
- package/dist/components/data-display/AvatarGroup.mjs +89 -88
- package/dist/components/data-display/AvatarGroup.mjs.map +1 -1
- package/dist/components/data-display/Badge.cjs +1 -1
- package/dist/components/data-display/Badge.cjs.map +1 -1
- package/dist/components/data-display/Badge.mjs +17 -16
- package/dist/components/data-display/Badge.mjs.map +1 -1
- package/dist/components/data-display/CounterBadge.cjs +1 -1
- package/dist/components/data-display/CounterBadge.cjs.map +1 -1
- package/dist/components/data-display/CounterBadge.mjs +18 -17
- package/dist/components/data-display/CounterBadge.mjs.map +1 -1
- package/dist/components/data-display/Divider.cjs +1 -1
- package/dist/components/data-display/Divider.cjs.map +1 -1
- package/dist/components/data-display/Divider.mjs +31 -30
- package/dist/components/data-display/Divider.mjs.map +1 -1
- package/dist/components/data-display/Image.cjs +1 -1
- package/dist/components/data-display/Image.cjs.map +1 -1
- package/dist/components/data-display/Image.mjs +16 -15
- package/dist/components/data-display/Image.mjs.map +1 -1
- package/dist/components/data-display/InfoLabel.cjs +1 -1
- package/dist/components/data-display/InfoLabel.cjs.map +1 -1
- package/dist/components/data-display/InfoLabel.mjs +74 -73
- package/dist/components/data-display/InfoLabel.mjs.map +1 -1
- package/dist/components/data-display/List.cjs +1 -1
- package/dist/components/data-display/List.cjs.map +1 -1
- package/dist/components/data-display/List.mjs +175 -174
- package/dist/components/data-display/List.mjs.map +1 -1
- package/dist/components/data-display/Persona.cjs +1 -1
- package/dist/components/data-display/Persona.cjs.map +1 -1
- package/dist/components/data-display/Persona.mjs +31 -29
- package/dist/components/data-display/Persona.mjs.map +1 -1
- package/dist/components/data-display/PresenceBadge.cjs +1 -1
- package/dist/components/data-display/PresenceBadge.cjs.map +1 -1
- package/dist/components/data-display/PresenceBadge.mjs +25 -24
- package/dist/components/data-display/PresenceBadge.mjs.map +1 -1
- package/dist/components/data-display/Tag.cjs +1 -1
- package/dist/components/data-display/Tag.cjs.map +1 -1
- package/dist/components/data-display/Tag.mjs +87 -82
- package/dist/components/data-display/Tag.mjs.map +1 -1
- package/dist/components/feedback/MessageBar.cjs +1 -1
- package/dist/components/feedback/MessageBar.cjs.map +1 -1
- package/dist/components/feedback/MessageBar.mjs +129 -71
- package/dist/components/feedback/MessageBar.mjs.map +1 -1
- package/dist/components/feedback/MessageBar.parts.cjs +2 -0
- package/dist/components/feedback/MessageBar.parts.cjs.map +1 -0
- package/dist/components/feedback/MessageBar.parts.mjs +84 -0
- package/dist/components/feedback/MessageBar.parts.mjs.map +1 -0
- package/dist/components/feedback/MessageBar.reflow.cjs +2 -0
- package/dist/components/feedback/MessageBar.reflow.cjs.map +1 -0
- package/dist/components/feedback/MessageBar.reflow.mjs +74 -0
- package/dist/components/feedback/MessageBar.reflow.mjs.map +1 -0
- package/dist/components/feedback/MessageBar.status.cjs +1 -1
- package/dist/components/feedback/MessageBar.status.cjs.map +1 -1
- package/dist/components/feedback/MessageBar.status.mjs +2 -1
- package/dist/components/feedback/MessageBar.status.mjs.map +1 -1
- package/dist/components/feedback/ProgressBar.cjs +1 -1
- package/dist/components/feedback/ProgressBar.cjs.map +1 -1
- package/dist/components/feedback/ProgressBar.mjs +44 -43
- package/dist/components/feedback/ProgressBar.mjs.map +1 -1
- package/dist/components/feedback/Skeleton.cjs +1 -1
- package/dist/components/feedback/Skeleton.cjs.map +1 -1
- package/dist/components/feedback/Skeleton.mjs +26 -24
- package/dist/components/feedback/Skeleton.mjs.map +1 -1
- package/dist/components/feedback/Spinner.cjs +1 -1
- package/dist/components/feedback/Spinner.cjs.map +1 -1
- package/dist/components/feedback/Spinner.mjs +32 -31
- package/dist/components/feedback/Spinner.mjs.map +1 -1
- package/dist/components/feedback/Toast.cjs +1 -1
- package/dist/components/feedback/Toast.cjs.map +1 -1
- package/dist/components/feedback/Toast.context.cjs +2 -0
- package/dist/components/feedback/Toast.context.cjs.map +1 -0
- package/dist/components/feedback/Toast.context.mjs +23 -0
- package/dist/components/feedback/Toast.context.mjs.map +1 -0
- package/dist/components/feedback/Toast.mjs +10 -342
- package/dist/components/feedback/Toast.mjs.map +1 -1
- package/dist/components/feedback/Toast.parts.cjs +2 -0
- package/dist/components/feedback/Toast.parts.cjs.map +1 -0
- package/dist/components/feedback/Toast.parts.mjs +98 -0
- package/dist/components/feedback/Toast.parts.mjs.map +1 -0
- package/dist/components/feedback/Toast.root.cjs +2 -0
- package/dist/components/feedback/Toast.root.cjs.map +1 -0
- package/dist/components/feedback/Toast.root.mjs +109 -0
- package/dist/components/feedback/Toast.root.mjs.map +1 -0
- package/dist/components/feedback/Toaster.cjs +2 -0
- package/dist/components/feedback/Toaster.cjs.map +1 -0
- package/dist/components/feedback/Toaster.mjs +564 -0
- package/dist/components/feedback/Toaster.mjs.map +1 -0
- package/dist/components/input/AlphaSlider.cjs +2 -0
- package/dist/components/input/AlphaSlider.cjs.map +1 -0
- package/dist/components/input/AlphaSlider.mjs +115 -0
- package/dist/components/input/AlphaSlider.mjs.map +1 -0
- package/dist/components/input/Checkbox.cjs +1 -1
- package/dist/components/input/Checkbox.cjs.map +1 -1
- package/dist/components/input/Checkbox.mjs +47 -46
- package/dist/components/input/Checkbox.mjs.map +1 -1
- package/dist/components/input/ColorArea.cjs +2 -0
- package/dist/components/input/ColorArea.cjs.map +1 -0
- package/dist/components/input/ColorArea.mjs +204 -0
- package/dist/components/input/ColorArea.mjs.map +1 -0
- package/dist/components/input/ColorPicker.cjs +5 -5
- package/dist/components/input/ColorPicker.cjs.map +1 -1
- package/dist/components/input/ColorPicker.mjs +142 -165
- package/dist/components/input/ColorPicker.mjs.map +1 -1
- package/dist/components/input/ColorPicker.parts.cjs +2 -0
- package/dist/components/input/ColorPicker.parts.cjs.map +1 -0
- package/dist/components/input/ColorPicker.parts.mjs +192 -0
- package/dist/components/input/ColorPicker.parts.mjs.map +1 -0
- package/dist/components/input/ColorSlider.cjs +2 -0
- package/dist/components/input/ColorSlider.cjs.map +1 -0
- package/dist/components/input/ColorSlider.mjs +138 -0
- package/dist/components/input/ColorSlider.mjs.map +1 -0
- package/dist/components/input/Combobox.cjs +1 -1
- package/dist/components/input/Combobox.cjs.map +1 -1
- package/dist/components/input/Combobox.expand.cjs +1 -1
- package/dist/components/input/Combobox.expand.cjs.map +1 -1
- package/dist/components/input/Combobox.expand.mjs +9 -9
- package/dist/components/input/Combobox.expand.mjs.map +1 -1
- package/dist/components/input/Combobox.mjs +90 -85
- package/dist/components/input/Combobox.mjs.map +1 -1
- package/dist/components/input/DatePicker.cjs +1 -1
- package/dist/components/input/DatePicker.cjs.map +1 -1
- package/dist/components/input/DatePicker.mjs +186 -185
- package/dist/components/input/DatePicker.mjs.map +1 -1
- package/dist/components/input/Dropdown.cjs +1 -1
- package/dist/components/input/Dropdown.cjs.map +1 -1
- package/dist/components/input/Dropdown.mjs +71 -68
- package/dist/components/input/Dropdown.mjs.map +1 -1
- package/dist/components/input/Field.cjs +1 -1
- package/dist/components/input/Field.cjs.map +1 -1
- package/dist/components/input/Field.mjs +113 -112
- package/dist/components/input/Field.mjs.map +1 -1
- package/dist/components/input/Input.cjs +1 -1
- package/dist/components/input/Input.cjs.map +1 -1
- package/dist/components/input/Input.mjs +55 -54
- package/dist/components/input/Input.mjs.map +1 -1
- package/dist/components/input/Label.cjs +1 -1
- package/dist/components/input/Label.cjs.map +1 -1
- package/dist/components/input/Label.mjs +12 -11
- package/dist/components/input/Label.mjs.map +1 -1
- package/dist/components/input/Option.cjs +1 -1
- package/dist/components/input/Option.cjs.map +1 -1
- package/dist/components/input/Option.mjs +100 -98
- package/dist/components/input/Option.mjs.map +1 -1
- package/dist/components/input/RadioGroup.cjs +1 -1
- package/dist/components/input/RadioGroup.cjs.map +1 -1
- package/dist/components/input/RadioGroup.mjs +89 -88
- package/dist/components/input/RadioGroup.mjs.map +1 -1
- package/dist/components/input/Rating.cjs +1 -1
- package/dist/components/input/Rating.cjs.map +1 -1
- package/dist/components/input/Rating.mjs +110 -109
- package/dist/components/input/Rating.mjs.map +1 -1
- package/dist/components/input/SearchBox.cjs +1 -1
- package/dist/components/input/SearchBox.cjs.map +1 -1
- package/dist/components/input/SearchBox.mjs +118 -119
- package/dist/components/input/SearchBox.mjs.map +1 -1
- package/dist/components/input/Select.cjs +1 -1
- package/dist/components/input/Select.cjs.map +1 -1
- package/dist/components/input/Select.mjs +25 -24
- package/dist/components/input/Select.mjs.map +1 -1
- package/dist/components/input/Slider.cjs +1 -1
- package/dist/components/input/Slider.cjs.map +1 -1
- package/dist/components/input/Slider.mjs +47 -46
- package/dist/components/input/Slider.mjs.map +1 -1
- package/dist/components/input/SpinButton.cjs +1 -1
- package/dist/components/input/SpinButton.cjs.map +1 -1
- package/dist/components/input/SpinButton.mjs +76 -75
- package/dist/components/input/SpinButton.mjs.map +1 -1
- package/dist/components/input/SwatchPicker.cjs +1 -1
- package/dist/components/input/SwatchPicker.cjs.map +1 -1
- package/dist/components/input/SwatchPicker.mjs +38 -37
- package/dist/components/input/SwatchPicker.mjs.map +1 -1
- package/dist/components/input/Switch.cjs +1 -1
- package/dist/components/input/Switch.cjs.map +1 -1
- package/dist/components/input/Switch.mjs +65 -64
- package/dist/components/input/Switch.mjs.map +1 -1
- package/dist/components/input/TagPicker.cjs +1 -1
- package/dist/components/input/TagPicker.cjs.map +1 -1
- package/dist/components/input/TagPicker.mjs +161 -157
- package/dist/components/input/TagPicker.mjs.map +1 -1
- package/dist/components/input/Textarea.cjs +1 -1
- package/dist/components/input/Textarea.cjs.map +1 -1
- package/dist/components/input/Textarea.mjs +24 -23
- package/dist/components/input/Textarea.mjs.map +1 -1
- package/dist/components/input/TimePicker.cjs +1 -1
- package/dist/components/input/TimePicker.cjs.map +1 -1
- package/dist/components/input/TimePicker.mjs +202 -199
- package/dist/components/input/TimePicker.mjs.map +1 -1
- package/dist/components/input/colorName.cjs +2 -0
- package/dist/components/input/colorName.cjs.map +1 -0
- package/dist/components/input/colorName.mjs +30 -0
- package/dist/components/input/colorName.mjs.map +1 -0
- package/dist/components/input/colorUtils.cjs +1 -1
- package/dist/components/input/colorUtils.cjs.map +1 -1
- package/dist/components/input/colorUtils.mjs +154 -56
- package/dist/components/input/colorUtils.mjs.map +1 -1
- package/dist/components/layout/Accordion.cjs +1 -1
- package/dist/components/layout/Accordion.cjs.map +1 -1
- package/dist/components/layout/Accordion.mjs +130 -129
- package/dist/components/layout/Accordion.mjs.map +1 -1
- package/dist/components/layout/Card.cjs +1 -1
- package/dist/components/layout/Card.cjs.map +1 -1
- package/dist/components/layout/Card.mjs +78 -77
- package/dist/components/layout/Card.mjs.map +1 -1
- package/dist/components/layout/Carousel.cjs +1 -1
- package/dist/components/layout/Carousel.cjs.map +1 -1
- package/dist/components/layout/Carousel.mjs +111 -110
- package/dist/components/layout/Carousel.mjs.map +1 -1
- package/dist/components/layout/Flex.cjs +1 -1
- package/dist/components/layout/Flex.cjs.map +1 -1
- package/dist/components/layout/Flex.mjs +22 -21
- package/dist/components/layout/Flex.mjs.map +1 -1
- package/dist/components/layout/Grid.cjs +1 -1
- package/dist/components/layout/Grid.cjs.map +1 -1
- package/dist/components/layout/Grid.mjs +19 -18
- package/dist/components/layout/Grid.mjs.map +1 -1
- package/dist/components/layout/Overflow.cjs +1 -1
- package/dist/components/layout/Overflow.cjs.map +1 -1
- package/dist/components/layout/Overflow.mjs +92 -91
- package/dist/components/layout/Overflow.mjs.map +1 -1
- package/dist/components/layout/Stack.cjs +1 -1
- package/dist/components/layout/Stack.cjs.map +1 -1
- package/dist/components/layout/Stack.mjs +14 -13
- package/dist/components/layout/Stack.mjs.map +1 -1
- package/dist/components/layout/TabList.cjs +1 -1
- package/dist/components/layout/TabList.cjs.map +1 -1
- package/dist/components/layout/TabList.mjs +118 -117
- package/dist/components/layout/TabList.mjs.map +1 -1
- package/dist/components/layout/Tree.cjs +1 -1
- package/dist/components/layout/Tree.cjs.map +1 -1
- package/dist/components/layout/Tree.context.cjs +2 -0
- package/dist/components/layout/Tree.context.cjs.map +1 -0
- package/dist/components/layout/Tree.context.mjs +33 -0
- package/dist/components/layout/Tree.context.mjs.map +1 -0
- package/dist/components/layout/Tree.core.cjs +2 -0
- package/dist/components/layout/Tree.core.cjs.map +1 -0
- package/dist/components/layout/Tree.core.mjs +416 -0
- package/dist/components/layout/Tree.core.mjs.map +1 -0
- package/dist/components/layout/Tree.itemPersonaLayout.cjs +2 -0
- package/dist/components/layout/Tree.itemPersonaLayout.cjs.map +1 -0
- package/dist/components/layout/Tree.itemPersonaLayout.mjs +46 -0
- package/dist/components/layout/Tree.itemPersonaLayout.mjs.map +1 -0
- package/dist/components/layout/Tree.mjs +7 -215
- package/dist/components/layout/Tree.mjs.map +1 -1
- package/dist/components/layout/Tree.selection.cjs +2 -0
- package/dist/components/layout/Tree.selection.cjs.map +1 -0
- package/dist/components/layout/Tree.selection.mjs +73 -0
- package/dist/components/layout/Tree.selection.mjs.map +1 -0
- package/dist/components/navigation/Breadcrumb.cjs +1 -1
- package/dist/components/navigation/Breadcrumb.cjs.map +1 -1
- package/dist/components/navigation/Breadcrumb.mjs +76 -75
- package/dist/components/navigation/Breadcrumb.mjs.map +1 -1
- package/dist/components/navigation/Menu.group.cjs +1 -1
- package/dist/components/navigation/Menu.group.cjs.map +1 -1
- package/dist/components/navigation/Menu.group.mjs +39 -37
- package/dist/components/navigation/Menu.group.mjs.map +1 -1
- package/dist/components/navigation/Menu.items.cjs +1 -1
- package/dist/components/navigation/Menu.items.cjs.map +1 -1
- package/dist/components/navigation/Menu.items.mjs +67 -61
- package/dist/components/navigation/Menu.items.mjs.map +1 -1
- package/dist/components/navigation/Menu.link.cjs +1 -1
- package/dist/components/navigation/Menu.link.cjs.map +1 -1
- package/dist/components/navigation/Menu.link.mjs +34 -28
- package/dist/components/navigation/Menu.link.mjs.map +1 -1
- package/dist/components/navigation/Menu.popover.cjs +1 -1
- package/dist/components/navigation/Menu.popover.cjs.map +1 -1
- package/dist/components/navigation/Menu.popover.mjs +110 -109
- package/dist/components/navigation/Menu.popover.mjs.map +1 -1
- package/dist/components/navigation/Menu.root.cjs +1 -1
- package/dist/components/navigation/Menu.root.cjs.map +1 -1
- package/dist/components/navigation/Menu.root.mjs +171 -170
- package/dist/components/navigation/Menu.root.mjs.map +1 -1
- package/dist/components/navigation/Menu.selectable.cjs +1 -1
- package/dist/components/navigation/Menu.selectable.cjs.map +1 -1
- package/dist/components/navigation/Menu.selectable.mjs +85 -63
- package/dist/components/navigation/Menu.selectable.mjs.map +1 -1
- package/dist/components/navigation/Menu.splitGroup.cjs +1 -1
- package/dist/components/navigation/Menu.splitGroup.cjs.map +1 -1
- package/dist/components/navigation/Menu.splitGroup.mjs +27 -26
- package/dist/components/navigation/Menu.splitGroup.mjs.map +1 -1
- package/dist/components/navigation/Menu.trigger.cjs +1 -1
- package/dist/components/navigation/Menu.trigger.cjs.map +1 -1
- package/dist/components/navigation/Menu.trigger.mjs +6 -6
- package/dist/components/navigation/Nav.cjs +1 -1
- package/dist/components/navigation/Nav.cjs.map +1 -1
- package/dist/components/navigation/Nav.mjs +170 -155
- package/dist/components/navigation/Nav.mjs.map +1 -1
- package/dist/components/navigation/Pagination.cjs +1 -1
- package/dist/components/navigation/Pagination.cjs.map +1 -1
- package/dist/components/navigation/Pagination.mjs +73 -65
- package/dist/components/navigation/Pagination.mjs.map +1 -1
- package/dist/components/navigation/Stepper.cjs +1 -1
- package/dist/components/navigation/Stepper.cjs.map +1 -1
- package/dist/components/navigation/Stepper.mjs +110 -109
- package/dist/components/navigation/Stepper.mjs.map +1 -1
- package/dist/components/overlays/Dialog.cjs +1 -1
- package/dist/components/overlays/Dialog.cjs.map +1 -1
- package/dist/components/overlays/Dialog.mjs +109 -108
- package/dist/components/overlays/Dialog.mjs.map +1 -1
- package/dist/components/overlays/Drawer.cjs +1 -1
- package/dist/components/overlays/Drawer.cjs.map +1 -1
- package/dist/components/overlays/Drawer.mjs +110 -109
- package/dist/components/overlays/Drawer.mjs.map +1 -1
- package/dist/components/overlays/Popover.cjs +1 -1
- package/dist/components/overlays/Popover.cjs.map +1 -1
- package/dist/components/overlays/Popover.mjs +229 -227
- package/dist/components/overlays/Popover.mjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.cjs +1 -1
- package/dist/components/overlays/TeachingPopover.cjs.map +1 -1
- package/dist/components/overlays/TeachingPopover.mjs +41 -37
- package/dist/components/overlays/TeachingPopover.mjs.map +1 -1
- package/dist/components/overlays/Tooltip.cjs +1 -1
- package/dist/components/overlays/Tooltip.cjs.map +1 -1
- package/dist/components/overlays/Tooltip.mjs +87 -86
- package/dist/components/overlays/Tooltip.mjs.map +1 -1
- package/dist/components/portal/Portal.cjs +1 -1
- package/dist/components/portal/Portal.cjs.map +1 -1
- package/dist/components/portal/Portal.mjs +33 -32
- package/dist/components/portal/Portal.mjs.map +1 -1
- package/dist/components/provider/WaveProvider.cjs +1 -1
- package/dist/components/provider/WaveProvider.cjs.map +1 -1
- package/dist/components/provider/WaveProvider.mjs +31 -30
- package/dist/components/provider/WaveProvider.mjs.map +1 -1
- package/dist/components/table/DataGrid.cjs +1 -1
- package/dist/components/table/DataGrid.cjs.map +1 -1
- package/dist/components/table/DataGrid.mjs +228 -227
- package/dist/components/table/DataGrid.mjs.map +1 -1
- package/dist/components/table/Table.cjs +1 -1
- package/dist/components/table/Table.cjs.map +1 -1
- package/dist/components/table/Table.mjs +60 -59
- package/dist/components/table/Table.mjs.map +1 -1
- package/dist/components/typography/Text.cjs +1 -1
- package/dist/components/typography/Text.cjs.map +1 -1
- package/dist/components/typography/Text.mjs +12 -11
- package/dist/components/typography/Text.mjs.map +1 -1
- package/dist/hooks/useMediaQuery.cjs +2 -0
- package/dist/hooks/useMediaQuery.cjs.map +1 -0
- package/dist/hooks/useMediaQuery.mjs +20 -0
- package/dist/hooks/useMediaQuery.mjs.map +1 -0
- package/dist/hooks/usePrefersReducedMotion.cjs +1 -1
- package/dist/hooks/usePrefersReducedMotion.cjs.map +1 -1
- package/dist/hooks/usePrefersReducedMotion.mjs +4 -18
- package/dist/hooks/usePrefersReducedMotion.mjs.map +1 -1
- package/dist/hooks/useRovingTabIndex.cjs +1 -1
- package/dist/hooks/useRovingTabIndex.cjs.map +1 -1
- package/dist/hooks/useRovingTabIndex.mjs +3 -3
- package/dist/hooks/useRovingTabIndex.mjs.map +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +2089 -102
- package/dist/index.d.ts +2089 -102
- package/dist/index.mjs +99 -87
- package/dist/lib/classNames.cjs +2 -0
- package/dist/lib/classNames.cjs.map +1 -0
- package/dist/lib/classNames.mjs +415 -0
- package/dist/lib/classNames.mjs.map +1 -0
- package/dist/lib/color.cjs +2 -0
- package/dist/lib/color.cjs.map +1 -0
- package/dist/lib/color.mjs +86 -0
- package/dist/lib/color.mjs.map +1 -0
- package/dist/lib/globalRegistry.cjs.map +1 -1
- package/dist/lib/globalRegistry.mjs.map +1 -1
- package/dist/lib/toaster.cjs +2 -0
- package/dist/lib/toaster.cjs.map +1 -0
- package/dist/lib/toaster.mjs +77 -0
- package/dist/lib/toaster.mjs.map +1 -0
- package/dist/styles.css +1 -1
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MessageBar.mjs","names":["React","tintClasses","DEFAULT_DISMISS_LABEL","BUTTON_ONLY_KEYS","NAMING_KEYS","HANDLER_KEY","dismissContentClassName","noop","defaultDismissContent","DismissIcon","isButtonType","type","Button","defaultDismiss","resolveDismiss","dismiss","element","isElementOfType","buttonProps","key","value","BUTTON_OWN_PROP_KEYS","isWaveButton","markup","children","materialiseSlotContent","icon","iconNode","slotRendersContent","renderSlot","placeButtonIcon","hasTextLabel","resolved","resolveSlot","asButton","Component","isButtonObject","props","contentProps","ContentTag","elementProps","cn","inner","slotWrapsDefaultContent","MessageBar","rest","iconClassName","STATUS_ICON_COLOR","status","renderedIcon","StatusIcon","dismissParts","onDismiss","dismissWarning","warnOnce","slotRef","slotButtonProps","hasOwnName","checksContent","literalTextLabel","labelTarget","setLabelTarget","subscribeToContent","observeTextLabel","onChange","contentHasTextLabel","hasRenderedTextLabel","namedByContent","dismissRef","useMergedRefs","renderedDismiss","mergeProps","focusRing","mergedAriaDisabledClasses","MERGED_DISABLED_FOCUSABLE_PROPS","STATUS_BORDER","className","StatusText","getStatusLabel","statusLabel"],"sources":["../../../src/components/feedback/MessageBar.tsx"],"sourcesContent":["import * as React from 'react';\nimport { isElementOfType } from '../../lib/children';\nimport { cn } from '../../lib/cn';\nimport { warnOnce } from '../../lib/dev';\nimport { DismissIcon } from '../../lib/icons';\nimport { hasRenderedTextLabel, hasTextLabel, observeTextLabel } from '../../lib/labelInName';\nimport { mergeProps } from '../../lib/mergeProps';\nimport {\n materialiseSlotContent,\n renderSlot,\n resolveSlot,\n slotRendersContent,\n slotWrapsDefaultContent,\n} from '../../lib/slot';\nimport { focusRing } from '../../lib/styles';\nimport type { Status, Slot, SlotObject } from '../../lib/types';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { Button } from '../button/Button';\nimport {\n BUTTON_OWN_PROP_KEYS,\n MERGED_DISABLED_FOCUSABLE_PROPS,\n mergedAriaDisabledClasses,\n placeButtonIcon,\n} from '../button/Button.slots';\nimport {\n STATUS_BORDER,\n STATUS_ICON_COLOR,\n StatusIcon,\n StatusText,\n getStatusLabel,\n} from './MessageBar.status';\n\n/** Properties for the MessageBar component. */\nexport interface MessageBarProps extends React.HTMLAttributes<HTMLDivElement> {\n /** Status level controlling the color, icon, status text and role of the message bar.\n * `warning` and `error` render `role=\"alert\"`, `info` and `success` `role=\"status\"` (a consumer\n * `role` wins).\n * @default 'info'\n */\n status?: Status;\n /**\n * Visually hidden text read before the message so screen-reader users hear the severity\n * (`'Info:'`, `'Success:'`, `'Warning:'`, `'Error:'` by default). Pass a translation for other\n * languages, or `''` when the message text already states the severity.\n */\n statusLabel?: string;\n /**\n * Called when the dismiss button is activated. Passing it renders the dismiss button (unless\n * `dismiss` is `null`).\n */\n onDismiss?: () => void;\n /**\n * Custom status icon, rendered decoratively (`aria-hidden=\"true\"`, a slot object can override\n * it) in the status color. `null` renders no icon.\n */\n icon?: Slot<'span'>;\n /**\n * Content of the dismiss button (replaces the default dismiss icon). It always renders **inside**\n * the built-in `<button type=\"button\" aria-label=\"Dismiss\">`, which calls `onDismiss`; passing\n * content shows the dismiss button even without `onDismiss`. `null` is the only value that hides\n * the button. A boolean counts as no slot, so the conditional idiom\n * `dismiss={useBrandIcon && <BrandCloseIcon />}` keeps the default button: the default icon with\n * `onDismiss`, no button without it. Content that renders nothing (`''`, or an array or Fragment\n * of only `null`, `false`, `true` and `''`, also as the children of a slot object or a merged\n * button) keeps the default icon, so the button is never empty; a slot object that renders a\n * component or a void element (`{ as: CloseIcon }`, `{ as: 'img', src, alt: '' }`) or sets\n * `dangerouslySetInnerHTML` is the icon itself. The content is\n * decorative (`aria-hidden`), so the button keeps the name \"Dismiss\": when the content is\n * visible text, pass a slot object whose `aria-label` matches it\n * (`{ children: 'Close', 'aria-label': 'Close' }`) so the name contains the visible label. An\n * `aria-label`, `aria-labelledby` or `title` on a slot object names the button instead of\n * \"Dismiss\".\n *\n * A `<button>` element or a Wave `Button` passed here is not nested: its props are merged into\n * the built-in button (its `onClick` runs first and can call `preventDefault()` to cancel\n * `onDismiss`; its `aria-label` and an explicit `type` win over the defaults) and its content\n * (children, or `dangerouslySetInnerHTML` markup) is used as is, with a development warning.\n * A Wave `Button`'s own props are not attributes: its `icon` becomes decorative content before\n * its children (after them with `iconPosition=\"after\"`), `disabledFocusable` makes the dismiss\n * button unavailable but focusable as on the Button (`onDismiss` is not called), and\n * `appearance` and `size` are ignored.\n * When the rendered content has a text label (at least two letters or digits:\n * `<button>Close</button>`, or text rendered by a component such as a translation), that text\n * names the button, as in 0.4. An icon, a lone character (`X`, `×`,\n * `+`: a symbol, not a label) and text that is `aria-hidden` or `hidden` keep the name\n * \"Dismiss\". Text hidden only with CSS still counts as the label: a responsive label such as\n * `<span className=\"hidden sm:inline\">Close</span>` drops the default name, so the button has\n * no name wherever that text is not displayed. Give such a button an explicit `aria-label`\n * (`<button aria-label=\"Close\">…</button>`). An `aria-label`, `aria-labelledby` or `title` on\n * the element names the button.\n *\n * The 0.4 button-object form (`{ as: 'button', onClick, … }`, `{ as: Button, … }` or an object\n * with button props) is **deprecated**: its button props (`type` included), `className` and\n * `style` are merged the same way, and a Wave Button's own props apply as for the element form.\n * Pass icon content instead, e.g. `dismiss={<CloseIcon />}`.\n */\n dismiss?: Slot<'span'> | SlotObject<'button'>;\n /** Message content to display. */\n children: React.ReactNode;\n /** Ref to the root `<div>`. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\nconst tintClasses: Record<Status, string> = {\n info: 'bg-info-tint',\n success: 'bg-success-tint',\n warning: 'bg-warning-tint',\n error: 'bg-error-tint',\n};\n\ntype UnknownProps = Record<string, unknown>;\n\n/** Name of the dismiss button when nothing else names it. */\nconst DEFAULT_DISMISS_LABEL = 'Dismiss';\n\n/** Attributes that only make sense on the dismiss `<button>` itself. */\nconst BUTTON_ONLY_KEYS: ReadonlySet<string> = new Set([\n 'type',\n 'disabled',\n 'autoFocus',\n 'form',\n 'formAction',\n 'formEncType',\n 'formMethod',\n 'formNoValidate',\n 'formTarget',\n 'name',\n 'value',\n 'popoverTarget',\n 'popoverTargetAction',\n]);\n\n/**\n * Attributes that name the dismiss button. On a slot object they go to the button (its content is\n * decorative); on the merged button, any of them replaces the default `aria-label`.\n */\nconst NAMING_KEYS: ReadonlySet<string> = new Set(['aria-label', 'aria-labelledby', 'title']);\n\nconst HANDLER_KEY = /^on[A-Z]/;\n\nconst dismissContentClassName = 'inline-flex items-center justify-center';\n\ninterface DismissParts {\n /** Props merged onto the wired dismiss button. */\n buttonProps: UnknownProps;\n /** What renders inside the dismiss button. */\n content: React.ReactNode;\n /**\n * `true` when the content is rendered as is (a merged `<button>`/`Button`), so a text label in it\n * names the button (C-SLOTS naming, WCAG 2.5.3 Label in Name); `false` when the content is\n * decorative (`aria-hidden`).\n */\n contentMayName: boolean;\n /**\n * Whether the content's literal children contain a text label. Used for the server render and\n * the first client render; after mount, the rendered button's text decides (see\n * {@link hasRenderedTextLabel}).\n */\n literalTextLabel: boolean;\n /**\n * Whether a merged Wave `Button` set `disabledFocusable`: the dismiss button is then unavailable\n * but focusable, as the Button would be.\n */\n disabledFocusable: boolean;\n /** Which development warning the slot needs. */\n warning: 'button-element' | 'button-object' | null;\n}\n\nconst noop = () => {};\n\n/** The decorative default dismiss glyph. */\nfunction defaultDismissContent(): React.ReactNode {\n return <DismissIcon />;\n}\n\nfunction isButtonType(type: unknown): boolean {\n return type === 'button' || type === Button;\n}\n\n/** The dismiss button without a slot: the default icon and name. */\nfunction defaultDismiss(): DismissParts {\n return {\n buttonProps: {},\n content: defaultDismissContent(),\n contentMayName: false,\n literalTextLabel: false,\n disabledFocusable: false,\n warning: null,\n };\n}\n\n/**\n * Splits the `dismiss` slot into props for the wired dismiss button and the content rendered\n * inside it (C-SLOTS dismiss semantics). `null` means: no dismiss button. A boolean is no slot\n * (the default dismiss button), and content that renders nothing keeps the default icon.\n */\nfunction resolveDismiss(dismiss: MessageBarProps['dismiss']): DismissParts | null {\n if (dismiss === null) return null;\n if (dismiss === undefined || typeof dismiss === 'boolean') return defaultDismiss();\n\n // A merged `<button>`/`Button` keeps its content accessible (as in 0.4): a text label names the\n // button, anything else (an icon, a lone character such as `X` or `×`) gets the default name.\n // The type is compared through `isElementOfType`, so a Button written in a Server Component\n // (a lazy client reference) is merged too.\n const element = dismiss as React.ReactNode;\n if (isElementOfType<UnknownProps>(element, 'button', Button)) {\n const buttonProps: UnknownProps = {};\n for (const [key, value] of Object.entries(element.props)) {\n if (\n key !== 'children' &&\n key !== 'dangerouslySetInnerHTML' &&\n !BUTTON_OWN_PROP_KEYS.has(key)\n ) {\n buttonProps[key] = value;\n }\n }\n const isWaveButton = isElementOfType(element, Button);\n // A generator is read once by the check; its items are what renders (and names the button).\n // Markup of the merged button (`dangerouslySetInnerHTML`) is its content as well, rendered in\n // a span inside the dismiss button (the button itself also holds the icon).\n const markup = element.props.dangerouslySetInnerHTML as\n React.HTMLAttributes<HTMLElement>['dangerouslySetInnerHTML'] | undefined;\n const children =\n markup != null ? (\n <span className={dismissContentClassName} dangerouslySetInnerHTML={markup} />\n ) : (\n materialiseSlotContent(element.props.children)\n );\n // Wave Button's icon becomes decorative content before its children (after them with\n // `iconPosition=\"after\"`).\n const icon = element.props.icon as Slot<'span'>;\n const iconNode =\n isWaveButton && slotRendersContent(icon)\n ? renderSlot(icon, 'span', dismissContentClassName, { 'aria-hidden': true })\n : null;\n const content =\n iconNode || slotRendersContent(children)\n ? placeButtonIcon(iconNode, children, element.props.iconPosition)\n : defaultDismissContent();\n return {\n buttonProps,\n content,\n contentMayName: true,\n literalTextLabel: hasTextLabel(children),\n disabledFocusable: isWaveButton && Boolean(element.props.disabledFocusable),\n warning: 'button-element',\n };\n }\n\n // Everything else is classified by the slot system (F2): shorthand content resolves to the\n // default `span` with no attributes; a slot object resolves to its element and attributes.\n const resolved = resolveSlot(dismiss as Slot<'span'>, 'span');\n if (!resolved) return defaultDismiss();\n const { Component, props, children } = resolved;\n const asButton = isButtonType(Component);\n const isButtonObject =\n asButton ||\n Object.keys(props).some((key) => BUTTON_ONLY_KEYS.has(key) || HANDLER_KEY.test(key));\n const buttonProps: UnknownProps = {};\n const contentProps: UnknownProps = {};\n let iconNode: React.ReactNode = null;\n for (const [key, value] of Object.entries(props)) {\n if (Component === Button && BUTTON_OWN_PROP_KEYS.has(key)) {\n // Wave Button's own props are not attributes: `icon`, `iconPosition` and\n // `disabledFocusable` are applied below, the others (`appearance`, `size`) are dropped.\n if (key === 'icon' && slotRendersContent(value)) {\n iconNode = renderSlot(value as Slot<'span'>, 'span', dismissContentClassName, {\n 'aria-hidden': true,\n });\n }\n } else if (\n BUTTON_ONLY_KEYS.has(key) ||\n HANDLER_KEY.test(key) ||\n NAMING_KEYS.has(key) ||\n // 0.4 rendered the object as the button itself: its className, style and ref stay there.\n (isButtonObject && (key === 'className' || key === 'style' || key === 'ref'))\n ) {\n buttonProps[key] = value;\n } else {\n contentProps[key] = value;\n }\n }\n\n // The content element: the object's own element, or a span for the button-object form. An\n // object whose children render nothing styles the default icon\n // (e.g. `{ className: 'text-error' }`), unless its element is the icon itself.\n const ContentTag: React.ElementType = asButton ? 'span' : Component;\n const elementProps = {\n 'aria-hidden': true,\n ...contentProps,\n className: cn(dismissContentClassName, contentProps.className as string | undefined),\n };\n let inner: React.ReactNode = null;\n if (iconNode || slotRendersContent(children)) {\n inner = placeButtonIcon(iconNode, children, Component === Button && props.iconPosition);\n } else if (slotWrapsDefaultContent(ContentTag, { ...contentProps, children })) {\n inner = defaultDismissContent();\n }\n return {\n buttonProps,\n content:\n inner === null\n ? React.createElement(ContentTag, elementProps)\n : React.createElement(ContentTag, elementProps, inner),\n contentMayName: false,\n literalTextLabel: false,\n disabledFocusable: Component === Button && Boolean(props.disabledFocusable),\n warning: isButtonObject ? 'button-object' : null,\n };\n}\n\n/**\n * An inline message that tells the user about the state of a page or task: a status icon, a\n * visually hidden status label (\"Warning:\"), the message and an optional dismiss button.\n *\n * - The status sets the tint, the logical start border, the icon and the role (`alert` for\n * `warning`/`error`, `status` otherwise). Screen readers hear the severity through `statusLabel`.\n * - The dismiss button is always the MessageBar's own `<button>` wired to `onDismiss`\n * (`type=\"button\"` unless a merged button slot sets its own `type`); the `dismiss` slot only\n * replaces its content (see {@link MessageBarProps.dismiss}).\n *\n * @example\n * <MessageBar status=\"warning\" onDismiss={() => setVisible(false)}>\n * Your subscription expires in 3 days.\n * </MessageBar>\n */\nexport const MessageBar = ({\n status = 'info',\n statusLabel,\n onDismiss,\n icon,\n dismiss,\n children,\n className,\n ref,\n ...rest\n}: MessageBarProps) => {\n const iconClassName = cn('mt-0.5 inline-flex shrink-0', STATUS_ICON_COLOR[status]);\n const renderedIcon =\n icon !== undefined ? (\n renderSlot(icon, 'span', iconClassName, { 'aria-hidden': true })\n ) : (\n <span aria-hidden=\"true\" className={iconClassName}>\n <StatusIcon status={status} size={20} />\n </span>\n );\n\n // A boolean `dismiss` is no slot (`dismiss={cond && <CloseIcon />}`): only `onDismiss` shows it.\n const showDismiss =\n onDismiss !== undefined || (dismiss !== undefined && typeof dismiss !== 'boolean');\n const dismissParts = showDismiss ? resolveDismiss(dismiss) : null;\n const dismissWarning = dismissParts?.warning ?? null;\n React.useEffect(() => {\n if (dismissWarning === 'button-element') {\n warnOnce(\n 'MessageBar:dismiss-button-element',\n 'MessageBar: `dismiss` received a button element; its props were merged into the built-in dismiss button (buttons cannot be nested). Pass icon content instead, e.g. `dismiss={<CloseIcon />}`, and use `onDismiss`.',\n );\n } else if (dismissWarning === 'button-object') {\n warnOnce(\n 'MessageBar:dismiss-button-object',\n 'MessageBar: the button-object form of `dismiss` is deprecated and will be removed in 1.0; its button props were merged into the built-in dismiss button. Pass icon content instead, e.g. `dismiss={<CloseIcon />}`, and use `onDismiss`.',\n );\n }\n }, [dismissWarning]);\n\n // The slot's ref joins ours through a stable merged ref (never a new callback per render).\n const { ref: slotRef, ...slotButtonProps } = dismissParts?.buttonProps ?? {};\n const hasOwnName = Object.keys(slotButtonProps).some(\n (key) => NAMING_KEYS.has(key) && slotButtonProps[key] != null,\n );\n\n // C-SLOTS naming (WCAG 2.5.3 Label in Name): a merged button's content names it when it renders\n // a text label (at least two letters or digits; a lone `X` or `×` is a glyph), and the default\n // `aria-label` would hide that label. The literal children decide on the server and on the first\n // render; after mount, the rendered button's text does (text from components, e.g. translations,\n // and later changes).\n const checksContent = dismissParts !== null && dismissParts.contentMayName && !hasOwnName;\n const literalTextLabel = dismissParts?.literalTextLabel ?? false;\n const [labelTarget, setLabelTarget] = React.useState<HTMLButtonElement | null>(null);\n const subscribeToContent = React.useCallback(\n (onChange: () => void) => (labelTarget ? observeTextLabel(labelTarget, onChange) : noop),\n [labelTarget],\n );\n const contentHasTextLabel = React.useSyncExternalStore(\n subscribeToContent,\n () => (labelTarget ? hasRenderedTextLabel(labelTarget) : literalTextLabel),\n () => literalTextLabel,\n );\n const namedByContent = checksContent && contentHasTextLabel;\n const dismissRef = useMergedRefs<HTMLButtonElement>(\n slotRef as React.Ref<HTMLButtonElement> | undefined,\n checksContent ? setLabelTarget : undefined,\n );\n\n let renderedDismiss: React.ReactNode = null;\n if (dismissParts) {\n const buttonProps = mergeProps(\n {\n 'aria-label': hasOwnName || namedByContent ? undefined : DEFAULT_DISMISS_LABEL,\n onClick: () => onDismiss?.(),\n className: cn(\n 'ms-auto inline-flex shrink-0 cursor-pointer items-center justify-center rounded border-none bg-transparent p-1 text-muted-foreground',\n 'not-disabled:not-aria-disabled:hover:bg-subtle-hover not-disabled:not-aria-disabled:hover:text-foreground',\n 'not-disabled:not-aria-disabled:active:bg-subtle-pressed',\n focusRing,\n 'disabled:cursor-not-allowed disabled:opacity-50',\n mergedAriaDisabledClasses,\n ),\n },\n slotButtonProps,\n ) as React.ComponentPropsWithoutRef<'button'>;\n renderedDismiss = (\n // `type` is \"button\" unless the slot sets one (`null`, from JavaScript callers, means the\n // default too, so the button never submits an enclosing form by accident). A merged\n // `disabledFocusable` Button makes it unavailable but focusable (spread last: it wins).\n <button\n {...buttonProps}\n ref={dismissRef}\n type={buttonProps.type ?? 'button'}\n {...(dismissParts.disabledFocusable ? MERGED_DISABLED_FOCUSABLE_PROPS : undefined)}\n >\n {dismissParts.content}\n </button>\n );\n }\n\n return (\n <div\n ref={ref}\n role={status === 'error' || status === 'warning' ? 'alert' : 'status'}\n {...rest}\n className={cn(\n 'flex items-start gap-3 rounded border-s-4 px-4 py-3 text-foreground',\n tintClasses[status],\n STATUS_BORDER[status],\n className,\n )}\n >\n {renderedIcon}\n <div className=\"min-w-0 flex-1 text-body-1\">\n <StatusText label={getStatusLabel(status, statusLabel)} />\n {children}\n </div>\n {renderedDismiss}\n </div>\n );\n};\n\nMessageBar.displayName = 'MessageBar';\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"MessageBar.mjs","names":["useId","useId$1","React","tintClasses","DEFAULT_DISMISS_LABEL","BUTTON_ONLY_KEYS","NAMING_KEYS","HANDLER_KEY","dismissContentClassName","LIVE_REGION_ROLES","UNNAMED_ROLES","firstRoleToken","role","isNamedByTitle","token","noop","defaultDismissContent","DismissIcon","isButtonType","type","Button","defaultDismiss","messageBarClassNames","resolveDismiss","dismiss","element","isElementOfType","buttonProps","key","value","BUTTON_OWN_PROP_KEYS","isWaveButton","markup","children","materialiseSlotContent","icon","iconNode","slotRendersContent","renderSlot","cn","placeButtonIcon","hasTextLabel","resolved","resolveSlot","asButton","Component","isButtonObject","props","contentProps","ContentTag","elementProps","inner","slotWrapsDefaultContent","MessageBarRoot","rest","iconClassName","STATUS_ICON_COLOR","status","renderedIcon","StatusIcon","dismissParts","onDismiss","dismissWarning","warnOnce","slotRef","slotButtonProps","hasOwnName","checksContent","literalTextLabel","labelTarget","setLabelTarget","subscribeToContent","observeTextLabel","onChange","contentHasTextLabel","hasRenderedTextLabel","namedByContent","dismissRef","useMergedRefs","renderedDismiss","mergeProps","focusRing","mergedAriaDisabledClasses","MERGED_DISABLED_FOCUSABLE_PROPS","partitionMessageBarChildren","generatedTitleId","titlePlacement","useTitlePlacement","ownTitleId","titleId","defaultRole","ownName","statusText","getStatusLabel","statusLabel","statusTextId","namedByTitle","title","labelledBy","joinIds","missingRegionName","hasActions","actions","measuring","layout","rootElement","setRootElement","textElement","setTextElement","rootRef","ref","measuredLayout","useMessageBarReflow","resolvedLayout","unwrapped","text","StatusText","MessageBarPartContext","body","extraTitle","EXTRA_TITLE_PLACEMENT","node","STATUS_BORDER","className","CONTENT_PLACEMENT","ACTIONS_PLACEMENT","MessageBar","MessageBarTitle","MessageBarActions"],"sources":["../../../src/components/feedback/MessageBar.tsx"],"sourcesContent":["import * as React from 'react';\nimport { joinIds } from '../../lib/aria';\nimport { isElementOfType } from '../../lib/children';\nimport { messageBarClassNames } from '../../lib/classNames';\nimport { cn } from '../../lib/cn';\nimport { warnOnce } from '../../lib/dev';\nimport { DismissIcon } from '../../lib/icons';\nimport { hasRenderedTextLabel, hasTextLabel, observeTextLabel } from '../../lib/labelInName';\nimport { mergeProps } from '../../lib/mergeProps';\nimport {\n materialiseSlotContent,\n renderSlot,\n resolveSlot,\n slotRendersContent,\n slotWrapsDefaultContent,\n} from '../../lib/slot';\nimport { focusRing } from '../../lib/styles';\nimport type { Status, Slot, SlotObject } from '../../lib/types';\nimport { useId } from '../../hooks/useId';\nimport { useMergedRefs } from '../../hooks/useMergedRefs';\nimport { Button } from '../button/Button';\nimport { useMessageBarReflow } from './MessageBar.reflow';\nimport {\n BUTTON_OWN_PROP_KEYS,\n MERGED_DISABLED_FOCUSABLE_PROPS,\n mergedAriaDisabledClasses,\n placeButtonIcon,\n} from '../button/Button.slots';\nimport {\n STATUS_BORDER,\n STATUS_ICON_COLOR,\n StatusIcon,\n StatusText,\n getStatusLabel,\n} from './MessageBar.status';\nimport {\n ACTIONS_PLACEMENT,\n CONTENT_PLACEMENT,\n EXTRA_TITLE_PLACEMENT,\n MessageBarActions,\n MessageBarPartContext,\n MessageBarTitle,\n partitionMessageBarChildren,\n useTitlePlacement,\n} from './MessageBar.parts';\n\n/** Properties for the MessageBar component. */\nexport interface MessageBarProps extends React.HTMLAttributes<HTMLDivElement> {\n /** Status level controlling the color, icon, status text and role of the message bar.\n * `warning` and `error` render `role=\"alert\"`, `info` and `success` `role=\"status\"` (a consumer\n * `role` wins).\n * @default 'info'\n */\n status?: Status;\n /**\n * Visually hidden text read before the message so screen-reader users hear the severity\n * (`'Info:'`, `'Success:'`, `'Warning:'`, `'Error:'` by default). Pass a translation for other\n * languages, or `''` when the message text already states the severity.\n */\n statusLabel?: string;\n /**\n * Called when the dismiss button is activated. Passing it renders the dismiss button (unless\n * `dismiss` is `null`).\n */\n onDismiss?: () => void;\n /**\n * Custom status icon, rendered decoratively (`aria-hidden=\"true\"`, a slot object can override\n * it) in the status color. Only `undefined` keeps the default status icon; `null`, or anything that\n * renders nothing (`false`, `''`), shows no icon.\n */\n icon?: Slot<'span'>;\n /**\n * Content of the dismiss button (replaces the default dismiss icon). It always renders **inside**\n * the built-in `<button type=\"button\" aria-label=\"Dismiss\">`, which calls `onDismiss`; passing\n * content shows the dismiss button even without `onDismiss`. `null` is the only value that hides\n * the button. A boolean counts as no slot, so the conditional idiom\n * `dismiss={useBrandIcon && <BrandCloseIcon />}` keeps the default button: the default icon with\n * `onDismiss`, no button without it. Content that renders nothing (`''`, or an array or Fragment\n * of only `null`, `false`, `true` and `''`, also as the children of a slot object or a merged\n * button) keeps the default icon, so the button is never empty; a slot object that renders a\n * component or a void element (`{ as: CloseIcon }`, `{ as: 'img', src, alt: '' }`) or sets\n * `dangerouslySetInnerHTML` is the icon itself. The content is\n * decorative (`aria-hidden`), so the button keeps the name \"Dismiss\": when the content is\n * visible text, pass a slot object whose `aria-label` matches it\n * (`{ children: 'Close', 'aria-label': 'Close' }`) so the name contains the visible label. An\n * `aria-label`, `aria-labelledby` or `title` on a slot object names the button instead of\n * \"Dismiss\".\n *\n * A `<button>` element or a Wave `Button` passed here is not nested: its props are merged into\n * the built-in button (its `onClick` runs first and can call `preventDefault()` to cancel\n * `onDismiss`; its `aria-label` and an explicit `type` win over the defaults) and its content\n * (children, or `dangerouslySetInnerHTML` markup) is used as is, with a development warning.\n * A Wave `Button`'s own props are not attributes: its `icon` becomes decorative content before\n * its children (after them with `iconPosition=\"after\"`), `disabledFocusable` makes the dismiss\n * button unavailable but focusable as on the Button (`onDismiss` is not called), and\n * `appearance` and `size` are ignored.\n * When the rendered content has a text label (at least two letters or digits:\n * `<button>Close</button>`, or text rendered by a component such as a translation), that text\n * names the button, as in 0.4. An icon, a lone character (`X`, `×`,\n * `+`: a symbol, not a label) and text that is `aria-hidden` or `hidden` keep the name\n * \"Dismiss\". Text hidden only with CSS still counts as the label: a responsive label such as\n * `<span className=\"hidden sm:inline\">Close</span>` drops the default name, so the button has\n * no name wherever that text is not displayed. Give such a button an explicit `aria-label`\n * (`<button aria-label=\"Close\">…</button>`). An `aria-label`, `aria-labelledby` or `title` on\n * the element names the button.\n *\n * The 0.4 button-object form (`{ as: 'button', onClick, … }`, `{ as: Button, … }` or an object\n * with button props) is **deprecated**: its button props (`type` included), `className` and\n * `style` are merged the same way, and a Wave Button's own props apply as for the element form.\n * Pass icon content instead, e.g. `dismiss={<CloseIcon />}`.\n */\n dismiss?: Slot<'span'> | SlotObject<'button'>;\n /**\n * How the text and the actions share the bar. `'singleline'`: the actions sit on the text's row\n * (the text wraps inside its column; it is never cut off). `'multiline'`: the actions get a row of\n * their own under the text. `'auto'`: the actions stay on the text's row while the text fits on\n * one line, measured after mount (the server renders one row), and move below it otherwise; a bar\n * without `MessageBar.Actions` is `'multiline'`, the 0.7 look. The root renders the layout in use\n * as `data-layout` (`singleline` or `multiline`). Fluent's `layout`.\n * @default 'auto'\n */\n layout?: 'auto' | 'singleline' | 'multiline';\n /**\n * The message: body text, with the parts `MessageBar.Title` and `MessageBar.Actions` as direct\n * children (see the component docs).\n */\n children: React.ReactNode;\n /** Ref to the root `<div>`. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\nconst tintClasses: Record<Status, string> = {\n info: 'bg-info-tint',\n success: 'bg-success-tint',\n warning: 'bg-warning-tint',\n error: 'bg-error-tint',\n};\n\ntype UnknownProps = Record<string, unknown>;\n\n/** Name of the dismiss button when nothing else names it. */\nconst DEFAULT_DISMISS_LABEL = 'Dismiss';\n\n/** Attributes that only make sense on the dismiss `<button>` itself. */\nconst BUTTON_ONLY_KEYS: ReadonlySet<string> = new Set([\n 'type',\n 'disabled',\n 'autoFocus',\n 'form',\n 'formAction',\n 'formEncType',\n 'formMethod',\n 'formNoValidate',\n 'formTarget',\n 'name',\n 'value',\n 'popoverTarget',\n 'popoverTargetAction',\n]);\n\n/**\n * Attributes that name the dismiss button. On a slot object they go to the button (its content is\n * decorative); on the merged button, any of them replaces the default `aria-label`.\n */\nconst NAMING_KEYS: ReadonlySet<string> = new Set(['aria-label', 'aria-labelledby', 'title']);\n\nconst HANDLER_KEY = /^on[A-Z]/;\n\nconst dismissContentClassName = 'inline-flex items-center justify-center';\n\n/** Live-region roles: a title is read as the start of their content, never as their name. */\nconst LIVE_REGION_ROLES: ReadonlySet<string> = new Set([\n 'alert',\n 'status',\n 'log',\n 'marquee',\n 'timer',\n]);\n\n/** Roles that take no name. */\nconst UNNAMED_ROLES: ReadonlySet<string> = new Set(['none', 'presentation', 'generic']);\n\n/** The first token of a `role` value (a list of fallback roles is read by its first). */\nfunction firstRoleToken(role: string | undefined): string | undefined {\n return role?.trim().split(/\\s+/)[0] || undefined;\n}\n\n/** Whether a title names a bar with this role (spec D16: a non-live role, such as region or group). */\nfunction isNamedByTitle(role: string | undefined): boolean {\n const token = firstRoleToken(role);\n return token !== undefined && !LIVE_REGION_ROLES.has(token) && !UNNAMED_ROLES.has(token);\n}\n\ninterface DismissParts {\n /** Props merged onto the wired dismiss button. */\n buttonProps: UnknownProps;\n /** What renders inside the dismiss button. */\n content: React.ReactNode;\n /**\n * `true` when the content is rendered as is (a merged `<button>`/`Button`), so a text label in it\n * names the button (C-SLOTS naming, WCAG 2.5.3 Label in Name); `false` when the content is\n * decorative (`aria-hidden`).\n */\n contentMayName: boolean;\n /**\n * Whether the content's literal children contain a text label. Used for the server render and\n * the first client render; after mount, the rendered button's text decides (see\n * {@link hasRenderedTextLabel}).\n */\n literalTextLabel: boolean;\n /**\n * Whether a merged Wave `Button` set `disabledFocusable`: the dismiss button is then unavailable\n * but focusable, as the Button would be.\n */\n disabledFocusable: boolean;\n /** Which development warning the slot needs. */\n warning: 'button-element' | 'button-object' | null;\n}\n\nconst noop = () => {};\n\n/**\n * The decorative default dismiss glyph. It carries the dismiss icon part class when it is the\n * dismiss button's own content, not when the element of a slot object wraps it.\n */\nfunction defaultDismissContent(className?: string): React.ReactNode {\n return <DismissIcon className={className} />;\n}\n\nfunction isButtonType(type: unknown): boolean {\n return type === 'button' || type === Button;\n}\n\n/** The dismiss button without a slot: the default icon and name. */\nfunction defaultDismiss(): DismissParts {\n return {\n buttonProps: {},\n content: defaultDismissContent(messageBarClassNames.dismissIcon),\n contentMayName: false,\n literalTextLabel: false,\n disabledFocusable: false,\n warning: null,\n };\n}\n\n/**\n * Splits the `dismiss` slot into props for the wired dismiss button and the content rendered\n * inside it (C-SLOTS dismiss semantics). `null` means: no dismiss button. A boolean is no slot\n * (the default dismiss button), and content that renders nothing keeps the default icon.\n */\nfunction resolveDismiss(dismiss: MessageBarProps['dismiss']): DismissParts | null {\n if (dismiss === null) return null;\n if (dismiss === undefined || typeof dismiss === 'boolean') return defaultDismiss();\n\n // A merged `<button>`/`Button` keeps its content accessible (as in 0.4): a text label names the\n // button, anything else (an icon, a lone character such as `X` or `×`) gets the default name.\n // The type is compared through `isElementOfType`, so a Button written in a Server Component\n // (a lazy client reference) is merged too.\n const element = dismiss as React.ReactNode;\n if (isElementOfType<UnknownProps>(element, 'button', Button)) {\n const buttonProps: UnknownProps = {};\n for (const [key, value] of Object.entries(element.props)) {\n if (\n key !== 'children' &&\n key !== 'dangerouslySetInnerHTML' &&\n !BUTTON_OWN_PROP_KEYS.has(key)\n ) {\n buttonProps[key] = value;\n }\n }\n const isWaveButton = isElementOfType(element, Button);\n // A generator is read once by the check; its items are what renders (and names the button).\n // Markup of the merged button (`dangerouslySetInnerHTML`) is its content as well, rendered in\n // a span inside the dismiss button (the button itself also holds the icon).\n const markup = element.props.dangerouslySetInnerHTML as\n React.HTMLAttributes<HTMLElement>['dangerouslySetInnerHTML'] | undefined;\n const children =\n markup != null ? (\n <span className={dismissContentClassName} dangerouslySetInnerHTML={markup} />\n ) : (\n materialiseSlotContent(element.props.children)\n );\n // Wave Button's icon becomes decorative content before its children (after them with\n // `iconPosition=\"after\"`).\n const icon = element.props.icon as Slot<'span'>;\n const iconNode =\n isWaveButton && slotRendersContent(icon)\n ? renderSlot(icon, 'span', cn(messageBarClassNames.dismissIcon, dismissContentClassName), {\n 'aria-hidden': true,\n })\n : null;\n const content =\n iconNode || slotRendersContent(children)\n ? placeButtonIcon(iconNode, children, element.props.iconPosition)\n : defaultDismissContent(messageBarClassNames.dismissIcon);\n return {\n buttonProps,\n content,\n contentMayName: true,\n literalTextLabel: hasTextLabel(children),\n disabledFocusable: isWaveButton && Boolean(element.props.disabledFocusable),\n warning: 'button-element',\n };\n }\n\n // Everything else is classified by the slot system (F2): shorthand content resolves to the\n // default `span` with no attributes; a slot object resolves to its element and attributes.\n const resolved = resolveSlot(dismiss as Slot<'span'>, 'span');\n if (!resolved) return defaultDismiss();\n const { Component, props, children } = resolved;\n const asButton = isButtonType(Component);\n const isButtonObject =\n asButton ||\n Object.keys(props).some((key) => BUTTON_ONLY_KEYS.has(key) || HANDLER_KEY.test(key));\n const buttonProps: UnknownProps = {};\n const contentProps: UnknownProps = {};\n let iconNode: React.ReactNode = null;\n for (const [key, value] of Object.entries(props)) {\n if (Component === Button && BUTTON_OWN_PROP_KEYS.has(key)) {\n // Wave Button's own props are not attributes: `icon`, `iconPosition` and\n // `disabledFocusable` are applied below, the others (`appearance`, `size`) are dropped.\n if (key === 'icon' && slotRendersContent(value)) {\n iconNode = renderSlot(\n value as Slot<'span'>,\n 'span',\n cn(messageBarClassNames.dismissIcon, dismissContentClassName),\n { 'aria-hidden': true },\n );\n }\n } else if (\n BUTTON_ONLY_KEYS.has(key) ||\n HANDLER_KEY.test(key) ||\n NAMING_KEYS.has(key) ||\n // 0.4 rendered the object as the button itself: its className, style and ref stay there.\n (isButtonObject && (key === 'className' || key === 'style' || key === 'ref'))\n ) {\n buttonProps[key] = value;\n } else {\n contentProps[key] = value;\n }\n }\n\n // The content element: the object's own element, or a span for the button-object form. An\n // object whose children render nothing styles the default icon\n // (e.g. `{ className: 'text-error' }`), unless its element is the icon itself.\n const ContentTag: React.ElementType = asButton ? 'span' : Component;\n const elementProps = {\n 'aria-hidden': true,\n ...contentProps,\n className: cn(\n iconNode === null && messageBarClassNames.dismissIcon,\n dismissContentClassName,\n contentProps.className as string | undefined,\n ),\n };\n let inner: React.ReactNode = null;\n if (iconNode || slotRendersContent(children)) {\n inner = placeButtonIcon(iconNode, children, Component === Button && props.iconPosition);\n } else if (slotWrapsDefaultContent(ContentTag, { ...contentProps, children })) {\n inner = defaultDismissContent();\n }\n return {\n buttonProps,\n content:\n inner === null\n ? React.createElement(ContentTag, elementProps)\n : React.createElement(ContentTag, elementProps, inner),\n contentMayName: false,\n literalTextLabel: false,\n disabledFocusable: Component === Button && Boolean(props.disabledFocusable),\n warning: isButtonObject ? 'button-object' : null,\n };\n}\n\n// The MessageBar root, documented on the exported `MessageBar` const.\nconst MessageBarRoot = ({\n status = 'info',\n statusLabel,\n onDismiss,\n icon,\n dismiss,\n layout = 'auto',\n children,\n className,\n ref,\n ...rest\n}: MessageBarProps) => {\n const iconClassName = cn(\n messageBarClassNames.icon,\n 'mt-0.5 inline-flex shrink-0',\n STATUS_ICON_COLOR[status],\n );\n const renderedIcon =\n icon !== undefined ? (\n slotRendersContent(icon) ? (\n renderSlot(icon, 'span', iconClassName, { 'aria-hidden': true })\n ) : null\n ) : (\n <span aria-hidden=\"true\" className={iconClassName}>\n <StatusIcon status={status} size={20} />\n </span>\n );\n\n // A boolean `dismiss` is no slot (`dismiss={cond && <CloseIcon />}`): only `onDismiss` shows it.\n const showDismiss =\n onDismiss !== undefined || (dismiss !== undefined && typeof dismiss !== 'boolean');\n const dismissParts = showDismiss ? resolveDismiss(dismiss) : null;\n const dismissWarning = dismissParts?.warning ?? null;\n React.useEffect(() => {\n if (dismissWarning === 'button-element') {\n warnOnce(\n 'MessageBar:dismiss-button-element',\n 'MessageBar: `dismiss` received a button element; its props were merged into the built-in dismiss button (buttons cannot be nested). Pass icon content instead, e.g. `dismiss={<CloseIcon />}`, and use `onDismiss`.',\n );\n } else if (dismissWarning === 'button-object') {\n warnOnce(\n 'MessageBar:dismiss-button-object',\n 'MessageBar: the button-object form of `dismiss` is deprecated and will be removed in 1.0; its button props were merged into the built-in dismiss button. Pass icon content instead, e.g. `dismiss={<CloseIcon />}`, and use `onDismiss`.',\n );\n }\n }, [dismissWarning]);\n\n // The slot's ref joins ours through a stable merged ref (never a new callback per render).\n const { ref: slotRef, ...slotButtonProps } = dismissParts?.buttonProps ?? {};\n const hasOwnName = Object.keys(slotButtonProps).some(\n (key) => NAMING_KEYS.has(key) && slotButtonProps[key] != null,\n );\n\n // C-SLOTS naming (WCAG 2.5.3 Label in Name): a merged button's content names it when it renders\n // a text label (at least two letters or digits; a lone `X` or `×` is a glyph), and the default\n // `aria-label` would hide that label. The literal children decide on the server and on the first\n // render; after mount, the rendered button's text does (text from components, e.g. translations,\n // and later changes).\n const checksContent = dismissParts !== null && dismissParts.contentMayName && !hasOwnName;\n const literalTextLabel = dismissParts?.literalTextLabel ?? false;\n const [labelTarget, setLabelTarget] = React.useState<HTMLButtonElement | null>(null);\n const subscribeToContent = React.useCallback(\n (onChange: () => void) => (labelTarget ? observeTextLabel(labelTarget, onChange) : noop),\n [labelTarget],\n );\n const contentHasTextLabel = React.useSyncExternalStore(\n subscribeToContent,\n () => (labelTarget ? hasRenderedTextLabel(labelTarget) : literalTextLabel),\n () => literalTextLabel,\n );\n const namedByContent = checksContent && contentHasTextLabel;\n const dismissRef = useMergedRefs<HTMLButtonElement>(\n slotRef as React.Ref<HTMLButtonElement> | undefined,\n checksContent ? setLabelTarget : undefined,\n );\n\n let renderedDismiss: React.ReactNode = null;\n if (dismissParts) {\n const buttonProps = mergeProps(\n {\n 'aria-label': hasOwnName || namedByContent ? undefined : DEFAULT_DISMISS_LABEL,\n onClick: () => onDismiss?.(),\n className: cn(\n messageBarClassNames.dismissButton,\n 'ms-auto inline-flex shrink-0 cursor-pointer items-center justify-center rounded border-none bg-transparent p-1 text-muted-foreground',\n 'not-disabled:not-aria-disabled:hover:bg-subtle-hover not-disabled:not-aria-disabled:hover:text-foreground',\n 'not-disabled:not-aria-disabled:active:bg-subtle-pressed',\n focusRing,\n 'disabled:cursor-not-allowed disabled:opacity-50',\n mergedAriaDisabledClasses,\n ),\n },\n slotButtonProps,\n ) as React.ComponentPropsWithoutRef<'button'>;\n renderedDismiss = (\n // `type` is \"button\" unless the slot sets one (`null`, from JavaScript callers, means the\n // default too, so the button never submits an enclosing form by accident). A merged\n // `disabledFocusable` Button makes it unavailable but focusable (spread last: it wins).\n <button\n {...buttonProps}\n ref={dismissRef}\n type={buttonProps.type ?? 'button'}\n {...(dismissParts.disabledFocusable ? MERGED_DISABLED_FOCUSABLE_PROPS : undefined)}\n >\n {dismissParts.content}\n </button>\n );\n }\n\n // Parts (D15): a static scan of the direct children (Fragments flattened, Server Component\n // references included), so the title and the actions are placed in the server HTML too.\n const { title, ownTitleId, actions, body } = partitionMessageBarChildren(children);\n const generatedTitleId = useId('wave-message-bar-title');\n const titlePlacement = useTitlePlacement(ownTitleId, generatedTitleId);\n const titleId = titlePlacement.titleId;\n\n // Labelling (D16). The role the bar renders: the consumer's when the prop is given (it is spread\n // after the default, as in 0.7), else the status role. A live bar is read once, title included,\n // and gets no name; a bar with a non-live role is named by the severity text and the title.\n const defaultRole = status === 'error' || status === 'warning' ? 'alert' : 'status';\n const role = 'role' in rest ? rest.role : defaultRole;\n // A prop that holds `undefined` (a wrapper forwarding it) is no name of the consumer's.\n const ownName = rest['aria-label'] !== undefined || rest['aria-labelledby'] !== undefined;\n const statusText = getStatusLabel(status, statusLabel);\n const statusTextId = useId('wave-message-bar-status');\n const namedByTitle = title !== undefined && !ownName && isNamedByTitle(role);\n // Written after the spread, so a forwarded `aria-labelledby={undefined}` cannot remove it.\n const labelledBy = ownName\n ? rest['aria-labelledby']\n : namedByTitle\n ? joinIds(statusText ? statusTextId : undefined, titleId)\n : undefined;\n const missingRegionName = firstRoleToken(role) === 'region' && title === undefined && !ownName;\n React.useEffect(() => {\n if (missingRegionName) {\n warnOnce(\n 'MessageBar:region-name',\n 'MessageBar: a bar with role=\"region\" is a landmark only when it has a name. Add a MessageBar.Title, or pass aria-label or aria-labelledby.',\n );\n }\n }, [missingRegionName]);\n\n // Layout (D17): one DOM order in every layout (icon, text, actions, Dismiss), so a layout change\n // never moves a focused element; only classes change. Without actions the bar keeps 0.7's markup.\n const hasActions = actions.length > 0;\n // `'auto'` with actions measures its text (MessageBar.reflow.ts); the elements it reads are held\n // in state through callback refs, attached only while it measures (no extra render otherwise).\n const measuring = layout === 'auto' && hasActions;\n const [rootElement, setRootElement] = React.useState<HTMLDivElement | null>(null);\n const [textElement, setTextElement] = React.useState<HTMLDivElement | null>(null);\n const rootRef = useMergedRefs<HTMLDivElement>(ref, measuring ? setRootElement : undefined);\n const measuredLayout = useMessageBarReflow(rootElement, textElement, measuring);\n const resolvedLayout: 'singleline' | 'multiline' =\n layout === 'auto' ? (hasActions ? measuredLayout : 'multiline') : layout;\n // While it measures one row, the text column does not wrap, so text that does not fit overflows\n // the column (never cut off) and the measurement sees it.\n const unwrapped = measuring && resolvedLayout === 'singleline';\n\n // The text column: the severity text, the title (and a space, so the two never run together),\n // then the body in its order.\n const text = (\n <div\n ref={measuring ? setTextElement : undefined}\n className={cn(\n messageBarClassNames.body,\n 'min-w-0 flex-1 text-body-1',\n unwrapped && 'whitespace-nowrap',\n )}\n >\n <StatusText id={namedByTitle && statusText ? statusTextId : undefined} label={statusText} />\n {title && (\n <MessageBarPartContext.Provider value={titlePlacement}>\n {title.element}\n </MessageBarPartContext.Provider>\n )}\n {title && ' '}\n {body.map(({ key, node, extraTitle }) =>\n extraTitle ? (\n <MessageBarPartContext.Provider key={key} value={EXTRA_TITLE_PLACEMENT}>\n {node}\n </MessageBarPartContext.Provider>\n ) : (\n <React.Fragment key={key}>{node}</React.Fragment>\n ),\n )}\n </div>\n );\n\n return (\n <div\n ref={rootRef}\n role={defaultRole}\n data-layout={resolvedLayout}\n {...rest}\n aria-labelledby={labelledBy}\n className={cn(\n messageBarClassNames.root,\n 'flex items-start gap-3 rounded border-s-4 px-4 py-3 text-foreground',\n tintClasses[status],\n STATUS_BORDER[status],\n className,\n )}\n >\n <MessageBarPartContext.Provider value={CONTENT_PLACEMENT}>\n {renderedIcon}\n {hasActions ? (\n // A layout wrapper (not a part): the text column and the actions, in this DOM order.\n <div\n className={cn(\n 'flex min-w-0 flex-1 gap-x-3 gap-y-2',\n resolvedLayout === 'multiline' ? 'flex-col' : 'items-start',\n )}\n >\n {text}\n <MessageBarPartContext.Provider value={ACTIONS_PLACEMENT}>\n {actions.map(({ key, element }) => (\n <React.Fragment key={key}>{element}</React.Fragment>\n ))}\n </MessageBarPartContext.Provider>\n </div>\n ) : (\n text\n )}\n {renderedDismiss}\n </MessageBarPartContext.Provider>\n </div>\n );\n};\nMessageBarRoot.displayName = 'MessageBar';\n\n/**\n * An inline message that tells the user about the state of a page or task: a status icon, a\n * visually hidden status label (\"Warning:\"), an optional title, the message, optional actions and\n * an optional dismiss button.\n *\n * - The status sets the tint, the logical start border, the icon and the role (`alert` for\n * `warning`/`error`, `status` otherwise). Screen readers hear the severity through `statusLabel`.\n * - Parts, as direct children: `MessageBar.Title` (a semibold lead-in, read first after the\n * severity) and `MessageBar.Actions` (buttons after the text on one row, or below it with\n * `layout=\"multiline\"`). The built-in Dismiss button stays the bar's own.\n * - With its default roles the bar is a live region and the title is read as the start of its\n * content; give the bar `role=\"region\"` (a notice that stays on the page) and the title names it.\n * - The dismiss button is always the MessageBar's own `<button>` wired to `onDismiss`\n * (`type=\"button\"` unless a merged button slot sets its own `type`); the `dismiss` slot only\n * replaces its content (see {@link MessageBarProps.dismiss}).\n *\n * React Server Components cannot dot into a client module: import the flat names\n * `MessageBarTitle` and `MessageBarActions` there; `MessageBar.Title` and `MessageBar.Actions`\n * work in client files.\n *\n * @example\n * <MessageBar status=\"warning\" onDismiss={() => setVisible(false)}>\n * <MessageBar.Title>Update available</MessageBar.Title>\n * A new version is ready to install.\n * <MessageBar.Actions>\n * <Button size=\"small\">Update now</Button>\n * </MessageBar.Actions>\n * </MessageBar>\n */\nexport const MessageBar = /* @__PURE__ */ Object.assign(MessageBarRoot, {\n Title: MessageBarTitle,\n Actions: MessageBarActions,\n});\n\nexport { MessageBarTitle, MessageBarActions };\nexport type { MessageBarTitleProps, MessageBarActionsProps } from './MessageBar.parts';\n"],"mappings":"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"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/children.cjs"),r=require("../../lib/dev.cjs"),i=require("../../lib/slot.cjs"),a=require("../../lib/classNames.cjs");let o=require("react");o=e.__toESM(o,1);let s=require("react/jsx-runtime");var c=o.createContext(null);c.displayName=`MessageBarPartContext`;var l={placement:`content`},u={placement:`actions`},d={placement:`extra-title`};function f(e){return o.useContext(c)||(r.reportMissingContext(e,`<MessageBar>`),l)}var p=({id:e,className:n,children:u,ref:d,...p})=>{let m=f(`MessageBar.Title`),h=m.placement===`title`,g=h?null:m.placement===`extra-title`?`multiple`:`unscanned`;return o.useEffect(()=>{g===`unscanned`?r.warnOnce(`MessageBar.Title:unscanned`,`MessageBar.Title is not a direct child of MessageBar, so it is not placed first in the text. Make it a direct child.`):g===`multiple`&&r.warnOnce(`MessageBar.Title:multiple`,`MessageBar.Title: this MessageBar already has a title (its first MessageBar.Title among its direct children), so this one renders as body text. Give a bar one title.`)},[g]),(0,s.jsx)(`span`,{...p,ref:d,id:(h?m.titleId:e)||void 0,className:t.cn(a.messageBarTitleClassNames.root,`font-semibold`,n),children:(0,s.jsx)(c.Provider,{value:l,children:i.materialiseSlotContent(u)})})};p.displayName=`MessageBarTitle`;var m=({className:e,children:n,ref:u,...d})=>{let p=f(`MessageBar.Actions`).placement===`actions`;return o.useEffect(()=>{p||r.warnOnce(`MessageBar.Actions:unscanned`,`MessageBar.Actions is not a direct child of MessageBar, so it is not placed in the action area. Make it a direct child.`)},[p]),(0,s.jsx)(`div`,{...d,ref:u,className:t.cn(a.messageBarActionsClassNames.root,`flex shrink-0 flex-wrap items-center gap-2`,e),children:(0,s.jsx)(c.Provider,{value:l,children:i.materialiseSlotContent(n)})})};m.displayName=`MessageBarActions`;function h(e,t){let n=e||t;return o.useMemo(()=>({placement:`title`,titleId:n}),[n])}function g(e){let t,r=[],a=[];for(let{key:o,node:s}of n.flattenChildren(e))if(n.isElementOfType(s,p)){if(!i.slotRendersContent(s.props.children))continue;t===void 0?t={key:o,element:s}:a.push({key:o,node:s,extraTitle:!0})}else n.isElementOfType(s,m)?i.slotRendersContent(s.props.children)&&r.push({key:o,element:s}):a.push({key:o,node:s,extraTitle:!1});return{title:t,ownTitleId:t?.element.props.id,actions:r,body:a}}exports.ACTIONS_PLACEMENT=u,exports.CONTENT_PLACEMENT=l,exports.EXTRA_TITLE_PLACEMENT=d,exports.MessageBarActions=m,exports.MessageBarPartContext=c,exports.MessageBarTitle=p,exports.partitionMessageBarChildren=g,exports.useTitlePlacement=h;
|
|
2
|
+
//# sourceMappingURL=MessageBar.parts.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MessageBar.parts.cjs","names":["React","cn","messageBarTitleClassNames","materialiseSlotContent","messageBarActionsClassNames","flattenChildren","isElementOfType","slotRendersContent","require_runtime","require_cn","require_children","require_dev","require_slot","require_classNames","react","react_jsx_runtime","MessageBarPartContext","CONTENT_PLACEMENT","ACTIONS_PLACEMENT","EXTRA_TITLE_PLACEMENT","useMessageBarPart","componentName","MessageBarTitle","rest","part","placed","problem","id","className","children","MessageBarActions","useTitlePlacement","titleId","ownTitleId","generatedTitleId","partitionMessageBarChildren","title","actions","body","node"],"sources":["../../../src/components/feedback/MessageBar.parts.tsx"],"sourcesContent":["import * as React from 'react';\nimport { flattenChildren, isElementOfType } from '../../lib/children';\nimport { messageBarActionsClassNames, messageBarTitleClassNames } from '../../lib/classNames';\nimport { cn } from '../../lib/cn';\nimport { reportMissingContext, warnOnce } from '../../lib/dev';\nimport { materialiseSlotContent, slotRendersContent } from '../../lib/slot';\n\n/** Properties for the MessageBarTitle sub-component. */\nexport interface MessageBarTitleProps extends React.HTMLAttributes<HTMLSpanElement> {\n /** Ref to the title `<span>`. */\n ref?: React.Ref<HTMLSpanElement>;\n}\n\n/** Properties for the MessageBarActions sub-component. */\nexport interface MessageBarActionsProps extends React.HTMLAttributes<HTMLDivElement> {\n /** Ref to the element that holds the actions. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\n/**\n * Where a MessageBar put a part (C-CONTEXT: `null` outside every MessageBar). The bar provides\n * `'content'` around everything it renders and a more specific value around the parts that its\n * scan of its direct children placed; each part resets it to `'content'` for its own children, so\n * a part inside another part, or inside the app's own component, counts as not placed.\n */\nexport interface MessageBarPartContextValue {\n /**\n * `'title'`: the bar's title, first in the text column. `'actions'`: in the action area.\n * `'extra-title'`: a later title, left in the body. `'content'`: anywhere else inside the bar.\n */\n placement: 'title' | 'actions' | 'extra-title' | 'content';\n /** The id the placed title renders (its own `id`, else a generated one); `'title'` only. */\n titleId?: string;\n}\n\nexport const MessageBarPartContext = React.createContext<MessageBarPartContextValue | null>(null);\nMessageBarPartContext.displayName = 'MessageBarPartContext';\n\n/** Inside a bar but not placed by its scan (also the inert value in production, C-CONTEXT). */\nexport const CONTENT_PLACEMENT: MessageBarPartContextValue = { placement: 'content' };\n/** A `MessageBar.Actions` the bar placed in its action area. */\nexport const ACTIONS_PLACEMENT: MessageBarPartContextValue = { placement: 'actions' };\n/** A second or later `MessageBar.Title`, rendered where it is in the body. */\nexport const EXTRA_TITLE_PLACEMENT: MessageBarPartContextValue = { placement: 'extra-title' };\n\n/** C-CONTEXT: throws in development, logs once and returns an inert value in production. */\nfunction useMessageBarPart(componentName: string): MessageBarPartContextValue {\n const context = React.useContext(MessageBarPartContext);\n if (context) return context;\n reportMissingContext(componentName, '<MessageBar>');\n return CONTENT_PLACEMENT;\n}\n\n/**\n * The bar's title, read right after the severity text. Names the bar when the bar has a non-live\n * `role` (`region`, `group`). Must be a direct child of MessageBar (a Fragment there counts, and so\n * does a title written in a Server Component); anywhere else it renders where it is, without its\n * place or the naming (development warning). Give a bar one title: a second one renders as body\n * text (development warning). A title whose children render nothing is left out.\n *\n * Also exported as `MessageBarTitle` (import the flat name from React Server Components).\n */\nexport const MessageBarTitle = ({\n id,\n className,\n children,\n ref,\n ...rest\n}: MessageBarTitleProps) => {\n const part = useMessageBarPart('MessageBar.Title');\n const placed = part.placement === 'title';\n const problem: 'unscanned' | 'multiple' | null = placed\n ? null\n : part.placement === 'extra-title'\n ? 'multiple'\n : 'unscanned';\n React.useEffect(() => {\n if (problem === 'unscanned') {\n warnOnce(\n 'MessageBar.Title:unscanned',\n 'MessageBar.Title is not a direct child of MessageBar, so it is not placed first in the text. Make it a direct child.',\n );\n } else if (problem === 'multiple') {\n warnOnce(\n 'MessageBar.Title:multiple',\n 'MessageBar.Title: this MessageBar already has a title (its first MessageBar.Title among its direct children), so this one renders as body text. Give a bar one title.',\n );\n }\n }, [problem]);\n\n return (\n <span\n {...rest}\n ref={ref}\n id={(placed ? part.titleId : id) || undefined}\n className={cn(messageBarTitleClassNames.root, 'font-semibold', className)}\n >\n <MessageBarPartContext.Provider value={CONTENT_PLACEMENT}>\n {materialiseSlotContent(children)}\n </MessageBarPartContext.Provider>\n </span>\n );\n};\nMessageBarTitle.displayName = 'MessageBarTitle';\n\n/**\n * The bar's actions (Retry, Learn more): after the text on one row, on their own row under it in\n * the multiline layout. Must be a direct child of MessageBar (a Fragment there counts, and so does\n * a part written in a Server Component); anywhere else it renders where it is (development\n * warning). Actions whose children render nothing are left out, so the bar keeps its look without\n * actions. The actions have no role of their own: the bar is already the grouping.\n *\n * Also exported as `MessageBarActions` (import the flat name from React Server Components).\n */\nexport const MessageBarActions = ({\n className,\n children,\n ref,\n ...rest\n}: MessageBarActionsProps) => {\n const part = useMessageBarPart('MessageBar.Actions');\n const placed = part.placement === 'actions';\n React.useEffect(() => {\n if (!placed) {\n warnOnce(\n 'MessageBar.Actions:unscanned',\n 'MessageBar.Actions is not a direct child of MessageBar, so it is not placed in the action area. Make it a direct child.',\n );\n }\n }, [placed]);\n\n return (\n <div\n {...rest}\n ref={ref}\n className={cn(\n messageBarActionsClassNames.root,\n 'flex shrink-0 flex-wrap items-center gap-2',\n className,\n )}\n >\n <MessageBarPartContext.Provider value={CONTENT_PLACEMENT}>\n {materialiseSlotContent(children)}\n </MessageBarPartContext.Provider>\n </div>\n );\n};\nMessageBarActions.displayName = 'MessageBarActions';\n\n/** The context value of the placed title (C-MEMO): stable while its id is. */\nexport function useTitlePlacement(\n ownTitleId: string | undefined,\n generatedTitleId: string,\n): MessageBarPartContextValue {\n const titleId = ownTitleId || generatedTitleId;\n return React.useMemo<MessageBarPartContextValue>(\n () => ({ placement: 'title', titleId }),\n [titleId],\n );\n}\n\n/** How a MessageBar sorts its direct children (D15). */\nexport interface MessageBarPartition {\n /** The first `MessageBar.Title` whose children render content, with its flattened key. */\n title: { key: string; element: React.ReactElement<MessageBarTitleProps> } | undefined;\n /** The `id` the first title was given by its consumer, if any. */\n ownTitleId: string | undefined;\n /** Every `MessageBar.Actions` whose children render content, in order. */\n actions: Array<{ key: string; element: React.ReactElement<MessageBarActionsProps> }>;\n /** Everything else, in order; `extraTitle` marks a later title that renders content. */\n body: Array<{ key: string; node: React.ReactNode; extraTitle: boolean }>;\n}\n\n/**\n * The static scan of D15, during render (so the placement is in the server HTML): the direct\n * children with Fragments flattened, parts recognised by `isElementOfType` (a part written in a\n * Server Component arrives as a lazy reference). A part whose children render nothing\n * (`slotRendersContent`) is dropped.\n */\nexport function partitionMessageBarChildren(children: React.ReactNode): MessageBarPartition {\n let title: MessageBarPartition['title'];\n const actions: MessageBarPartition['actions'] = [];\n const body: MessageBarPartition['body'] = [];\n for (const { key, node } of flattenChildren(children)) {\n if (isElementOfType<MessageBarTitleProps>(node, MessageBarTitle)) {\n if (!slotRendersContent(node.props.children)) continue;\n if (title === undefined) title = { key, element: node };\n else body.push({ key, node, extraTitle: true });\n } else if (isElementOfType<MessageBarActionsProps>(node, MessageBarActions)) {\n if (slotRendersContent(node.props.children)) actions.push({ key, element: node });\n } else {\n body.push({ key, node, extraTitle: false });\n }\n }\n return { title, ownTitleId: title?.element.props.id, actions, body };\n}\n"],"mappings":"uTAmCA,IAAagB,EAAwBhB,EAAM,cAAiD,IAAI,EAChG,EAAsB,YAAc,wBAGpC,IAAaiB,EAAgD,CAAE,UAAW,SAAU,EAEvEC,EAAgD,CAAE,UAAW,SAAU,EAEvEC,EAAoD,CAAE,UAAW,aAAc,EAG5F,SAASC,EAAkB,EAAmD,CAI5E,OAHgBpB,EAAM,WAAWgB,CAC7B,IACJL,EAAA,qBAAqBU,EAAe,cAAc,EAC3CJ,EACT,CAWA,IAAaK,GAAmB,CAC9B,KACA,YACA,WACA,MACA,GAAGC,KACuB,CAC1B,IAAMC,EAAOJ,EAAkB,kBAAkB,EAC3CK,EAASD,EAAK,YAAc,QAC5BE,EAA2CD,EAC7C,KACAD,EAAK,YAAc,cACjB,WACA,YAeN,OAdAV,EAAM,cAAgB,CAChBY,IAAY,YACdf,EAAA,SACE,6BACA,sHACF,EACSe,IAAY,YACrBf,EAAA,SACE,4BACA,uKACF,CAEJ,EAAG,CAACe,CAAO,CAAC,GAGV,EAAAX,EAAA,IAAA,CAAC,OAAD,CACE,GAAIQ,EACC,MACL,IAAKE,EAASD,EAAK,QAAUG,IAAO,IAAA,GACpC,UAAW1B,EAAAA,GAAGC,EAAAA,0BAA0B,KAAM,gBAAiB0B,CAAS,EAExE,UAAA,EAAAb,EAAA,IAAA,CAACC,EAAsB,SAAvB,CAAgC,MAAOC,EACpC,SAAAd,EAAAA,uBAAuB0B,CAAQ,CACF,CAAA,CAC5B,CAAA,CAEV,EACA,EAAgB,YAAc,kBAW9B,IAAaC,GAAqB,CAChC,YACA,WACA,MACA,GAAGP,KACyB,CAE5B,IAAME,EADOL,EAAkB,oBAChB,CAAA,CAAK,YAAc,UAUlC,OATAN,EAAM,cAAgB,CACfW,GACHd,EAAA,SACE,+BACA,yHACF,CAEJ,EAAG,CAACc,CAAM,CAAC,GAGT,EAAAV,EAAA,IAAA,CAAC,MAAD,CACE,GAAIQ,EACC,MACL,UAAWtB,EAAAA,GACTG,EAAAA,4BAA4B,KAC5B,6CACAwB,CACF,EAEA,UAAA,EAAAb,EAAA,IAAA,CAACC,EAAsB,SAAvB,CAAgC,MAAOC,EACpC,SAAAd,EAAAA,uBAAuB0B,CAAQ,CACF,CAAA,CAC7B,CAAA,CAET,EACA,EAAkB,YAAc,oBAGhC,SAAgBE,EACd,EACA,EAC4B,CAC5B,IAAMC,EAAUC,GAAcC,EAC9B,OAAOlC,EAAM,aACJ,CAAE,UAAW,QAAS,SAAQ,GACrC,CAACgC,CAAO,CACV,CACF,CAoBA,SAAgBG,EAA4B,EAAgD,CAC1F,IAAIC,EACEC,EAA0C,CAAC,EAC3CC,EAAoC,CAAC,EAC3C,IAAK,GAAM,CAAE,MAAK,UAAUjC,EAAAA,gBAAgBwB,CAAQ,EAClD,GAAIvB,EAAAA,gBAAsCiC,EAAMjB,CAAe,EAAG,CAChE,GAAI,CAACf,EAAAA,mBAAmBgC,EAAK,MAAM,QAAQ,EAAG,SAC1CH,IAAU,IAAA,GAAW,EAAQ,CAAE,MAAK,QAASG,CAAK,EACjDD,EAAK,KAAK,CAAE,MAAK,OAAM,WAAY,EAAK,CAAC,CAChD,MAAWhC,EAAAA,gBAAwCiC,EAAMT,CAAiB,EACpEvB,EAAAA,mBAAmBgC,EAAK,MAAM,QAAQ,GAAGF,EAAQ,KAAK,CAAE,MAAK,QAASE,CAAK,CAAC,EAEhFD,EAAK,KAAK,CAAE,MAAK,OAAM,WAAY,EAAM,CAAC,EAG9C,MAAO,CAAE,QAAO,WAAYF,GAAO,QAAQ,MAAM,GAAI,UAAS,MAAK,CACrE"}
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { cn as e } from "../../lib/cn.mjs";
|
|
3
|
+
import { flattenChildren as t, isElementOfType as n } from "../../lib/children.mjs";
|
|
4
|
+
import { reportMissingContext as r, warnOnce as i } from "../../lib/dev.mjs";
|
|
5
|
+
import { materialiseSlotContent as a, slotRendersContent as o } from "../../lib/slot.mjs";
|
|
6
|
+
import { messageBarActionsClassNames as s, messageBarTitleClassNames as c } from "../../lib/classNames.mjs";
|
|
7
|
+
import * as l from "react";
|
|
8
|
+
import { jsx as u } from "react/jsx-runtime";
|
|
9
|
+
//#region src/components/feedback/MessageBar.parts.tsx
|
|
10
|
+
var d = l.createContext(null);
|
|
11
|
+
d.displayName = "MessageBarPartContext";
|
|
12
|
+
var f = { placement: "content" }, p = { placement: "actions" }, m = { placement: "extra-title" };
|
|
13
|
+
function h(e) {
|
|
14
|
+
return l.useContext(d) || (r(e, "<MessageBar>"), f);
|
|
15
|
+
}
|
|
16
|
+
var g = ({ id: t, className: n, children: r, ref: o, ...s }) => {
|
|
17
|
+
let p = h("MessageBar.Title"), m = p.placement === "title", g = m ? null : p.placement === "extra-title" ? "multiple" : "unscanned";
|
|
18
|
+
return l.useEffect(() => {
|
|
19
|
+
g === "unscanned" ? i("MessageBar.Title:unscanned", "MessageBar.Title is not a direct child of MessageBar, so it is not placed first in the text. Make it a direct child.") : g === "multiple" && i("MessageBar.Title:multiple", "MessageBar.Title: this MessageBar already has a title (its first MessageBar.Title among its direct children), so this one renders as body text. Give a bar one title.");
|
|
20
|
+
}, [g]), /* @__PURE__ */ u("span", {
|
|
21
|
+
...s,
|
|
22
|
+
ref: o,
|
|
23
|
+
id: (m ? p.titleId : t) || void 0,
|
|
24
|
+
className: e(c.root, "font-semibold", n),
|
|
25
|
+
children: /* @__PURE__ */ u(d.Provider, {
|
|
26
|
+
value: f,
|
|
27
|
+
children: a(r)
|
|
28
|
+
})
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
g.displayName = "MessageBarTitle";
|
|
32
|
+
var _ = ({ className: t, children: n, ref: r, ...o }) => {
|
|
33
|
+
let c = h("MessageBar.Actions").placement === "actions";
|
|
34
|
+
return l.useEffect(() => {
|
|
35
|
+
c || i("MessageBar.Actions:unscanned", "MessageBar.Actions is not a direct child of MessageBar, so it is not placed in the action area. Make it a direct child.");
|
|
36
|
+
}, [c]), /* @__PURE__ */ u("div", {
|
|
37
|
+
...o,
|
|
38
|
+
ref: r,
|
|
39
|
+
className: e(s.root, "flex shrink-0 flex-wrap items-center gap-2", t),
|
|
40
|
+
children: /* @__PURE__ */ u(d.Provider, {
|
|
41
|
+
value: f,
|
|
42
|
+
children: a(n)
|
|
43
|
+
})
|
|
44
|
+
});
|
|
45
|
+
};
|
|
46
|
+
_.displayName = "MessageBarActions";
|
|
47
|
+
function v(e, t) {
|
|
48
|
+
let n = e || t;
|
|
49
|
+
return l.useMemo(() => ({
|
|
50
|
+
placement: "title",
|
|
51
|
+
titleId: n
|
|
52
|
+
}), [n]);
|
|
53
|
+
}
|
|
54
|
+
function y(e) {
|
|
55
|
+
let r, i = [], a = [];
|
|
56
|
+
for (let { key: s, node: c } of t(e)) if (n(c, g)) {
|
|
57
|
+
if (!o(c.props.children)) continue;
|
|
58
|
+
r === void 0 ? r = {
|
|
59
|
+
key: s,
|
|
60
|
+
element: c
|
|
61
|
+
} : a.push({
|
|
62
|
+
key: s,
|
|
63
|
+
node: c,
|
|
64
|
+
extraTitle: !0
|
|
65
|
+
});
|
|
66
|
+
} else n(c, _) ? o(c.props.children) && i.push({
|
|
67
|
+
key: s,
|
|
68
|
+
element: c
|
|
69
|
+
}) : a.push({
|
|
70
|
+
key: s,
|
|
71
|
+
node: c,
|
|
72
|
+
extraTitle: !1
|
|
73
|
+
});
|
|
74
|
+
return {
|
|
75
|
+
title: r,
|
|
76
|
+
ownTitleId: r?.element.props.id,
|
|
77
|
+
actions: i,
|
|
78
|
+
body: a
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
//#endregion
|
|
82
|
+
export { p as ACTIONS_PLACEMENT, f as CONTENT_PLACEMENT, m as EXTRA_TITLE_PLACEMENT, _ as MessageBarActions, d as MessageBarPartContext, g as MessageBarTitle, y as partitionMessageBarChildren, v as useTitlePlacement };
|
|
83
|
+
|
|
84
|
+
//# sourceMappingURL=MessageBar.parts.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MessageBar.parts.mjs","names":["React","MessageBarPartContext","CONTENT_PLACEMENT","ACTIONS_PLACEMENT","EXTRA_TITLE_PLACEMENT","useMessageBarPart","reportMissingContext","componentName","MessageBarTitle","rest","part","placed","problem","warnOnce","id","cn","messageBarTitleClassNames","className","materialiseSlotContent","children","MessageBarActions","messageBarActionsClassNames","useTitlePlacement","titleId","ownTitleId","generatedTitleId","partitionMessageBarChildren","title","actions","body","flattenChildren","isElementOfType","node","slotRendersContent"],"sources":["../../../src/components/feedback/MessageBar.parts.tsx"],"sourcesContent":["import * as React from 'react';\nimport { flattenChildren, isElementOfType } from '../../lib/children';\nimport { messageBarActionsClassNames, messageBarTitleClassNames } from '../../lib/classNames';\nimport { cn } from '../../lib/cn';\nimport { reportMissingContext, warnOnce } from '../../lib/dev';\nimport { materialiseSlotContent, slotRendersContent } from '../../lib/slot';\n\n/** Properties for the MessageBarTitle sub-component. */\nexport interface MessageBarTitleProps extends React.HTMLAttributes<HTMLSpanElement> {\n /** Ref to the title `<span>`. */\n ref?: React.Ref<HTMLSpanElement>;\n}\n\n/** Properties for the MessageBarActions sub-component. */\nexport interface MessageBarActionsProps extends React.HTMLAttributes<HTMLDivElement> {\n /** Ref to the element that holds the actions. */\n ref?: React.Ref<HTMLDivElement>;\n}\n\n/**\n * Where a MessageBar put a part (C-CONTEXT: `null` outside every MessageBar). The bar provides\n * `'content'` around everything it renders and a more specific value around the parts that its\n * scan of its direct children placed; each part resets it to `'content'` for its own children, so\n * a part inside another part, or inside the app's own component, counts as not placed.\n */\nexport interface MessageBarPartContextValue {\n /**\n * `'title'`: the bar's title, first in the text column. `'actions'`: in the action area.\n * `'extra-title'`: a later title, left in the body. `'content'`: anywhere else inside the bar.\n */\n placement: 'title' | 'actions' | 'extra-title' | 'content';\n /** The id the placed title renders (its own `id`, else a generated one); `'title'` only. */\n titleId?: string;\n}\n\nexport const MessageBarPartContext = React.createContext<MessageBarPartContextValue | null>(null);\nMessageBarPartContext.displayName = 'MessageBarPartContext';\n\n/** Inside a bar but not placed by its scan (also the inert value in production, C-CONTEXT). */\nexport const CONTENT_PLACEMENT: MessageBarPartContextValue = { placement: 'content' };\n/** A `MessageBar.Actions` the bar placed in its action area. */\nexport const ACTIONS_PLACEMENT: MessageBarPartContextValue = { placement: 'actions' };\n/** A second or later `MessageBar.Title`, rendered where it is in the body. */\nexport const EXTRA_TITLE_PLACEMENT: MessageBarPartContextValue = { placement: 'extra-title' };\n\n/** C-CONTEXT: throws in development, logs once and returns an inert value in production. */\nfunction useMessageBarPart(componentName: string): MessageBarPartContextValue {\n const context = React.useContext(MessageBarPartContext);\n if (context) return context;\n reportMissingContext(componentName, '<MessageBar>');\n return CONTENT_PLACEMENT;\n}\n\n/**\n * The bar's title, read right after the severity text. Names the bar when the bar has a non-live\n * `role` (`region`, `group`). Must be a direct child of MessageBar (a Fragment there counts, and so\n * does a title written in a Server Component); anywhere else it renders where it is, without its\n * place or the naming (development warning). Give a bar one title: a second one renders as body\n * text (development warning). A title whose children render nothing is left out.\n *\n * Also exported as `MessageBarTitle` (import the flat name from React Server Components).\n */\nexport const MessageBarTitle = ({\n id,\n className,\n children,\n ref,\n ...rest\n}: MessageBarTitleProps) => {\n const part = useMessageBarPart('MessageBar.Title');\n const placed = part.placement === 'title';\n const problem: 'unscanned' | 'multiple' | null = placed\n ? null\n : part.placement === 'extra-title'\n ? 'multiple'\n : 'unscanned';\n React.useEffect(() => {\n if (problem === 'unscanned') {\n warnOnce(\n 'MessageBar.Title:unscanned',\n 'MessageBar.Title is not a direct child of MessageBar, so it is not placed first in the text. Make it a direct child.',\n );\n } else if (problem === 'multiple') {\n warnOnce(\n 'MessageBar.Title:multiple',\n 'MessageBar.Title: this MessageBar already has a title (its first MessageBar.Title among its direct children), so this one renders as body text. Give a bar one title.',\n );\n }\n }, [problem]);\n\n return (\n <span\n {...rest}\n ref={ref}\n id={(placed ? part.titleId : id) || undefined}\n className={cn(messageBarTitleClassNames.root, 'font-semibold', className)}\n >\n <MessageBarPartContext.Provider value={CONTENT_PLACEMENT}>\n {materialiseSlotContent(children)}\n </MessageBarPartContext.Provider>\n </span>\n );\n};\nMessageBarTitle.displayName = 'MessageBarTitle';\n\n/**\n * The bar's actions (Retry, Learn more): after the text on one row, on their own row under it in\n * the multiline layout. Must be a direct child of MessageBar (a Fragment there counts, and so does\n * a part written in a Server Component); anywhere else it renders where it is (development\n * warning). Actions whose children render nothing are left out, so the bar keeps its look without\n * actions. The actions have no role of their own: the bar is already the grouping.\n *\n * Also exported as `MessageBarActions` (import the flat name from React Server Components).\n */\nexport const MessageBarActions = ({\n className,\n children,\n ref,\n ...rest\n}: MessageBarActionsProps) => {\n const part = useMessageBarPart('MessageBar.Actions');\n const placed = part.placement === 'actions';\n React.useEffect(() => {\n if (!placed) {\n warnOnce(\n 'MessageBar.Actions:unscanned',\n 'MessageBar.Actions is not a direct child of MessageBar, so it is not placed in the action area. Make it a direct child.',\n );\n }\n }, [placed]);\n\n return (\n <div\n {...rest}\n ref={ref}\n className={cn(\n messageBarActionsClassNames.root,\n 'flex shrink-0 flex-wrap items-center gap-2',\n className,\n )}\n >\n <MessageBarPartContext.Provider value={CONTENT_PLACEMENT}>\n {materialiseSlotContent(children)}\n </MessageBarPartContext.Provider>\n </div>\n );\n};\nMessageBarActions.displayName = 'MessageBarActions';\n\n/** The context value of the placed title (C-MEMO): stable while its id is. */\nexport function useTitlePlacement(\n ownTitleId: string | undefined,\n generatedTitleId: string,\n): MessageBarPartContextValue {\n const titleId = ownTitleId || generatedTitleId;\n return React.useMemo<MessageBarPartContextValue>(\n () => ({ placement: 'title', titleId }),\n [titleId],\n );\n}\n\n/** How a MessageBar sorts its direct children (D15). */\nexport interface MessageBarPartition {\n /** The first `MessageBar.Title` whose children render content, with its flattened key. */\n title: { key: string; element: React.ReactElement<MessageBarTitleProps> } | undefined;\n /** The `id` the first title was given by its consumer, if any. */\n ownTitleId: string | undefined;\n /** Every `MessageBar.Actions` whose children render content, in order. */\n actions: Array<{ key: string; element: React.ReactElement<MessageBarActionsProps> }>;\n /** Everything else, in order; `extraTitle` marks a later title that renders content. */\n body: Array<{ key: string; node: React.ReactNode; extraTitle: boolean }>;\n}\n\n/**\n * The static scan of D15, during render (so the placement is in the server HTML): the direct\n * children with Fragments flattened, parts recognised by `isElementOfType` (a part written in a\n * Server Component arrives as a lazy reference). A part whose children render nothing\n * (`slotRendersContent`) is dropped.\n */\nexport function partitionMessageBarChildren(children: React.ReactNode): MessageBarPartition {\n let title: MessageBarPartition['title'];\n const actions: MessageBarPartition['actions'] = [];\n const body: MessageBarPartition['body'] = [];\n for (const { key, node } of flattenChildren(children)) {\n if (isElementOfType<MessageBarTitleProps>(node, MessageBarTitle)) {\n if (!slotRendersContent(node.props.children)) continue;\n if (title === undefined) title = { key, element: node };\n else body.push({ key, node, extraTitle: true });\n } else if (isElementOfType<MessageBarActionsProps>(node, MessageBarActions)) {\n if (slotRendersContent(node.props.children)) actions.push({ key, element: node });\n } else {\n body.push({ key, node, extraTitle: false });\n }\n }\n return { title, ownTitleId: title?.element.props.id, actions, body };\n}\n"],"mappings":";;;;;;;;;AAmCA,IAAaC,IAAwBD,EAAM,cAAiD,IAAI;AAChG,EAAsB,cAAc;AAGpC,IAAaE,IAAgD,EAAE,WAAW,UAAU,GAEvEC,IAAgD,EAAE,WAAW,UAAU,GAEvEC,IAAoD,EAAE,WAAW,cAAc;AAG5F,SAASC,EAAkB,GAAmD;CAI5E,OAHgBL,EAAM,WAAWC,CAC7B,MACJK,EAAqBC,GAAe,cAAc,GAC3CL;AACT;AAWA,IAAaM,KAAmB,EAC9B,OACA,cACA,aACA,QACA,GAAGC,QACuB;CAC1B,IAAMC,IAAOL,EAAkB,kBAAkB,GAC3CM,IAASD,EAAK,cAAc,SAC5BE,IAA2CD,IAC7C,OACAD,EAAK,cAAc,gBACjB,aACA;CAeN,OAdAV,EAAM,gBAAgB;EACpB,AAAIY,MAAY,cACdC,EACE,8BACA,sHACF,IACSD,MAAY,cACrBC,EACE,6BACA,uKACF;CAEJ,GAAG,CAACD,CAAO,CAAC,GAGV,kBAAC,QAAD;EACE,GAAIH;EACC;EACL,KAAKE,IAASD,EAAK,UAAUI,MAAO,KAAA;EACpC,WAAWC,EAAGC,EAA0B,MAAM,iBAAiBC,CAAS;EAExE,UAAA,kBAAChB,EAAsB,UAAvB;GAAgC,OAAOC;GACpC,UAAAgB,EAAuBC,CAAQ;EACF,CAAA;CAC5B,CAAA;AAEV;AACA,EAAgB,cAAc;AAW9B,IAAaC,KAAqB,EAChC,cACA,aACA,QACA,GAAGX,QACyB;CAE5B,IAAME,IADON,EAAkB,oBAChB,CAAA,CAAK,cAAc;CAUlC,OATAL,EAAM,gBAAgB;EACpB,AAAKW,KACHE,EACE,gCACA,yHACF;CAEJ,GAAG,CAACF,CAAM,CAAC,GAGT,kBAAC,OAAD;EACE,GAAIF;EACC;EACL,WAAWM,EACTM,EAA4B,MAC5B,8CACAJ,CACF;EAEA,UAAA,kBAAChB,EAAsB,UAAvB;GAAgC,OAAOC;GACpC,UAAAgB,EAAuBC,CAAQ;EACF,CAAA;CAC7B,CAAA;AAET;AACA,EAAkB,cAAc;AAGhC,SAAgBG,EACd,GACA,GAC4B;CAC5B,IAAMC,IAAUC,KAAcC;CAC9B,OAAOzB,EAAM,eACJ;EAAE,WAAW;EAAS;CAAQ,IACrC,CAACuB,CAAO,CACV;AACF;AAoBA,SAAgBG,EAA4B,GAAgD;CAC1F,IAAIC,GACEC,IAA0C,CAAC,GAC3CC,IAAoC,CAAC;CAC3C,KAAK,IAAM,EAAE,QAAK,aAAUC,EAAgBX,CAAQ,GAClD,IAAIY,EAAsCC,GAAMxB,CAAe,GAAG;EAChE,IAAI,CAACyB,EAAmBD,EAAK,MAAM,QAAQ,GAAG;EAC9C,AAAIL,MAAU,KAAA,IAAW,IAAQ;GAAE;GAAK,SAASK;EAAK,IACjDH,EAAK,KAAK;GAAE;GAAK;GAAM,YAAY;EAAK,CAAC;CAChD,OAAO,AAAIE,EAAwCC,GAAMZ,CAAiB,IACpEa,EAAmBD,EAAK,MAAM,QAAQ,KAAGJ,EAAQ,KAAK;EAAE;EAAK,SAASI;CAAK,CAAC,IAEhFH,EAAK,KAAK;EAAE;EAAK;EAAM,YAAY;CAAM,CAAC;CAG9C,OAAO;EAAE;EAAO,YAAYF,GAAO,QAAQ,MAAM;EAAI;EAAS;CAAK;AACrE"}
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs");let t=require("react");t=e.__toESM(t,1);var n=class{reflowing=!1;neededWidth=0;listeners=new Set;subscribe=e=>(this.listeners.add(e),()=>{this.listeners.delete(e)});getSnapshot=()=>this.reflowing?`multiline`:`singleline`;getServerSnapshot=()=>`singleline`;measure(e,t){if(this.reflowing){if(e.clientWidth<this.neededWidth)return;this.reflowing=!1,this.neededWidth=0}else{let n=t.scrollWidth-t.clientWidth;if(n<=0)return;this.reflowing=!0,this.neededWidth=e.clientWidth+n}this.emit()}reset(e=!0){this.reflowing&&(this.reflowing=!1,this.neededWidth=0,e&&this.emit())}connect(e,t){let n=[],r=()=>this.measure(e,t);if(typeof ResizeObserver<`u`){let t=0,i=new ResizeObserver(()=>{cancelAnimationFrame(t),t=requestAnimationFrame(r)});i.observe(e,{box:`border-box`}),n.push(()=>{i.disconnect(),cancelAnimationFrame(t)})}else typeof window<`u`&&(window.addEventListener(`resize`,r),n.push(()=>window.removeEventListener(`resize`,r)));if(typeof MutationObserver<`u`){let e=new MutationObserver(()=>{this.reflowing?this.reset():r()});e.observe(t,{childList:!0,subtree:!0,characterData:!0}),n.push(()=>e.disconnect())}return()=>{for(let e of n)e();this.reset(!1)}}emit(){for(let e of Array.from(this.listeners))e()}};function r(e,r,i){let[a]=t.useState(()=>new n),o=t.useSyncExternalStore(a.subscribe,a.getSnapshot,a.getServerSnapshot),[,s]=t.useReducer(e=>e+1,0);return t.useLayoutEffect(()=>{if(i&&e&&r)return a.connect(e,r)},[a,i,e,r]),t.useLayoutEffect(()=>{if(!i||!e||!r||a.getSnapshot()!==`singleline`)return;let t=a.subscribe(s);a.measure(e,r),t()}),i?o:`singleline`}exports.useMessageBarReflow=r;
|
|
2
|
+
//# sourceMappingURL=MessageBar.reflow.cjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MessageBar.reflow.cjs","names":["React","require_runtime","react","MessageBarReflowStore","listener","root","overflow","text","notify","cleanups","measure","frame","observer","mutations","cleanup","useMessageBarReflow","store","layout","forceRender","count","enabled","unsubscribe"],"sources":["../../../src/components/feedback/MessageBar.reflow.ts"],"sourcesContent":["import * as React from 'react';\n\n/** The layout an `'auto'` MessageBar with actions renders. */\nexport type MessageBarReflowLayout = 'singleline' | 'multiline';\n\n/**\n * One bar's measurement (spec D17): whether its text needs the multiline layout, and the bar width\n * at which the text fits on one line again. Read through `useSyncExternalStore`.\n */\nclass MessageBarReflowStore {\n private reflowing = false;\n /** The bar's client width at which its text fits on one line. */\n private neededWidth = 0;\n private readonly listeners = new Set<() => void>();\n\n subscribe = (listener: () => void): (() => void) => {\n this.listeners.add(listener);\n return () => {\n this.listeners.delete(listener);\n };\n };\n\n getSnapshot = (): MessageBarReflowLayout => (this.reflowing ? 'multiline' : 'singleline');\n\n /** The server HTML and hydration use the one-row layout. */\n getServerSnapshot = (): MessageBarReflowLayout => 'singleline';\n\n /**\n * The two-way rule. One row: text wider than its column (`scrollWidth > clientWidth`; the column\n * does not wrap while measured) switches to multiline and remembers the bar width it needed,\n * `root.clientWidth + text.scrollWidth - text.clientWidth`. Multiline: a bar at least that wide\n * switches back.\n */\n measure(root: HTMLElement, text: HTMLElement): void {\n if (this.reflowing) {\n if (root.clientWidth < this.neededWidth) return;\n this.reflowing = false;\n this.neededWidth = 0;\n } else {\n const overflow = text.scrollWidth - text.clientWidth;\n if (overflow <= 0) return;\n this.reflowing = true;\n this.neededWidth = root.clientWidth + overflow;\n }\n this.emit();\n }\n\n /** Forgets the measurement: the next render uses the one-row layout and measures again. */\n reset(notify = true): void {\n if (!this.reflowing) return;\n this.reflowing = false;\n this.neededWidth = 0;\n if (notify) this.emit();\n }\n\n /**\n * Observes `root` and `text` until the returned teardown runs, which also forgets the\n * measurement.\n * - The root's size (a ResizeObserver): measured in the next animation frame, so the layout\n * change never resizes the observed root while the observer is still delivering (browsers\n * report that as a loop error). Without ResizeObserver: window size changes.\n * - Text changed inside the column without a render of the bar (a MutationObserver): measured at\n * once in the one-row layout; in the multiline layout the measurement starts over from the\n * one-row layout (the render that follows measures before paint).\n */\n connect(root: HTMLElement, text: HTMLElement): () => void {\n const cleanups: Array<() => void> = [];\n const measure = () => this.measure(root, text);\n if (typeof ResizeObserver !== 'undefined') {\n let frame = 0;\n const observer = new ResizeObserver(() => {\n cancelAnimationFrame(frame);\n frame = requestAnimationFrame(measure);\n });\n observer.observe(root, { box: 'border-box' });\n cleanups.push(() => {\n observer.disconnect();\n cancelAnimationFrame(frame);\n });\n } else if (typeof window !== 'undefined') {\n window.addEventListener('resize', measure);\n cleanups.push(() => window.removeEventListener('resize', measure));\n }\n if (typeof MutationObserver !== 'undefined') {\n const mutations = new MutationObserver(() => {\n if (this.reflowing) this.reset();\n else measure();\n });\n mutations.observe(text, { childList: true, subtree: true, characterData: true });\n cleanups.push(() => mutations.disconnect());\n }\n return () => {\n for (const cleanup of cleanups) cleanup();\n // Silent: on unmount the layout cleanups run before useSyncExternalStore unsubscribes, and a\n // notification would schedule an update on a deleted fiber. A bar that stays mounted reads\n // the reset snapshot on its next render (useSyncExternalStore re-checks it after each commit).\n this.reset(false);\n };\n }\n\n private emit(): void {\n for (const listener of Array.from(this.listeners)) listener();\n }\n}\n\n/**\n * The layout of a MessageBar with `layout=\"auto\"` and actions: `'singleline'` on the server, on the\n * first client render and while the text fits on one line; `'multiline'` otherwise. `root` is the\n * bar's root element and `text` its text column, both held in state through callback refs\n * (C-POPUPS). With `enabled` false (every other bar) nothing is observed or measured and the result\n * is `'singleline'`.\n */\nexport function useMessageBarReflow(\n root: HTMLElement | null,\n text: HTMLElement | null,\n enabled: boolean,\n): MessageBarReflowLayout {\n const [store] = React.useState(() => new MessageBarReflowStore());\n const layout = React.useSyncExternalStore(\n store.subscribe,\n store.getSnapshot,\n store.getServerSnapshot,\n );\n const [, forceRender] = React.useReducer((count: number) => count + 1, 0);\n\n // The observers follow the elements. Their teardown forgets the measurement, so a bar that\n // measures again (its actions back, or `layout` back to 'auto') starts from one row.\n React.useLayoutEffect(() => {\n if (!enabled || !root || !text) return undefined;\n return store.connect(root, text);\n }, [store, enabled, root, text]);\n\n // After every commit in the one-row layout, before paint: useSyncExternalStore subscribes only in\n // a passive effect, which can run after the browser painted, so a change found here re-renders\n // through `forceRender` (the pattern of Overflow's `useIsOverflowing`).\n React.useLayoutEffect(() => {\n if (!enabled || !root || !text || store.getSnapshot() !== 'singleline') return;\n const unsubscribe = store.subscribe(forceRender);\n store.measure(root, text);\n unsubscribe();\n });\n\n return enabled ? layout : 'singleline';\n}\n"],"mappings":"6GASA,IAAMG,EAAN,KAA4B,CAC1B,UAAoB,GAEpB,YAAsB,EACtB,UAA6B,IAAI,IAEjC,UAAa,IACX,KAAK,UAAU,IAAIC,CAAQ,MACd,CACX,KAAK,UAAU,OAAOA,CAAQ,CAChC,GAGF,gBAA6C,KAAK,UAAY,YAAc,aAG5E,sBAAkD,aAQlD,QAAQ,EAAmB,EAAyB,CAClD,GAAI,KAAK,UAAW,CAClB,GAAIC,EAAK,YAAc,KAAK,YAAa,OACzC,KAAK,UAAY,GACjB,KAAK,YAAc,CACrB,KAAO,CACL,IAAMC,EAAWC,EAAK,YAAcA,EAAK,YACzC,GAAID,GAAY,EAAG,OACnB,KAAK,UAAY,GACjB,KAAK,YAAcD,EAAK,YAAcC,CACxC,CACA,KAAK,KAAK,CACZ,CAGA,MAAM,EAAS,GAAY,CACpB,KAAK,YACV,KAAK,UAAY,GACjB,KAAK,YAAc,EACfE,GAAQ,KAAK,KAAK,EACxB,CAYA,QAAQ,EAAmB,EAA+B,CACxD,IAAMC,EAA8B,CAAC,EAC/BC,MAAgB,KAAK,QAAQL,EAAME,CAAI,EAC7C,GAAI,OAAO,eAAmB,IAAa,CACzC,IAAII,EAAQ,EACNC,EAAW,IAAI,mBAAqB,CACxC,qBAAqBD,CAAK,EAC1B,EAAQ,sBAAsBD,CAAO,CACvC,CAAC,EACDE,EAAS,QAAQP,EAAM,CAAE,IAAK,YAAa,CAAC,EAC5CI,EAAS,SAAW,CAClBG,EAAS,WAAW,EACpB,qBAAqBD,CAAK,CAC5B,CAAC,CACH,MAAW,OAAO,OAAW,MAC3B,OAAO,iBAAiB,SAAUD,CAAO,EACzCD,EAAS,SAAW,OAAO,oBAAoB,SAAUC,CAAO,CAAC,GAEnE,GAAI,OAAO,iBAAqB,IAAa,CAC3C,IAAMG,EAAY,IAAI,qBAAuB,CACvC,KAAK,UAAW,KAAK,MAAM,EAC1BH,EAAQ,CACf,CAAC,EACDG,EAAU,QAAQN,EAAM,CAAE,UAAW,GAAM,QAAS,GAAM,cAAe,EAAK,CAAC,EAC/EE,EAAS,SAAWI,EAAU,WAAW,CAAC,CAC5C,CACA,UAAa,CACX,IAAK,IAAMC,KAAWL,EAAUK,EAAQ,EAIxC,KAAK,MAAM,EAAK,CAClB,CACF,CAEA,MAAqB,CACnB,IAAK,IAAMV,KAAY,MAAM,KAAK,KAAK,SAAS,EAAGA,EAAS,CAC9D,CACF,EASA,SAAgBW,EACd,EACA,EACA,EACwB,CACxB,GAAM,CAACC,GAAShB,EAAM,aAAe,IAAIG,CAAuB,EAC1Dc,EAASjB,EAAM,qBACnBgB,EAAM,UACNA,EAAM,YACNA,EAAM,iBACR,EACM,EAAGE,GAAelB,EAAM,WAAY,GAAkBmB,EAAQ,EAAG,CAAC,EAmBxE,OAfAjB,EAAM,oBAAsB,CAC1B,GAAKkB,GAAYf,GAASE,EAC1B,OAAOS,EAAM,QAAQX,EAAME,CAAI,CACjC,EAAG,CAACS,EAAOI,EAASf,EAAME,CAAI,CAAC,EAK/BL,EAAM,oBAAsB,CAC1B,GAAI,CAACkB,GAAW,CAACf,GAAQ,CAACE,GAAQS,EAAM,YAAY,IAAM,aAAc,OACxE,IAAMK,EAAcL,EAAM,UAAUE,CAAW,EAC/CF,EAAM,QAAQX,EAAME,CAAI,EACxBc,EAAY,CACd,CAAC,EAEMD,EAAUH,EAAS,YAC5B"}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import * as e from "react";
|
|
3
|
+
//#region src/components/feedback/MessageBar.reflow.ts
|
|
4
|
+
var t = class {
|
|
5
|
+
reflowing = !1;
|
|
6
|
+
neededWidth = 0;
|
|
7
|
+
listeners = /* @__PURE__ */ new Set();
|
|
8
|
+
subscribe = (e) => (this.listeners.add(e), () => {
|
|
9
|
+
this.listeners.delete(e);
|
|
10
|
+
});
|
|
11
|
+
getSnapshot = () => this.reflowing ? "multiline" : "singleline";
|
|
12
|
+
getServerSnapshot = () => "singleline";
|
|
13
|
+
measure(e, t) {
|
|
14
|
+
if (this.reflowing) {
|
|
15
|
+
if (e.clientWidth < this.neededWidth) return;
|
|
16
|
+
this.reflowing = !1, this.neededWidth = 0;
|
|
17
|
+
} else {
|
|
18
|
+
let n = t.scrollWidth - t.clientWidth;
|
|
19
|
+
if (n <= 0) return;
|
|
20
|
+
this.reflowing = !0, this.neededWidth = e.clientWidth + n;
|
|
21
|
+
}
|
|
22
|
+
this.emit();
|
|
23
|
+
}
|
|
24
|
+
reset(e = !0) {
|
|
25
|
+
this.reflowing && (this.reflowing = !1, this.neededWidth = 0, e && this.emit());
|
|
26
|
+
}
|
|
27
|
+
connect(e, t) {
|
|
28
|
+
let n = [], r = () => this.measure(e, t);
|
|
29
|
+
if (typeof ResizeObserver < "u") {
|
|
30
|
+
let t = 0, i = new ResizeObserver(() => {
|
|
31
|
+
cancelAnimationFrame(t), t = requestAnimationFrame(r);
|
|
32
|
+
});
|
|
33
|
+
i.observe(e, { box: "border-box" }), n.push(() => {
|
|
34
|
+
i.disconnect(), cancelAnimationFrame(t);
|
|
35
|
+
});
|
|
36
|
+
} else typeof window < "u" && (window.addEventListener("resize", r), n.push(() => window.removeEventListener("resize", r)));
|
|
37
|
+
if (typeof MutationObserver < "u") {
|
|
38
|
+
let e = new MutationObserver(() => {
|
|
39
|
+
this.reflowing ? this.reset() : r();
|
|
40
|
+
});
|
|
41
|
+
e.observe(t, {
|
|
42
|
+
childList: !0,
|
|
43
|
+
subtree: !0,
|
|
44
|
+
characterData: !0
|
|
45
|
+
}), n.push(() => e.disconnect());
|
|
46
|
+
}
|
|
47
|
+
return () => {
|
|
48
|
+
for (let e of n) e();
|
|
49
|
+
this.reset(!1);
|
|
50
|
+
};
|
|
51
|
+
}
|
|
52
|
+
emit() {
|
|
53
|
+
for (let e of Array.from(this.listeners)) e();
|
|
54
|
+
}
|
|
55
|
+
};
|
|
56
|
+
function n(n, r, i) {
|
|
57
|
+
let [a] = e.useState(() => new t()), o = e.useSyncExternalStore(a.subscribe, a.getSnapshot, a.getServerSnapshot), [, s] = e.useReducer((e) => e + 1, 0);
|
|
58
|
+
return e.useLayoutEffect(() => {
|
|
59
|
+
if (i && n && r) return a.connect(n, r);
|
|
60
|
+
}, [
|
|
61
|
+
a,
|
|
62
|
+
i,
|
|
63
|
+
n,
|
|
64
|
+
r
|
|
65
|
+
]), e.useLayoutEffect(() => {
|
|
66
|
+
if (!i || !n || !r || a.getSnapshot() !== "singleline") return;
|
|
67
|
+
let e = a.subscribe(s);
|
|
68
|
+
a.measure(n, r), e();
|
|
69
|
+
}), i ? o : "singleline";
|
|
70
|
+
}
|
|
71
|
+
//#endregion
|
|
72
|
+
export { n as useMessageBarReflow };
|
|
73
|
+
|
|
74
|
+
//# sourceMappingURL=MessageBar.reflow.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"MessageBar.reflow.mjs","names":["React","MessageBarReflowStore","listener","root","overflow","text","notify","cleanups","measure","frame","observer","mutations","cleanup","useMessageBarReflow","store","layout","forceRender","count","enabled","unsubscribe"],"sources":["../../../src/components/feedback/MessageBar.reflow.ts"],"sourcesContent":["import * as React from 'react';\n\n/** The layout an `'auto'` MessageBar with actions renders. */\nexport type MessageBarReflowLayout = 'singleline' | 'multiline';\n\n/**\n * One bar's measurement (spec D17): whether its text needs the multiline layout, and the bar width\n * at which the text fits on one line again. Read through `useSyncExternalStore`.\n */\nclass MessageBarReflowStore {\n private reflowing = false;\n /** The bar's client width at which its text fits on one line. */\n private neededWidth = 0;\n private readonly listeners = new Set<() => void>();\n\n subscribe = (listener: () => void): (() => void) => {\n this.listeners.add(listener);\n return () => {\n this.listeners.delete(listener);\n };\n };\n\n getSnapshot = (): MessageBarReflowLayout => (this.reflowing ? 'multiline' : 'singleline');\n\n /** The server HTML and hydration use the one-row layout. */\n getServerSnapshot = (): MessageBarReflowLayout => 'singleline';\n\n /**\n * The two-way rule. One row: text wider than its column (`scrollWidth > clientWidth`; the column\n * does not wrap while measured) switches to multiline and remembers the bar width it needed,\n * `root.clientWidth + text.scrollWidth - text.clientWidth`. Multiline: a bar at least that wide\n * switches back.\n */\n measure(root: HTMLElement, text: HTMLElement): void {\n if (this.reflowing) {\n if (root.clientWidth < this.neededWidth) return;\n this.reflowing = false;\n this.neededWidth = 0;\n } else {\n const overflow = text.scrollWidth - text.clientWidth;\n if (overflow <= 0) return;\n this.reflowing = true;\n this.neededWidth = root.clientWidth + overflow;\n }\n this.emit();\n }\n\n /** Forgets the measurement: the next render uses the one-row layout and measures again. */\n reset(notify = true): void {\n if (!this.reflowing) return;\n this.reflowing = false;\n this.neededWidth = 0;\n if (notify) this.emit();\n }\n\n /**\n * Observes `root` and `text` until the returned teardown runs, which also forgets the\n * measurement.\n * - The root's size (a ResizeObserver): measured in the next animation frame, so the layout\n * change never resizes the observed root while the observer is still delivering (browsers\n * report that as a loop error). Without ResizeObserver: window size changes.\n * - Text changed inside the column without a render of the bar (a MutationObserver): measured at\n * once in the one-row layout; in the multiline layout the measurement starts over from the\n * one-row layout (the render that follows measures before paint).\n */\n connect(root: HTMLElement, text: HTMLElement): () => void {\n const cleanups: Array<() => void> = [];\n const measure = () => this.measure(root, text);\n if (typeof ResizeObserver !== 'undefined') {\n let frame = 0;\n const observer = new ResizeObserver(() => {\n cancelAnimationFrame(frame);\n frame = requestAnimationFrame(measure);\n });\n observer.observe(root, { box: 'border-box' });\n cleanups.push(() => {\n observer.disconnect();\n cancelAnimationFrame(frame);\n });\n } else if (typeof window !== 'undefined') {\n window.addEventListener('resize', measure);\n cleanups.push(() => window.removeEventListener('resize', measure));\n }\n if (typeof MutationObserver !== 'undefined') {\n const mutations = new MutationObserver(() => {\n if (this.reflowing) this.reset();\n else measure();\n });\n mutations.observe(text, { childList: true, subtree: true, characterData: true });\n cleanups.push(() => mutations.disconnect());\n }\n return () => {\n for (const cleanup of cleanups) cleanup();\n // Silent: on unmount the layout cleanups run before useSyncExternalStore unsubscribes, and a\n // notification would schedule an update on a deleted fiber. A bar that stays mounted reads\n // the reset snapshot on its next render (useSyncExternalStore re-checks it after each commit).\n this.reset(false);\n };\n }\n\n private emit(): void {\n for (const listener of Array.from(this.listeners)) listener();\n }\n}\n\n/**\n * The layout of a MessageBar with `layout=\"auto\"` and actions: `'singleline'` on the server, on the\n * first client render and while the text fits on one line; `'multiline'` otherwise. `root` is the\n * bar's root element and `text` its text column, both held in state through callback refs\n * (C-POPUPS). With `enabled` false (every other bar) nothing is observed or measured and the result\n * is `'singleline'`.\n */\nexport function useMessageBarReflow(\n root: HTMLElement | null,\n text: HTMLElement | null,\n enabled: boolean,\n): MessageBarReflowLayout {\n const [store] = React.useState(() => new MessageBarReflowStore());\n const layout = React.useSyncExternalStore(\n store.subscribe,\n store.getSnapshot,\n store.getServerSnapshot,\n );\n const [, forceRender] = React.useReducer((count: number) => count + 1, 0);\n\n // The observers follow the elements. Their teardown forgets the measurement, so a bar that\n // measures again (its actions back, or `layout` back to 'auto') starts from one row.\n React.useLayoutEffect(() => {\n if (!enabled || !root || !text) return undefined;\n return store.connect(root, text);\n }, [store, enabled, root, text]);\n\n // After every commit in the one-row layout, before paint: useSyncExternalStore subscribes only in\n // a passive effect, which can run after the browser painted, so a change found here re-renders\n // through `forceRender` (the pattern of Overflow's `useIsOverflowing`).\n React.useLayoutEffect(() => {\n if (!enabled || !root || !text || store.getSnapshot() !== 'singleline') return;\n const unsubscribe = store.subscribe(forceRender);\n store.measure(root, text);\n unsubscribe();\n });\n\n return enabled ? layout : 'singleline';\n}\n"],"mappings":";;;AASA,IAAMC,IAAN,MAA4B;CAC1B,YAAoB;CAEpB,cAAsB;CACtB,4BAA6B,IAAI,IAAgB;CAEjD,aAAa,OACX,KAAK,UAAU,IAAIC,CAAQ,SACd;EACX,KAAK,UAAU,OAAOA,CAAQ;CAChC;CAGF,oBAA6C,KAAK,YAAY,cAAc;CAG5E,0BAAkD;CAQlD,QAAQ,GAAmB,GAAyB;EAClD,IAAI,KAAK,WAAW;GAClB,IAAIC,EAAK,cAAc,KAAK,aAAa;GAEzC,AADA,KAAK,YAAY,IACjB,KAAK,cAAc;EACrB,OAAO;GACL,IAAMC,IAAWC,EAAK,cAAcA,EAAK;GACzC,IAAID,KAAY,GAAG;GAEnB,AADA,KAAK,YAAY,IACjB,KAAK,cAAcD,EAAK,cAAcC;EACxC;EACA,KAAK,KAAK;CACZ;CAGA,MAAM,IAAS,IAAY;EACzB,AAAK,KAAK,cACV,KAAK,YAAY,IACjB,KAAK,cAAc,GACfE,KAAQ,KAAK,KAAK;CACxB;CAYA,QAAQ,GAAmB,GAA+B;EACxD,IAAMC,IAA8B,CAAC,GAC/BC,UAAgB,KAAK,QAAQL,GAAME,CAAI;EAC7C,IAAI,OAAO,iBAAmB,KAAa;GACzC,IAAII,IAAQ,GACNC,IAAW,IAAI,qBAAqB;IAExC,AADA,qBAAqBD,CAAK,GAC1B,IAAQ,sBAAsBD,CAAO;GACvC,CAAC;GAED,AADAE,EAAS,QAAQP,GAAM,EAAE,KAAK,aAAa,CAAC,GAC5CI,EAAS,WAAW;IAElB,AADAG,EAAS,WAAW,GACpB,qBAAqBD,CAAK;GAC5B,CAAC;EACH,OAAO,AAAI,OAAO,SAAW,QAC3B,OAAO,iBAAiB,UAAUD,CAAO,GACzCD,EAAS,WAAW,OAAO,oBAAoB,UAAUC,CAAO,CAAC;EAEnE,IAAI,OAAO,mBAAqB,KAAa;GAC3C,IAAMG,IAAY,IAAI,uBAAuB;IAC3C,AAAI,KAAK,YAAW,KAAK,MAAM,IAC1BH,EAAQ;GACf,CAAC;GAED,AADAG,EAAU,QAAQN,GAAM;IAAE,WAAW;IAAM,SAAS;IAAM,eAAe;GAAK,CAAC,GAC/EE,EAAS,WAAWI,EAAU,WAAW,CAAC;EAC5C;EACA,aAAa;GACX,KAAK,IAAMC,KAAWL,GAAU,EAAQ;GAIxC,KAAK,MAAM,EAAK;EAClB;CACF;CAEA,OAAqB;EACnB,KAAK,IAAML,KAAY,MAAM,KAAK,KAAK,SAAS,GAAG,EAAS;CAC9D;AACF;AASA,SAAgBW,EACd,GACA,GACA,GACwB;CACxB,IAAM,CAACC,KAASd,EAAM,eAAe,IAAIC,EAAsB,CAAC,GAC1Dc,IAASf,EAAM,qBACnBc,EAAM,WACNA,EAAM,aACNA,EAAM,iBACR,GACM,GAAGE,KAAehB,EAAM,YAAY,MAAkBiB,IAAQ,GAAG,CAAC;CAmBxE,OAfAjB,EAAM,sBAAsB;EAC1B,IAAKkB,KAAYf,KAASE,GAC1B,OAAOS,EAAM,QAAQX,GAAME,CAAI;CACjC,GAAG;EAACS;EAAOI;EAASf;EAAME;CAAI,CAAC,GAK/BL,EAAM,sBAAsB;EAC1B,IAAI,CAACkB,KAAW,CAACf,KAAQ,CAACE,KAAQS,EAAM,YAAY,MAAM,cAAc;EACxE,IAAMK,IAAcL,EAAM,UAAUE,CAAW;EAE/C,AADAF,EAAM,QAAQX,GAAME,CAAI,GACxBc,EAAY;CACd,CAAC,GAEMD,IAAUH,IAAS;AAC5B"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/icons.cjs");let n=require("react");n=e.__toESM(n,1);let r=require("react/jsx-runtime");var i={info:`Info:`,success:`Success:`,warning:`Warning:`,error:`Error:`},a={info:t.InfoIcon,success:t.SuccessIcon,warning:t.WarningIcon,error:t.ErrorIcon},o={info:`text-info-tint-foreground`,success:`text-success-tint-foreground`,warning:`text-warning-tint-foreground`,error:`text-error-tint-foreground`},s={info:`border-s-info`,success:`border-s-success`,warning:`border-s-warning`,error:`border-s-error`};function c(e,t){return t??i[e]}function l({status:e,size:t}){let n=a[e];return(0,r.jsx)(n,{size:t})}l.displayName=`StatusIcon`;function u({label:e}){return e?(0,r.jsx)(`span`,{className:`sr-only`,children:`${e} `}):null}u.displayName=`StatusText`,exports.STATUS_BORDER=s,exports.STATUS_ICON_COLOR=o,exports.STATUS_LABELS=i,exports.StatusIcon=l,exports.StatusText=u,exports.getStatusLabel=c;
|
|
1
|
+
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/icons.cjs");let n=require("react");n=e.__toESM(n,1);let r=require("react/jsx-runtime");var i={info:`Info:`,success:`Success:`,warning:`Warning:`,error:`Error:`},a={info:t.InfoIcon,success:t.SuccessIcon,warning:t.WarningIcon,error:t.ErrorIcon},o={info:`text-info-tint-foreground`,success:`text-success-tint-foreground`,warning:`text-warning-tint-foreground`,error:`text-error-tint-foreground`},s={info:`border-s-info`,success:`border-s-success`,warning:`border-s-warning`,error:`border-s-error`};function c(e,t){return t??i[e]}function l({status:e,size:t}){let n=a[e];return(0,r.jsx)(n,{size:t})}l.displayName=`StatusIcon`;function u({label:e,id:t}){return e?(0,r.jsx)(`span`,{id:t,className:`sr-only`,children:`${e} `}):null}u.displayName=`StatusText`,exports.STATUS_BORDER=s,exports.STATUS_ICON_COLOR=o,exports.STATUS_LABELS=i,exports.StatusIcon=l,exports.StatusText=u,exports.getStatusLabel=c;
|
|
2
2
|
//# sourceMappingURL=MessageBar.status.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MessageBar.status.cjs","names":["InfoIcon","SuccessIcon","WarningIcon","ErrorIcon","require_runtime","require_icons","react","react_jsx_runtime","STATUS_LABELS","STATUS_ICONS","STATUS_ICON_COLOR","STATUS_BORDER","getStatusLabel","statusLabel","status","StatusIcon","Icon","StatusText","label"],"sources":["../../../src/components/feedback/MessageBar.status.tsx"],"sourcesContent":["/**\n * Internal status building blocks shared by MessageBar and Toast (spec §5.7): the status icons and\n * the visually hidden status text that tells screen-reader users the severity\n * (feedback-navigation#4). Not exported from the package.\n */\nimport * as React from 'react';\nimport { ErrorIcon, InfoIcon, SuccessIcon, WarningIcon } from '../../lib/icons';\nimport type { IconComponent } from '../../lib/icons';\nimport type { Status } from '../../lib/types';\n\n/** Default visually hidden status text, read before the message (\"Warning: Disk almost full\"). */\nexport const STATUS_LABELS: Readonly<Record<Status, string>> = {\n info: 'Info:',\n success: 'Success:',\n warning: 'Warning:',\n error: 'Error:',\n};\n\nconst STATUS_ICONS: Readonly<Record<Status, IconComponent>> = {\n info: InfoIcon,\n success: SuccessIcon,\n warning: WarningIcon,\n error: ErrorIcon,\n};\n\n/**\n * Icon color per status. The `*-tint-foreground` tokens keep ≥ 4.5:1 on both the status tints\n * (MessageBar) and the page background (Toast) in every theme, unlike the `warning` fill.\n */\nexport const STATUS_ICON_COLOR: Readonly<Record<Status, string>> = {\n info: 'text-info-tint-foreground',\n success: 'text-success-tint-foreground',\n warning: 'text-warning-tint-foreground',\n error: 'text-error-tint-foreground',\n};\n\n/** Logical start border color per status. */\nexport const STATUS_BORDER: Readonly<Record<Status, string>> = {\n info: 'border-s-info',\n success: 'border-s-success',\n warning: 'border-s-warning',\n error: 'border-s-error',\n};\n\n/** The resolved status text: `statusLabel` when given (`''` hides it), else the default. */\nexport function getStatusLabel(status: Status, statusLabel: string | undefined): string {\n return statusLabel ?? STATUS_LABELS[status];\n}\n\n/** The default status glyph (decorative: `aria-hidden`, `currentColor`). */\nexport function StatusIcon({ status, size }: { status: Status; size?: number }) {\n const Icon = STATUS_ICONS[status];\n return <Icon size={size} />;\n}\nStatusIcon.displayName = 'StatusIcon';\n\n
|
|
1
|
+
{"version":3,"file":"MessageBar.status.cjs","names":["InfoIcon","SuccessIcon","WarningIcon","ErrorIcon","require_runtime","require_icons","react","react_jsx_runtime","STATUS_LABELS","STATUS_ICONS","STATUS_ICON_COLOR","STATUS_BORDER","getStatusLabel","statusLabel","status","StatusIcon","Icon","StatusText","label"],"sources":["../../../src/components/feedback/MessageBar.status.tsx"],"sourcesContent":["/**\n * Internal status building blocks shared by MessageBar and Toast (spec §5.7): the status icons and\n * the visually hidden status text that tells screen-reader users the severity\n * (feedback-navigation#4). Not exported from the package.\n */\nimport * as React from 'react';\nimport { ErrorIcon, InfoIcon, SuccessIcon, WarningIcon } from '../../lib/icons';\nimport type { IconComponent } from '../../lib/icons';\nimport type { Status } from '../../lib/types';\n\n/** Default visually hidden status text, read before the message (\"Warning: Disk almost full\"). */\nexport const STATUS_LABELS: Readonly<Record<Status, string>> = {\n info: 'Info:',\n success: 'Success:',\n warning: 'Warning:',\n error: 'Error:',\n};\n\nconst STATUS_ICONS: Readonly<Record<Status, IconComponent>> = {\n info: InfoIcon,\n success: SuccessIcon,\n warning: WarningIcon,\n error: ErrorIcon,\n};\n\n/**\n * Icon color per status. The `*-tint-foreground` tokens keep ≥ 4.5:1 on both the status tints\n * (MessageBar) and the page background (Toast) in every theme, unlike the `warning` fill.\n */\nexport const STATUS_ICON_COLOR: Readonly<Record<Status, string>> = {\n info: 'text-info-tint-foreground',\n success: 'text-success-tint-foreground',\n warning: 'text-warning-tint-foreground',\n error: 'text-error-tint-foreground',\n};\n\n/** Logical start border color per status. */\nexport const STATUS_BORDER: Readonly<Record<Status, string>> = {\n info: 'border-s-info',\n success: 'border-s-success',\n warning: 'border-s-warning',\n error: 'border-s-error',\n};\n\n/** The resolved status text: `statusLabel` when given (`''` hides it), else the default. */\nexport function getStatusLabel(status: Status, statusLabel: string | undefined): string {\n return statusLabel ?? STATUS_LABELS[status];\n}\n\n/** The default status glyph (decorative: `aria-hidden`, `currentColor`). */\nexport function StatusIcon({ status, size }: { status: Status; size?: number }) {\n const Icon = STATUS_ICONS[status];\n return <Icon size={size} />;\n}\nStatusIcon.displayName = 'StatusIcon';\n\n/**\n * Visually hidden status text, followed by a space so it reads apart from the message. `id` lets\n * a labelled MessageBar or a toast container point `aria-labelledby` at it; an empty label\n * renders nothing, so pass the id only while the text renders.\n */\nexport function StatusText({ label, id }: { label: string; id?: string }) {\n if (!label) return null;\n return (\n <span id={id} className=\"sr-only\">\n {`${label} `}\n </span>\n );\n}\nStatusText.displayName = 'StatusText';\n"],"mappings":"iLAWA,IAAaQ,EAAkD,CAC7D,KAAM,QACN,QAAS,WACT,QAAS,WACT,MAAO,QACT,EAEMC,EAAwD,CAC5D,KAAMT,EAAAA,SACN,QAASC,EAAAA,YACT,QAASC,EAAAA,YACT,MAAOC,EAAAA,SACT,EAMaO,EAAsD,CACjE,KAAM,4BACN,QAAS,+BACT,QAAS,+BACT,MAAO,4BACT,EAGaC,EAAkD,CAC7D,KAAM,gBACN,QAAS,mBACT,QAAS,mBACT,MAAO,gBACT,EAGA,SAAgBC,EAAe,EAAgB,EAAyC,CACtF,OAAOC,GAAeL,EAAcM,EACtC,CAGA,SAAgBC,EAAW,CAAE,SAAQ,QAA2C,CAC9E,IAAMC,EAAOP,EAAaK,GAC1B,OAAO,EAAAP,EAAA,IAAA,CAACS,EAAD,CAAY,MAAO,CAAA,CAC5B,CACA,EAAW,YAAc,aAOzB,SAAgBC,EAAW,CAAE,QAAO,MAAsC,CAExE,OADKC,GAEH,EAAAX,EAAA,IAAA,CAAC,OAAD,CAAU,KAAI,UAAU,UACrB,SAAA,GAAGW,EAAM,EACN,CAAA,EAJW,IAMrB,CACA,EAAW,YAAc"}
|
|
@@ -32,8 +32,9 @@ function u({ status: e, size: t }) {
|
|
|
32
32
|
return /* @__PURE__ */ i(n, { size: t });
|
|
33
33
|
}
|
|
34
34
|
u.displayName = "StatusIcon";
|
|
35
|
-
function d({ label: e }) {
|
|
35
|
+
function d({ label: e, id: t }) {
|
|
36
36
|
return e ? /* @__PURE__ */ i("span", {
|
|
37
|
+
id: t,
|
|
37
38
|
className: "sr-only",
|
|
38
39
|
children: `${e} `
|
|
39
40
|
}) : null;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MessageBar.status.mjs","names":["STATUS_LABELS","STATUS_ICONS","InfoIcon","SuccessIcon","WarningIcon","ErrorIcon","STATUS_ICON_COLOR","STATUS_BORDER","getStatusLabel","statusLabel","status","StatusIcon","Icon","StatusText","label"],"sources":["../../../src/components/feedback/MessageBar.status.tsx"],"sourcesContent":["/**\n * Internal status building blocks shared by MessageBar and Toast (spec §5.7): the status icons and\n * the visually hidden status text that tells screen-reader users the severity\n * (feedback-navigation#4). Not exported from the package.\n */\nimport * as React from 'react';\nimport { ErrorIcon, InfoIcon, SuccessIcon, WarningIcon } from '../../lib/icons';\nimport type { IconComponent } from '../../lib/icons';\nimport type { Status } from '../../lib/types';\n\n/** Default visually hidden status text, read before the message (\"Warning: Disk almost full\"). */\nexport const STATUS_LABELS: Readonly<Record<Status, string>> = {\n info: 'Info:',\n success: 'Success:',\n warning: 'Warning:',\n error: 'Error:',\n};\n\nconst STATUS_ICONS: Readonly<Record<Status, IconComponent>> = {\n info: InfoIcon,\n success: SuccessIcon,\n warning: WarningIcon,\n error: ErrorIcon,\n};\n\n/**\n * Icon color per status. The `*-tint-foreground` tokens keep ≥ 4.5:1 on both the status tints\n * (MessageBar) and the page background (Toast) in every theme, unlike the `warning` fill.\n */\nexport const STATUS_ICON_COLOR: Readonly<Record<Status, string>> = {\n info: 'text-info-tint-foreground',\n success: 'text-success-tint-foreground',\n warning: 'text-warning-tint-foreground',\n error: 'text-error-tint-foreground',\n};\n\n/** Logical start border color per status. */\nexport const STATUS_BORDER: Readonly<Record<Status, string>> = {\n info: 'border-s-info',\n success: 'border-s-success',\n warning: 'border-s-warning',\n error: 'border-s-error',\n};\n\n/** The resolved status text: `statusLabel` when given (`''` hides it), else the default. */\nexport function getStatusLabel(status: Status, statusLabel: string | undefined): string {\n return statusLabel ?? STATUS_LABELS[status];\n}\n\n/** The default status glyph (decorative: `aria-hidden`, `currentColor`). */\nexport function StatusIcon({ status, size }: { status: Status; size?: number }) {\n const Icon = STATUS_ICONS[status];\n return <Icon size={size} />;\n}\nStatusIcon.displayName = 'StatusIcon';\n\n
|
|
1
|
+
{"version":3,"file":"MessageBar.status.mjs","names":["STATUS_LABELS","STATUS_ICONS","InfoIcon","SuccessIcon","WarningIcon","ErrorIcon","STATUS_ICON_COLOR","STATUS_BORDER","getStatusLabel","statusLabel","status","StatusIcon","Icon","StatusText","label"],"sources":["../../../src/components/feedback/MessageBar.status.tsx"],"sourcesContent":["/**\n * Internal status building blocks shared by MessageBar and Toast (spec §5.7): the status icons and\n * the visually hidden status text that tells screen-reader users the severity\n * (feedback-navigation#4). Not exported from the package.\n */\nimport * as React from 'react';\nimport { ErrorIcon, InfoIcon, SuccessIcon, WarningIcon } from '../../lib/icons';\nimport type { IconComponent } from '../../lib/icons';\nimport type { Status } from '../../lib/types';\n\n/** Default visually hidden status text, read before the message (\"Warning: Disk almost full\"). */\nexport const STATUS_LABELS: Readonly<Record<Status, string>> = {\n info: 'Info:',\n success: 'Success:',\n warning: 'Warning:',\n error: 'Error:',\n};\n\nconst STATUS_ICONS: Readonly<Record<Status, IconComponent>> = {\n info: InfoIcon,\n success: SuccessIcon,\n warning: WarningIcon,\n error: ErrorIcon,\n};\n\n/**\n * Icon color per status. The `*-tint-foreground` tokens keep ≥ 4.5:1 on both the status tints\n * (MessageBar) and the page background (Toast) in every theme, unlike the `warning` fill.\n */\nexport const STATUS_ICON_COLOR: Readonly<Record<Status, string>> = {\n info: 'text-info-tint-foreground',\n success: 'text-success-tint-foreground',\n warning: 'text-warning-tint-foreground',\n error: 'text-error-tint-foreground',\n};\n\n/** Logical start border color per status. */\nexport const STATUS_BORDER: Readonly<Record<Status, string>> = {\n info: 'border-s-info',\n success: 'border-s-success',\n warning: 'border-s-warning',\n error: 'border-s-error',\n};\n\n/** The resolved status text: `statusLabel` when given (`''` hides it), else the default. */\nexport function getStatusLabel(status: Status, statusLabel: string | undefined): string {\n return statusLabel ?? STATUS_LABELS[status];\n}\n\n/** The default status glyph (decorative: `aria-hidden`, `currentColor`). */\nexport function StatusIcon({ status, size }: { status: Status; size?: number }) {\n const Icon = STATUS_ICONS[status];\n return <Icon size={size} />;\n}\nStatusIcon.displayName = 'StatusIcon';\n\n/**\n * Visually hidden status text, followed by a space so it reads apart from the message. `id` lets\n * a labelled MessageBar or a toast container point `aria-labelledby` at it; an empty label\n * renders nothing, so pass the id only while the text renders.\n */\nexport function StatusText({ label, id }: { label: string; id?: string }) {\n if (!label) return null;\n return (\n <span id={id} className=\"sr-only\">\n {`${label} `}\n </span>\n );\n}\nStatusText.displayName = 'StatusText';\n"],"mappings":";;;;;AAWA,IAAaA,IAAkD;CAC7D,MAAM;CACN,SAAS;CACT,SAAS;CACT,OAAO;AACT,GAEMC,IAAwD;CAC5D,MAAMC;CACN,SAASC;CACT,SAASC;CACT,OAAOC;AACT,GAMaC,IAAsD;CACjE,MAAM;CACN,SAAS;CACT,SAAS;CACT,OAAO;AACT,GAGaC,IAAkD;CAC7D,MAAM;CACN,SAAS;CACT,SAAS;CACT,OAAO;AACT;AAGA,SAAgBC,EAAe,GAAgB,GAAyC;CACtF,OAAOC,KAAeT,EAAcU;AACtC;AAGA,SAAgBC,EAAW,EAAE,WAAQ,WAA2C;CAC9E,IAAMC,IAAOX,EAAaS;CAC1B,OAAO,kBAACE,GAAD,EAAY,QAAO,CAAA;AAC5B;AACA,EAAW,cAAc;AAOzB,SAAgBC,EAAW,EAAE,UAAO,SAAsC;CAExE,OADKC,IAEH,kBAAC,QAAD;EAAU;EAAI,WAAU;EACrB,UAAA,GAAGA,EAAM;CACN,CAAA,IAJW;AAMrB;AACA,EAAW,cAAc"}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/dev.cjs"),r=require("../../hooks/useId.cjs"),
|
|
1
|
+
"use client";const e=require("../../_virtual/_rolldown/runtime.cjs"),t=require("../../lib/cn.cjs"),n=require("../../lib/dev.cjs"),r=require("../../lib/classNames.cjs"),i=require("../../hooks/useId.cjs"),a=require("../../hooks/useFieldControl.cjs"),o=require("../../lib/styles.cjs");let s=require("react");s=e.__toESM(s,1);let c=require("react/jsx-runtime");var l={brand:`bg-primary`,success:`bg-success`,warning:`bg-severe`,error:`bg-error`},u={error:`error`,warning:`warning`,success:`success`};function d(e){return typeof e==`string`&&e.trim()!==``}var f=({value:e,max:f=100,label:p,showLabel:m,color:h,id:g,"aria-describedby":_,"aria-invalid":v,"aria-required":y,className:b,ref:x,...S})=>{let C=i.useId(`progress-label`),w=i.useId(`progress`),T=a.useFieldContext(),E=a.useFieldControl({id:g??(T?w:void 0),"aria-describedby":_},{labelable:!1}),D=T?T.validationState??(T.invalid?`error`:`none`):`none`,O=h??u[D]??`brand`,k=e===void 0,A=Number.isFinite(f)&&f>0,j=k||Number.isFinite(e),M=!k&&A&&j?Math.min(f,Math.max(0,e)):0,N=A?M/f*100:0,P=d(p),F=d(S[`aria-label`]),I=d(S[`aria-labelledby`]),L=E[`aria-labelledby`],R=!P&&!F&&!I&&d(L);s.useEffect(()=>{n.isDev&&(!P&&!F&&!I&&!R&&n.warnOnce(`ProgressBar:name`,"ProgressBar: a progress bar needs an accessible name. Pass `label` (add `showLabel` to show it), `aria-label` or `aria-labelledby`."),m&&!P&&n.warnOnce(`ProgressBar:show-label`,"ProgressBar: `showLabel` renders the `label` prop, which is empty."),A||n.warnOnce(`ProgressBar:max`,`ProgressBar: \`max\` must be a finite number greater than 0 (got ${String(f)}); the bar renders 0%.`),j||n.warnOnce(`ProgressBar:value`,`ProgressBar: \`value\` must be a finite number (got ${String(e)}); the bar renders 0%.`))},[P,F,I,R,m,A,j,f,e]);let z=!!(m&&P),B={role:`progressbar`,"aria-valuenow":k?void 0:M,"aria-valuemin":0,"aria-valuemax":A?f:100,"data-color":O};E.id!==void 0&&(B.id=E.id),E[`aria-describedby`]!==void 0&&(B[`aria-describedby`]=E[`aria-describedby`]),!F&&!I&&(z?B[`aria-labelledby`]=C:P?B[`aria-label`]=p:R&&(B[`aria-labelledby`]=L));for(let[e,t]of Object.entries(S))t!==void 0&&(e!==`aria-label`&&e!==`aria-labelledby`||d(t))&&(B[e]=t);let V=(0,c.jsx)(`div`,{...B,ref:x,className:t.cn(r.progressBarClassNames.root,`h-2 overflow-hidden rounded-full bg-track`,`forced-colors:border`,o.forcedColors.border,b),children:(0,c.jsx)(`div`,{className:t.cn(r.progressBarClassNames.bar,`h-full rounded-full`,l[O],o.forcedColors.selectedLeaf,k&&`w-2/5 animate-wave-indeterminate wave-rtl:animate-wave-indeterminate-rtl motion-reduce:w-full motion-reduce:translate-x-0 motion-reduce:animate-wave-pulse wave-rtl:motion-reduce:animate-wave-pulse`),style:k?void 0:{width:`${N}%`}})});return z?(0,c.jsxs)(`div`,{className:`flex flex-col gap-1`,children:[(0,c.jsx)(`span`,{id:C,className:t.cn(r.progressBarClassNames.label,`text-body-1 text-foreground`),children:p}),V]}):V};f.displayName=`ProgressBar`,exports.ProgressBar=f;
|
|
2
2
|
//# sourceMappingURL=ProgressBar.cjs.map
|