@boostdev/design-system-components 2.14.1 → 2.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +20 -15
- package/dist/client.cjs +271 -205
- package/dist/client.css +808 -648
- package/dist/client.d.cts +19 -4
- package/dist/client.d.ts +19 -4
- package/dist/client.js +206 -139
- package/dist/index.cjs +271 -205
- package/dist/index.css +808 -648
- package/dist/index.d.cts +19 -4
- package/dist/index.d.ts +19 -4
- package/dist/index.js +206 -139
- package/dist/web-components/chunk-2DHW2WJZ.js +154 -0
- package/dist/web-components/{chunk-LDIPCTRN.js → chunk-2MJTO2IW.js} +48 -2
- package/dist/web-components/{chunk-3WAV6MDN.js → chunk-3FSGP35V.js} +1 -0
- package/dist/web-components/{chunk-KA3VPKMY.js → chunk-4MB2ICSK.js} +1 -0
- package/dist/web-components/{chunk-IDSM74LM.js → chunk-6XL5P76D.js} +3 -3
- package/dist/web-components/{chunk-P24JYC5V.js → chunk-7VXRMCAL.js} +10 -4
- package/dist/web-components/{chunk-CUKQ2L5B.js → chunk-AGI6YQRC.js} +9 -16
- package/dist/web-components/chunk-BDRV452N.js +51 -0
- package/dist/web-components/{chunk-3AY2YKCM.js → chunk-CKCPV347.js} +1 -0
- package/dist/web-components/{chunk-HBLJ4SLY.js → chunk-DD3OUXNG.js} +5 -5
- package/dist/web-components/{chunk-RVF7W653.js → chunk-DGOCPKHI.js} +30 -10
- package/dist/web-components/{chunk-2OLVQUBU.js → chunk-EYCW7TKB.js} +8 -15
- package/dist/web-components/{chunk-VANAKB6D.js → chunk-GPJWLAKU.js} +33 -16
- package/dist/web-components/{chunk-VED2DFJ6.js → chunk-GQNQBEYR.js} +8 -15
- package/dist/web-components/{chunk-WFVKU4GX.js → chunk-IKAJLROF.js} +49 -4
- package/dist/web-components/{chunk-RSZ3BWBK.js → chunk-KSK4RZZQ.js} +30 -7
- package/dist/web-components/{chunk-FEDABOR5.js → chunk-LHFUXZ52.js} +7 -15
- package/dist/web-components/{chunk-M3ECULRH.js → chunk-RBF7WPLI.js} +10 -8
- package/dist/web-components/{chunk-6G22I2CK.js → chunk-RZH5IVB5.js} +31 -1
- package/dist/web-components/chunk-SRKQ6GST.js +40 -0
- package/dist/web-components/{chunk-5HUAFCU6.js → chunk-TJV7UIXC.js} +7 -0
- package/dist/web-components/{chunk-J3HVUIUH.js → chunk-XI2U6U26.js} +8 -15
- package/dist/web-components/{chunk-JH6LQKLK.js → chunk-XJU7KITO.js} +8 -15
- package/dist/web-components/{chunk-XIZWAWMJ.js → chunk-XTPUKUN5.js} +16 -6
- package/dist/web-components/{chunk-JV5QT2OU.js → chunk-YLDQOESI.js} +27 -13
- package/dist/web-components/globals.js +1 -1
- package/dist/web-components/index.d.ts +1 -0
- package/dist/web-components/index.js +34 -29
- package/dist/web-components/interaction/bds-button.js +1 -1
- package/dist/web-components/interaction/bds-dropdown-menu-group.d.ts +41 -0
- package/dist/web-components/interaction/bds-dropdown-menu-group.js +7 -0
- package/dist/web-components/interaction/bds-dropdown-menu-item.d.ts +14 -1
- package/dist/web-components/interaction/bds-dropdown-menu-item.js +1 -1
- package/dist/web-components/interaction/bds-dropdown-menu.d.ts +2 -1
- package/dist/web-components/interaction/bds-dropdown-menu.js +1 -1
- package/dist/web-components/interaction/bds-tab.d.ts +5 -0
- package/dist/web-components/interaction/bds-tab.js +1 -1
- package/dist/web-components/interaction/bds-tooltip.js +1 -1
- package/dist/web-components/interaction/form/bds-checkbox-group.d.ts +6 -0
- package/dist/web-components/interaction/form/bds-checkbox-group.js +2 -1
- package/dist/web-components/interaction/form/bds-checkbox.js +1 -1
- package/dist/web-components/interaction/form/bds-combobox.js +2 -1
- package/dist/web-components/interaction/form/bds-form-input.js +2 -1
- package/dist/web-components/interaction/form/bds-number-input.js +2 -1
- package/dist/web-components/interaction/form/bds-radio-group.d.ts +5 -0
- package/dist/web-components/interaction/form/bds-radio-group.js +2 -1
- package/dist/web-components/interaction/form/bds-radio.js +1 -1
- package/dist/web-components/interaction/form/bds-select.js +2 -1
- package/dist/web-components/interaction/form/bds-slider.js +2 -1
- package/dist/web-components/interaction/form/bds-switch.js +1 -1
- package/dist/web-components/interaction/form/bds-textarea.js +2 -1
- package/dist/web-components/ui/bds-alert.d.ts +8 -1
- package/dist/web-components/ui/bds-alert.js +1 -1
- package/dist/web-components/ui/bds-avatar.d.ts +11 -0
- package/dist/web-components/ui/bds-avatar.js +1 -1
- package/dist/web-components/ui/bds-notification-banner.d.ts +14 -1
- package/dist/web-components/ui/bds-notification-banner.js +1 -1
- package/dist/web-components/ui/bds-section-header.d.ts +6 -0
- package/dist/web-components/ui/bds-section-header.js +1 -1
- package/dist/web-components/ui/bds-separator.js +1 -1
- package/dist/web-components/ui/bds-table.js +1 -1
- package/package.json +6 -2
- package/src/components/interaction/Button/Button.mdx +7 -0
- package/src/components/interaction/Button/Button.module.css +17 -9
- package/src/components/interaction/Button/Button.stories.tsx +28 -0
- package/src/components/interaction/DropdownMenu/DropdownMenu.mdx +35 -4
- package/src/components/interaction/DropdownMenu/DropdownMenu.module.css +58 -10
- package/src/components/interaction/DropdownMenu/DropdownMenu.spec.tsx +114 -1
- package/src/components/interaction/DropdownMenu/DropdownMenu.stories.tsx +25 -0
- package/src/components/interaction/DropdownMenu/DropdownMenu.tsx +69 -17
- package/src/components/interaction/form/Checkbox/Checkbox.module.css +1 -0
- package/src/components/interaction/form/Checkbox/Checkbox.spec.tsx +7 -0
- package/src/components/interaction/form/CheckboxGroup/CheckboxGroup.mdx +1 -0
- package/src/components/interaction/form/CheckboxGroup/CheckboxGroup.module.css +7 -0
- package/src/components/interaction/form/CheckboxGroup/CheckboxGroup.spec.tsx +22 -0
- package/src/components/interaction/form/CheckboxGroup/CheckboxGroup.tsx +1 -1
- package/src/components/interaction/form/Combobox/Combobox.module.css +1 -0
- package/src/components/interaction/form/Combobox/Combobox.spec.tsx +7 -0
- package/src/components/interaction/form/FormInput/FormInput.mdx +9 -0
- package/src/components/interaction/form/FormInput/FormInput.module.css +1 -0
- package/src/components/interaction/form/FormInput/FormInput.spec.tsx +7 -0
- package/src/components/interaction/form/NumberInput/NumberInput.module.css +1 -0
- package/src/components/interaction/form/NumberInput/NumberInput.spec.tsx +7 -0
- package/src/components/interaction/form/Radio/Radio.module.css +1 -0
- package/src/components/interaction/form/Radio/Radio.spec.tsx +7 -0
- package/src/components/interaction/form/RadioGroup/RadioGroup.mdx +1 -0
- package/src/components/interaction/form/RadioGroup/RadioGroup.module.css +7 -0
- package/src/components/interaction/form/RadioGroup/RadioGroup.spec.tsx +22 -0
- package/src/components/interaction/form/RadioGroup/RadioGroup.tsx +1 -1
- package/src/components/interaction/form/Select/Select.module.css +1 -0
- package/src/components/interaction/form/Select/Select.spec.tsx +7 -0
- package/src/components/interaction/form/Switch/Switch.module.css +1 -0
- package/src/components/interaction/form/Switch/Switch.spec.tsx +7 -0
- package/src/components/interaction/form/Textarea/Textarea.module.css +1 -0
- package/src/components/interaction/form/Textarea/Textarea.spec.tsx +7 -0
- package/src/components/interaction/form/atoms/Message.module.css +14 -3
- package/src/components/interaction/form/atoms/Message.spec.tsx +22 -0
- package/src/components/interaction/form/atoms/Message.tsx +5 -0
- package/src/components/layout/SectionHeader/SectionHeader.mdx +18 -5
- package/src/components/layout/SectionHeader/SectionHeader.module.css +35 -14
- package/src/components/layout/SectionHeader/SectionHeader.spec.tsx +44 -0
- package/src/components/layout/SectionHeader/SectionHeader.stories.tsx +5 -0
- package/src/components/layout/SectionHeader/SectionHeader.tsx +3 -1
- package/src/components/ui/Alert/Alert.mdx +11 -0
- package/src/components/ui/Alert/Alert.module.css +30 -1
- package/src/components/ui/Alert/Alert.spec.tsx +21 -0
- package/src/components/ui/Alert/Alert.stories.tsx +20 -0
- package/src/components/ui/Alert/Alert.tsx +8 -1
- package/src/components/ui/Avatar/Avatar.mdx +22 -2
- package/src/components/ui/Avatar/Avatar.module.css +29 -2
- package/src/components/ui/Avatar/Avatar.spec.tsx +26 -0
- package/src/components/ui/Avatar/Avatar.stories.tsx +23 -0
- package/src/components/ui/Avatar/Avatar.tsx +4 -2
- package/src/components/ui/Avatar/avatarTone.spec.ts +41 -0
- package/src/components/ui/Avatar/avatarTone.ts +22 -0
- package/src/components/ui/Collapsible/Collapsible.module.css +1 -2
- package/src/components/ui/NotificationBanner/NotificationBanner.mdx +14 -0
- package/src/components/ui/NotificationBanner/NotificationBanner.module.css +31 -1
- package/src/components/ui/NotificationBanner/NotificationBanner.spec.tsx +29 -0
- package/src/components/ui/NotificationBanner/NotificationBanner.stories.tsx +25 -0
- package/src/components/ui/NotificationBanner/NotificationBanner.tsx +15 -1
- package/src/components/ui/Separator/Separator.mdx +1 -0
- package/src/components/ui/Separator/Separator.module.css +6 -0
- package/src/components/ui/Separator/Separator.spec.tsx +19 -0
- package/src/components/ui/Separator/Separator.stories.tsx +15 -0
- package/src/components/ui/Table/Table.mdx +4 -1
- package/src/components/ui/Table/Table.module.css +7 -7
- package/src/components/ui/Table/Table.spec.tsx +11 -0
- package/src/components/ui/Tabs/Tabs.mdx +11 -5
- package/src/components/ui/Tabs/Tabs.module.css +23 -5
- package/src/components/ui/Tabs/Tabs.spec.tsx +39 -0
- package/src/components/ui/Tabs/Tabs.tsx +2 -1
- package/src/components/ui/Tabs/getNodeText.spec.tsx +23 -0
- package/src/components/ui/Tabs/getNodeText.ts +13 -0
- package/src/components/ui/Tooltip/Tooltip.mdx +6 -3
- package/src/components/ui/Tooltip/Tooltip.module.css +6 -2
- package/src/components/ui/Tooltip/Tooltip.spec.tsx +10 -0
- package/src/components/ui/Tooltip/Tooltip.stories.tsx +13 -0
- package/src/css/bdc.css +5 -2
- package/src/css/bdc.spec.ts +65 -0
- package/src/stories/DesignSystem/Borders.mdx +17 -9
- package/src/web-components/globals.ts +10 -4
- package/src/web-components/index.ts +1 -0
- package/src/web-components/interaction/BdsAccordion.mdx +1 -1
- package/src/web-components/interaction/BdsAccordion.stories.tsx +1 -1
- package/src/web-components/interaction/BdsButton.mdx +9 -1
- package/src/web-components/interaction/BdsButton.stories.tsx +42 -1
- package/src/web-components/interaction/BdsCollapsible.mdx +1 -1
- package/src/web-components/interaction/BdsCollapsible.stories.tsx +1 -1
- package/src/web-components/interaction/BdsDialog.mdx +1 -1
- package/src/web-components/interaction/BdsDialog.stories.tsx +1 -1
- package/src/web-components/interaction/BdsDrawer.mdx +1 -1
- package/src/web-components/interaction/BdsDrawer.stories.tsx +1 -1
- package/src/web-components/interaction/BdsDropdownMenu.mdx +62 -6
- package/src/web-components/interaction/BdsDropdownMenu.stories.tsx +32 -7
- package/src/web-components/interaction/BdsPopover.mdx +1 -1
- package/src/web-components/interaction/BdsPopover.stories.tsx +1 -1
- package/src/web-components/interaction/BdsSkipLink.mdx +1 -1
- package/src/web-components/interaction/BdsSkipLink.stories.tsx +1 -1
- package/src/web-components/interaction/BdsTabs.mdx +10 -1
- package/src/web-components/interaction/BdsTabs.stories.tsx +1 -1
- package/src/web-components/interaction/BdsToastProvider.mdx +1 -1
- package/src/web-components/interaction/BdsToastProvider.stories.tsx +1 -1
- package/src/web-components/interaction/BdsTooltip.mdx +13 -5
- package/src/web-components/interaction/BdsTooltip.stories.tsx +12 -12
- package/src/web-components/interaction/bds-button.ts +16 -6
- package/src/web-components/interaction/bds-dropdown-menu-group.ts +72 -0
- package/src/web-components/interaction/bds-dropdown-menu-item.ts +65 -17
- package/src/web-components/interaction/bds-dropdown-menu.spec.ts +135 -0
- package/src/web-components/interaction/bds-dropdown-menu.ts +5 -4
- package/src/web-components/interaction/bds-tab.spec.ts +34 -2
- package/src/web-components/interaction/bds-tab.ts +31 -6
- package/src/web-components/interaction/bds-tooltip.spec.ts +16 -0
- package/src/web-components/interaction/bds-tooltip.ts +10 -8
- package/src/web-components/interaction/form/BdsCheckbox.mdx +5 -1
- package/src/web-components/interaction/form/BdsCheckbox.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsCheckboxGroup.mdx +5 -1
- package/src/web-components/interaction/form/BdsCheckboxGroup.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsCombobox.mdx +5 -1
- package/src/web-components/interaction/form/BdsCombobox.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsFieldGroup.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsFileInput.mdx +1 -1
- package/src/web-components/interaction/form/BdsFileInput.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsFormInput.mdx +8 -1
- package/src/web-components/interaction/form/BdsFormInput.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsNumberInput.mdx +5 -1
- package/src/web-components/interaction/form/BdsNumberInput.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsRadio.mdx +5 -1
- package/src/web-components/interaction/form/BdsRadio.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsRadioGroup.mdx +5 -1
- package/src/web-components/interaction/form/BdsRadioGroup.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsSegmentedControl.mdx +1 -1
- package/src/web-components/interaction/form/BdsSegmentedControl.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsSelect.mdx +5 -1
- package/src/web-components/interaction/form/BdsSelect.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsSlider.mdx +5 -1
- package/src/web-components/interaction/form/BdsSlider.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsSwitch.mdx +5 -1
- package/src/web-components/interaction/form/BdsSwitch.stories.tsx +1 -1
- package/src/web-components/interaction/form/BdsTextarea.mdx +5 -1
- package/src/web-components/interaction/form/BdsTextarea.stories.tsx +1 -1
- package/src/web-components/interaction/form/bds-checkbox-group.spec.ts +32 -3
- package/src/web-components/interaction/form/bds-checkbox-group.ts +33 -17
- package/src/web-components/interaction/form/bds-checkbox.ts +1 -0
- package/src/web-components/interaction/form/bds-combobox.ts +6 -16
- package/src/web-components/interaction/form/bds-form-input.ts +6 -16
- package/src/web-components/interaction/form/bds-number-input.ts +6 -16
- package/src/web-components/interaction/form/bds-radio-group.spec.ts +32 -3
- package/src/web-components/interaction/form/bds-radio-group.ts +26 -14
- package/src/web-components/interaction/form/bds-radio.ts +1 -0
- package/src/web-components/interaction/form/bds-select.ts +6 -16
- package/src/web-components/interaction/form/bds-slider.ts +5 -16
- package/src/web-components/interaction/form/bds-switch.ts +1 -0
- package/src/web-components/interaction/form/bds-textarea.ts +6 -16
- package/src/web-components/interaction/form/field-message.spec.ts +62 -0
- package/src/web-components/interaction/form/field-message.ts +55 -0
- package/src/web-components/layout/BdsGrid.mdx +1 -1
- package/src/web-components/layout/BdsGrid.stories.tsx +1 -1
- package/src/web-components/layout/BdsGridItem.mdx +1 -1
- package/src/web-components/layout/BdsGridItem.stories.tsx +1 -1
- package/src/web-components/ui/BdsAlert.mdx +19 -1
- package/src/web-components/ui/BdsAlert.stories.tsx +29 -3
- package/src/web-components/ui/BdsAvatar.mdx +20 -3
- package/src/web-components/ui/BdsAvatar.stories.tsx +25 -2
- package/src/web-components/ui/BdsBadge.mdx +1 -1
- package/src/web-components/ui/BdsBadge.stories.tsx +1 -1
- package/src/web-components/ui/BdsBreadcrumb.mdx +1 -1
- package/src/web-components/ui/BdsBreadcrumb.stories.tsx +1 -1
- package/src/web-components/ui/BdsButtonContainer.mdx +1 -1
- package/src/web-components/ui/BdsButtonContainer.stories.tsx +1 -1
- package/src/web-components/ui/BdsCalendar.mdx +1 -1
- package/src/web-components/ui/BdsCalendar.stories.tsx +1 -1
- package/src/web-components/ui/BdsCalendarRange.mdx +1 -1
- package/src/web-components/ui/BdsCalendarRange.stories.tsx +1 -1
- package/src/web-components/ui/BdsCard.mdx +1 -1
- package/src/web-components/ui/BdsCard.stories.tsx +1 -1
- package/src/web-components/ui/BdsCarousel.mdx +1 -1
- package/src/web-components/ui/BdsCarousel.stories.tsx +1 -1
- package/src/web-components/ui/BdsDescriptionList.mdx +1 -1
- package/src/web-components/ui/BdsDescriptionList.stories.tsx +1 -1
- package/src/web-components/ui/BdsIconWrapper.mdx +1 -1
- package/src/web-components/ui/BdsIconWrapper.stories.tsx +1 -1
- package/src/web-components/ui/BdsLink.mdx +1 -1
- package/src/web-components/ui/BdsLink.stories.tsx +1 -1
- package/src/web-components/ui/BdsLoading.mdx +1 -1
- package/src/web-components/ui/BdsLoading.stories.tsx +1 -1
- package/src/web-components/ui/BdsNotificationBanner.mdx +10 -1
- package/src/web-components/ui/BdsNotificationBanner.stories.tsx +29 -2
- package/src/web-components/ui/BdsPagination.mdx +1 -1
- package/src/web-components/ui/BdsPagination.stories.tsx +1 -1
- package/src/web-components/ui/BdsProgress.mdx +1 -1
- package/src/web-components/ui/BdsProgress.stories.tsx +1 -1
- package/src/web-components/ui/BdsProgressCircle.mdx +1 -1
- package/src/web-components/ui/BdsProgressCircle.stories.tsx +1 -1
- package/src/web-components/ui/BdsRating.mdx +1 -1
- package/src/web-components/ui/BdsRating.stories.tsx +1 -1
- package/src/web-components/ui/BdsSectionHeader.mdx +18 -6
- package/src/web-components/ui/BdsSectionHeader.stories.tsx +10 -2
- package/src/web-components/ui/BdsSeparator.mdx +2 -1
- package/src/web-components/ui/BdsSeparator.stories.tsx +13 -1
- package/src/web-components/ui/BdsSkeleton.mdx +1 -1
- package/src/web-components/ui/BdsSkeleton.stories.tsx +1 -1
- package/src/web-components/ui/BdsTable.mdx +5 -1
- package/src/web-components/ui/BdsTable.stories.tsx +1 -1
- package/src/web-components/ui/BdsTypography.mdx +1 -1
- package/src/web-components/ui/BdsTypography.stories.tsx +1 -1
- package/src/web-components/ui/bds-alert.spec.ts +27 -0
- package/src/web-components/ui/bds-alert.ts +34 -1
- package/src/web-components/ui/bds-avatar.spec.ts +47 -0
- package/src/web-components/ui/bds-avatar.ts +36 -3
- package/src/web-components/ui/bds-notification-banner.spec.ts +45 -0
- package/src/web-components/ui/bds-notification-banner.ts +53 -1
- package/src/web-components/ui/bds-section-header.spec.ts +36 -3
- package/src/web-components/ui/bds-section-header.ts +32 -10
- package/src/web-components/ui/bds-separator.spec.ts +8 -0
- package/src/web-components/ui/bds-separator.ts +7 -0
- package/src/web-components/ui/bds-table.spec.ts +11 -0
- package/src/web-components/ui/bds-table.ts +5 -5
- package/dist/web-components/chunk-QZAIRJ75.js +0 -111
package/src/css/bdc.css
CHANGED
|
@@ -9,6 +9,8 @@
|
|
|
9
9
|
* --bdc-outline_* — tokens that directly map to CSS outline sub-properties
|
|
10
10
|
*
|
|
11
11
|
* @property declarations must be top-level (not inside @layer).
|
|
12
|
+
* The :root defaults live in boostdev.tokens.semantic so a consumer can override them in
|
|
13
|
+
* boostdev.tokens.override. --bdc-outline_width inherits so a :root value reaches components.
|
|
12
14
|
* --bdc_color uses inherits: false so each element owns its own colour instance,
|
|
13
15
|
* enabling per-element transition: --bdc_color for focus/error state animations.
|
|
14
16
|
* ─────────────────────────────────────────────────────────────────────────────── */
|
|
@@ -22,7 +24,7 @@
|
|
|
22
24
|
|
|
23
25
|
@property --bdc-outline_width {
|
|
24
26
|
syntax: '<length>';
|
|
25
|
-
inherits:
|
|
27
|
+
inherits: true;
|
|
26
28
|
initial-value: 1px;
|
|
27
29
|
}
|
|
28
30
|
|
|
@@ -46,7 +48,7 @@
|
|
|
46
48
|
initial-value: 0 0 0 0 transparent;
|
|
47
49
|
}
|
|
48
50
|
|
|
49
|
-
@layer boostdev.
|
|
51
|
+
@layer boostdev.tokens.semantic {
|
|
50
52
|
:root {
|
|
51
53
|
/* border: none by default — outline provides the visual edge */
|
|
52
54
|
--bdc-outline_border: none;
|
|
@@ -66,6 +68,7 @@
|
|
|
66
68
|
|
|
67
69
|
/* Outline geometry */
|
|
68
70
|
--bdc-outline_width: 1px;
|
|
71
|
+
--bdc-outline_width--error: 2px;
|
|
69
72
|
--bdc-outline_offset: -1px; /* available for consumer use; bdc borders now use inset box-shadow */
|
|
70
73
|
--bdc-outline_radius: var(--bds-border_radius--xs);
|
|
71
74
|
--bdc-outline_radius--l: 1.5em;
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { readFileSync } from 'node:fs';
|
|
2
|
+
import { resolve } from 'node:path';
|
|
3
|
+
import { describe, expect, it } from 'vitest';
|
|
4
|
+
|
|
5
|
+
const read = (path: string): string => readFileSync(resolve(__dirname, path), 'utf8');
|
|
6
|
+
|
|
7
|
+
const sources = {
|
|
8
|
+
'bdc.css': read('./bdc.css'),
|
|
9
|
+
'globals.ts': read('../web-components/globals.ts'),
|
|
10
|
+
} as const;
|
|
11
|
+
|
|
12
|
+
/** Returns the text between the braces of `@layer boostdev.tokens.semantic { ... }`. */
|
|
13
|
+
const semanticLayerBody = (source: string): string | undefined => {
|
|
14
|
+
const start = source.indexOf('@layer boostdev.tokens.semantic');
|
|
15
|
+
if (start === -1) return undefined;
|
|
16
|
+
const open = source.indexOf('{', start);
|
|
17
|
+
const body = [...source.slice(open)].reduce<{ depth: number; end: number }>(
|
|
18
|
+
(acc, ch, i) => {
|
|
19
|
+
if (acc.end !== -1) return acc;
|
|
20
|
+
const depth = acc.depth + (ch === '{' ? 1 : ch === '}' ? -1 : 0);
|
|
21
|
+
return { depth, end: depth === 0 ? i : -1 };
|
|
22
|
+
},
|
|
23
|
+
{ depth: 0, end: -1 },
|
|
24
|
+
);
|
|
25
|
+
return source.slice(open + 1, open + body.end);
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
const rootDeclarations = (source: string): string[] =>
|
|
29
|
+
[...(semanticLayerBody(source) ?? '').matchAll(/^\s*(--[\w-]+)\s*:/gm)].map((m) => m[1] ?? '');
|
|
30
|
+
|
|
31
|
+
describe.each(Object.entries(sources))('%s', (_name, source) => {
|
|
32
|
+
it('puts the :root defaults in boostdev.tokens.semantic', () => {
|
|
33
|
+
const body = semanticLayerBody(source);
|
|
34
|
+
expect(body).toBeDefined();
|
|
35
|
+
expect(body).toContain(':root');
|
|
36
|
+
expect(body).toContain('--bdc-color_active:');
|
|
37
|
+
expect(body).toContain('--bdc_color--error:');
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
it('does not put the :root defaults in boostdev.component', () => {
|
|
41
|
+
expect(source).not.toContain('@layer boostdev.component');
|
|
42
|
+
});
|
|
43
|
+
|
|
44
|
+
it('registers --bdc-outline_width as inheriting', () => {
|
|
45
|
+
expect(source).toMatch(/@property --bdc-outline_width\s*\{[^}]*inherits:\s*true/);
|
|
46
|
+
});
|
|
47
|
+
|
|
48
|
+
it('keeps the per-element tokens non-inheriting', () => {
|
|
49
|
+
['--bdc_color', '--bdc-outline_offset', '--bdc-outline_radius', '--bdc-outline_shadow'].forEach((token) => {
|
|
50
|
+
expect(source).toMatch(new RegExp(`@property ${token}\\s*\\{[^}]*inherits:\\s*false`));
|
|
51
|
+
});
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
it('declares the error outline width', () => {
|
|
55
|
+
expect(source).toContain('--bdc-outline_width--error: 2px;');
|
|
56
|
+
});
|
|
57
|
+
});
|
|
58
|
+
|
|
59
|
+
describe('bdc.css and globals.ts', () => {
|
|
60
|
+
it('declare the same set of :root custom properties', () => {
|
|
61
|
+
expect([...rootDeclarations(sources['globals.ts'])].sort()).toEqual(
|
|
62
|
+
[...rootDeclarations(sources['bdc.css'])].sort(),
|
|
63
|
+
);
|
|
64
|
+
});
|
|
65
|
+
});
|
|
@@ -123,23 +123,31 @@ See `src/components/ui/Accordion/Accordion.module.css` for a shipped example of
|
|
|
123
123
|
|
|
124
124
|
## Consumer overrides
|
|
125
125
|
|
|
126
|
-
|
|
126
|
+
The `:root` defaults of the `bdc` tokens (`--bdc_color--focus`, `--bdc_color--error`, `--bdc-color_active*`, `--bdc-color_on-active*`, `--bdc-outline_width`, `--bdc-outline_width--error`, `--bds-outline_default`, `--bds-outline_offset`) live in `@layer boostdev.tokens.semantic`, so they can be set in `@layer boostdev.tokens.override`:
|
|
127
127
|
|
|
128
128
|
```css
|
|
129
|
-
/* Scoped to a single component instance */
|
|
130
|
-
.my-context .my-input {
|
|
131
|
-
--bdc_color: var(--bds-color_warning);
|
|
132
|
-
}
|
|
133
|
-
|
|
134
|
-
/* Override globally via the token layer */
|
|
135
129
|
@layer boostdev.tokens.override {
|
|
136
130
|
:root {
|
|
137
|
-
--
|
|
131
|
+
--bdc-color_active: var(--bds-color_green);
|
|
132
|
+
--bdc_color--focus: var(--bds-color_green);
|
|
133
|
+
--bdc-outline_width: 2px;
|
|
138
134
|
}
|
|
139
135
|
}
|
|
140
136
|
```
|
|
141
137
|
|
|
142
|
-
|
|
138
|
+
The `bdc` defaults now share the `boostdev.tokens.semantic` layer with the foundation, so load the component stylesheet after the foundation stylesheet for the solid focus ring to win (the documented import order already does this). `--bdc-outline_radius` is registered with `inherits: false` and set by each component itself, so it cannot be set on `:root`.
|
|
139
|
+
|
|
140
|
+
`--bdc-outline_width` is registered with `inherits: true`, so a value on `:root` or on a wrapper reaches the components inside it.
|
|
141
|
+
|
|
142
|
+
`--bdc_color` is per element by design (`inherits: false`): every component owns its own instance so its state colour can transition. Do not set it on `:root`; that has no effect. Change a component's rest border colour through the component's own hook instead:
|
|
143
|
+
|
|
144
|
+
```css
|
|
145
|
+
.my-menu {
|
|
146
|
+
--dropdown_border-color: var(--bds-color_warning);
|
|
147
|
+
}
|
|
148
|
+
```
|
|
149
|
+
|
|
150
|
+
To change width or radius for one element:
|
|
143
151
|
|
|
144
152
|
```css
|
|
145
153
|
.my-card {
|
|
@@ -14,7 +14,7 @@ const bdcCss = `
|
|
|
14
14
|
|
|
15
15
|
@property --bdc-outline_width {
|
|
16
16
|
syntax: '<length>';
|
|
17
|
-
inherits:
|
|
17
|
+
inherits: true;
|
|
18
18
|
initial-value: 1px;
|
|
19
19
|
}
|
|
20
20
|
|
|
@@ -36,7 +36,7 @@ const bdcCss = `
|
|
|
36
36
|
initial-value: 0 0 0 0 transparent;
|
|
37
37
|
}
|
|
38
38
|
|
|
39
|
-
@layer boostdev.
|
|
39
|
+
@layer boostdev.tokens.semantic {
|
|
40
40
|
:root {
|
|
41
41
|
--bdc-outline_border: none;
|
|
42
42
|
|
|
@@ -47,14 +47,20 @@ const bdcCss = `
|
|
|
47
47
|
/* Active / selected state colours — override these to theme all filled form controls globally */
|
|
48
48
|
--bdc-color_active: var(--bds-color_interactive);
|
|
49
49
|
--bdc-color_on-active: var(--bds-color_on-interactive);
|
|
50
|
-
--bdc-color_active--subtle:
|
|
51
|
-
--bdc-
|
|
50
|
+
--bdc-color_active--subtle: var(--bds-color_blue--subtle);
|
|
51
|
+
--bdc-color_on-active--subtle: var(--bds-color_on-blue--subtle);
|
|
52
|
+
--bdc-color_active--strong: var(--bds-color_interactive_on-bg);
|
|
53
|
+
--bdc-color_on-active--strong: var(--bds-color_on-blue--strong);
|
|
52
54
|
|
|
53
55
|
--bdc-outline_width: 1px;
|
|
56
|
+
--bdc-outline_width--error: 2px;
|
|
54
57
|
--bdc-outline_offset: -1px; /* available for consumer use; bdc borders now use inset box-shadow */
|
|
55
58
|
--bdc-outline_radius: var(--bds-border_radius--xs);
|
|
56
59
|
--bdc-outline_radius--l: 1.5em;
|
|
57
60
|
--bdc-outline_shadow: 0 0 0 0 transparent;
|
|
61
|
+
|
|
62
|
+
--bds-outline_default: 2px solid var(--bds-color_interactive);
|
|
63
|
+
--bds-outline_offset: 2px;
|
|
58
64
|
}
|
|
59
65
|
}
|
|
60
66
|
`;
|
|
@@ -77,3 +77,4 @@ export { BdsCalendar } from './ui/bds-calendar';
|
|
|
77
77
|
export { BdsCalendarRange } from './ui/bds-calendar-range';
|
|
78
78
|
export { BdsDropdownMenu } from './interaction/bds-dropdown-menu';
|
|
79
79
|
export { BdsDropdownMenuItem } from './interaction/bds-dropdown-menu-item';
|
|
80
|
+
export { BdsDropdownMenuGroup } from './interaction/bds-dropdown-menu-group';
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsAccordion.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Accordion custom element. Coordinates open/closed state across `<bds-accordion-item>` children; by default only one item is open at a time.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -61,7 +61,7 @@ function BdsAccordionStory({
|
|
|
61
61
|
const meta = {
|
|
62
62
|
title: 'Web Components/UI/Accordion',
|
|
63
63
|
component: BdsAccordionStory,
|
|
64
|
-
tags: ['!stable', '
|
|
64
|
+
tags: ['!stable', 'alpha'],
|
|
65
65
|
parameters: { layout: 'padded' },
|
|
66
66
|
argTypes: {
|
|
67
67
|
allowMultiple: { control: 'boolean' },
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsButton.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic button custom element. Renders as `<button>` or `<a>` depending on whether `href` is set. Matches the React `Button` component in variants, sizes, and theming.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -54,6 +54,13 @@ Slot an SVG (or any element) into `icon-start` or `icon-end`:
|
|
|
54
54
|
<Canvas of={Stories.WithIconStart} />
|
|
55
55
|
<Canvas of={Stories.WithIconEnd} />
|
|
56
56
|
|
|
57
|
+
### Icon offset across sizes
|
|
58
|
+
|
|
59
|
+
The gap between an icon and the button edge (`--button_icon-offset`) is half the size's inline padding by default, so it scales automatically with `size` and with the responsive space tokens at wider viewports. Set `--button_icon-offset` on the host or an ancestor to override it — it inherits across the shadow boundary.
|
|
60
|
+
|
|
61
|
+
<Canvas of={Stories.IconOffsetMatrix} />
|
|
62
|
+
<Canvas of={Stories.IconOffsetOverride} />
|
|
63
|
+
|
|
57
64
|
### Icon-only (1:1 aspect ratio)
|
|
58
65
|
|
|
59
66
|
Set the `is-icon-only` attribute to render a square button with equal `var(--bds-space_xxs)` padding on both axes. Composable with any `variant`. Always pair with `aria-label` — there's no visible label text for assistive tech to read.
|
|
@@ -107,6 +114,7 @@ Set the `is-icon-only` attribute to render a square button with equal `var(--bds
|
|
|
107
114
|
|----------|-------------|
|
|
108
115
|
| `--button_color` | Identity colour — fills the default variant, outlines the outline variant |
|
|
109
116
|
| `--button_on-color` | Text/icon colour on the button surface. Pair with `--button_color` |
|
|
117
|
+
| `--button_icon-offset` | How far the icon slots pull into the padding (optical correction). Defaults to half the inline padding for the current `size`, so it scales with `size` and the responsive space tokens. Inherits across the shadow boundary — set it on the host or an ancestor. |
|
|
110
118
|
|
|
111
119
|
## Form participation
|
|
112
120
|
|
|
@@ -101,7 +101,7 @@ type BdsButtonStoryArgs = Omit<BdsButtonProps, 'iconStart' | 'iconEnd'> & {
|
|
|
101
101
|
const meta: Meta<BdsButtonStoryArgs> = {
|
|
102
102
|
title: 'Web Components/Interaction/Button',
|
|
103
103
|
component: BdsButton,
|
|
104
|
-
tags: ['!stable', '
|
|
104
|
+
tags: ['!stable', 'alpha'],
|
|
105
105
|
parameters: { layout: 'centered' },
|
|
106
106
|
argTypes: {
|
|
107
107
|
variant: {
|
|
@@ -210,3 +210,44 @@ export const AllIconOnly: Story = {
|
|
|
210
210
|
</div>
|
|
211
211
|
),
|
|
212
212
|
};
|
|
213
|
+
|
|
214
|
+
/**
|
|
215
|
+
* Every size × icon position × variant combination, mirroring the React
|
|
216
|
+
* `IconOffsetMatrix` story. The icon-to-edge offset (`--button_icon-offset`,
|
|
217
|
+
* defaulting to half the size's inline padding) is set inside the shadow DOM,
|
|
218
|
+
* so this also confirms React and the web component stay pixel-identical.
|
|
219
|
+
*/
|
|
220
|
+
export const IconOffsetMatrix: Story = {
|
|
221
|
+
render: () => (
|
|
222
|
+
<div style={{ display: 'flex', flexDirection: 'column', gap: '16px' }}>
|
|
223
|
+
{(['small', 'medium', 'large'] as const).map(s => (
|
|
224
|
+
<div key={s} style={{ display: 'flex', gap: '12px', flexWrap: 'wrap', alignItems: 'center' }}>
|
|
225
|
+
{(['default', 'outline'] as const).flatMap(v => [
|
|
226
|
+
<BdsButton key={`${v}-${s}-start`} variant={v} size={s} iconStart={CheckIcon}>
|
|
227
|
+
{v} {s} start
|
|
228
|
+
</BdsButton>,
|
|
229
|
+
<BdsButton key={`${v}-${s}-end`} variant={v} size={s} iconEnd={ArrowRightEnd}>
|
|
230
|
+
{v} {s} end
|
|
231
|
+
</BdsButton>,
|
|
232
|
+
])}
|
|
233
|
+
</div>
|
|
234
|
+
))}
|
|
235
|
+
</div>
|
|
236
|
+
),
|
|
237
|
+
};
|
|
238
|
+
|
|
239
|
+
/**
|
|
240
|
+
* `--button_icon-offset` set on a plain wrapper `<div>` (light DOM, an
|
|
241
|
+
* ancestor of the `<bds-button>` host) inherits across the shadow boundary
|
|
242
|
+
* and overrides the default half-padding calculation inside the shadow tree —
|
|
243
|
+
* confirming the token is a real public override point for the web component.
|
|
244
|
+
*/
|
|
245
|
+
export const IconOffsetOverride: Story = {
|
|
246
|
+
render: () => (
|
|
247
|
+
<div style={{ '--button_icon-offset': '4px' } as React.CSSProperties}>
|
|
248
|
+
<BdsButton size="large" iconStart={CheckIcon}>
|
|
249
|
+
Fixed 4px offset
|
|
250
|
+
</BdsButton>
|
|
251
|
+
</div>
|
|
252
|
+
),
|
|
253
|
+
};
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsCollapsible.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Collapsible custom element. Wraps a native `<details>`/`<summary>` pair for built-in toggle behaviour with design-system styling and a `bds-toggle` event.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -25,7 +25,7 @@ function BdsCollapsible({
|
|
|
25
25
|
const meta = {
|
|
26
26
|
title: 'Web Components/UI/Collapsible',
|
|
27
27
|
component: BdsCollapsible,
|
|
28
|
-
tags: ['!stable', '
|
|
28
|
+
tags: ['!stable', 'alpha'],
|
|
29
29
|
parameters: { layout: 'padded' },
|
|
30
30
|
argTypes: {
|
|
31
31
|
open: { control: 'boolean' },
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsDialog.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Dialog custom element. Wraps a native `<dialog>` element with `showModal()` / `close()` lifecycle, backdrop-click to dismiss, Escape key handling, Tab focus trapping, and the Invoker Commands API (custom commands).
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -53,7 +53,7 @@ function BdsDialog({
|
|
|
53
53
|
const meta = {
|
|
54
54
|
title: 'Web Components/Interaction/Dialog',
|
|
55
55
|
component: BdsDialog,
|
|
56
|
-
tags: ['!stable', '
|
|
56
|
+
tags: ['!stable', 'alpha'],
|
|
57
57
|
parameters: { layout: 'centered' },
|
|
58
58
|
argTypes: {
|
|
59
59
|
triggerLabel: { control: 'text' },
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsDrawer.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Drawer (slide-in panel) custom element. Same modal infrastructure as `<bds-dialog>` but positioned as a side panel that slides in from either side of the viewport.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -54,7 +54,7 @@ function BdsDrawer({
|
|
|
54
54
|
const meta = {
|
|
55
55
|
title: 'Web Components/Interaction/Drawer',
|
|
56
56
|
component: BdsDrawer,
|
|
57
|
-
tags: ['!stable', '
|
|
57
|
+
tags: ['!stable', 'alpha'],
|
|
58
58
|
parameters: { layout: 'centered' },
|
|
59
59
|
argTypes: {
|
|
60
60
|
side: { control: 'select', options: ['left', 'right'] },
|
|
@@ -5,9 +5,9 @@ import * as Stories from './BdsDropdownMenu.stories';
|
|
|
5
5
|
|
|
6
6
|
# <bds-dropdown-menu>
|
|
7
7
|
|
|
8
|
-
Framework-agnostic Dropdown Menu custom element. A trigger-anchored menu panel with keyboard navigation, light-dismiss, and support for disabled and destructive items.
|
|
8
|
+
Framework-agnostic Dropdown Menu custom element. A trigger-anchored menu panel with keyboard navigation, light-dismiss, and support for disabled and destructive items, shortcut hints and labelled groups.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -45,6 +45,9 @@ Or in HTML without a bundler:
|
|
|
45
45
|
### With disabled item
|
|
46
46
|
<Canvas of={Stories.WithDisabledItem} />
|
|
47
47
|
|
|
48
|
+
### With groups
|
|
49
|
+
<Canvas of={Stories.WithGroups} />
|
|
50
|
+
|
|
48
51
|
### All placements
|
|
49
52
|
<Canvas of={Stories.AllPlacements} />
|
|
50
53
|
|
|
@@ -57,17 +60,37 @@ Or in HTML without a bundler:
|
|
|
57
60
|
| Property | Default | Description |
|
|
58
61
|
|----------|---------|-------------|
|
|
59
62
|
| `--dropdown_border` | `none` | Real CSS `border` on the panel (in addition to the bdc inset outline) |
|
|
63
|
+
| `--dropdown_padding` | `--bds-space_xxs` | Panel padding on all sides |
|
|
64
|
+
| `--dropdown_border-color` | `--bds-color_on-bg--as-surface` | Panel outline colour (the bdc inset outline) |
|
|
60
65
|
| `--dropdown_radius` | `--bdc-outline_radius` (`--bds-border_radius--s`) | Panel corner radius |
|
|
61
66
|
| `--dropdown_color` | `--bds-color_bg` | Panel background colour |
|
|
62
67
|
| `--dropdown_on-color` | `--bds-color_on-bg` | Panel text colour |
|
|
63
|
-
| `--dropdown_shadow` | `--bds-
|
|
68
|
+
| `--dropdown_shadow` | `--bds-shadow_l` | Panel elevation shadow, layered behind the inset border |
|
|
64
69
|
|
|
65
70
|
## CSS Custom Properties — `<bds-dropdown-menu-item>`
|
|
66
71
|
|
|
67
72
|
| Property | Default | Description |
|
|
68
73
|
|----------|---------|-------------|
|
|
69
|
-
| `--dropdown_item-
|
|
70
|
-
| `--dropdown_item-
|
|
74
|
+
| `--dropdown_item-padding` | `--bds-space_xs --bds-space_s` | Item padding |
|
|
75
|
+
| `--dropdown_item-radius` | `--bds-border_radius--xs` | Item corner radius |
|
|
76
|
+
| `--dropdown_item-font-size` | `--bds-font_size--body` | Item font size |
|
|
77
|
+
| `--dropdown_item-bg--hover` | `--bds-color_primary--subtle` | Item background on hover and keyboard focus |
|
|
78
|
+
| `--dropdown_item-color--hover` | `--bds-color_on-primary--subtle` | Item text colour on hover and keyboard focus |
|
|
79
|
+
| `--dropdown_item-opacity--disabled` | `0.4` | Opacity of a disabled item |
|
|
80
|
+
| `--dropdown_item-color--destructive` | `--bds-color_error_on-bg` | Destructive item text colour |
|
|
81
|
+
| `--dropdown_item-bg--destructive-hover` | `--bds-color_error--subtle` | Destructive item background on hover and focus |
|
|
82
|
+
| `--dropdown_item-color--destructive-hover` | `--bds-color_on-error--subtle` | Destructive item text colour on hover and focus |
|
|
83
|
+
| `--dropdown_shortcut-color` | `--bds-color_on-bg--muted` | Shortcut hint colour |
|
|
84
|
+
| `--dropdown_shortcut-font-size` | `--bds-font_size--body--s` | Shortcut hint font size |
|
|
85
|
+
|
|
86
|
+
## CSS Custom Properties — `<bds-dropdown-menu-group>`
|
|
87
|
+
|
|
88
|
+
| Property | Default | Description |
|
|
89
|
+
|----------|---------|-------------|
|
|
90
|
+
| `--dropdown_group-label-font-size` | `--bds-font_size--body--s` | Group label font size |
|
|
91
|
+
| `--dropdown_group-label-font-weight` | `--bds-font_weight--bold` | Group label font weight |
|
|
92
|
+
| `--dropdown_group-label-color` | `--bds-color_on-bg--muted` | Group label colour |
|
|
93
|
+
| `--dropdown_group-label-padding` | `--bds-space_xs --bds-space_s --bds-space_xxs` | Group label padding |
|
|
71
94
|
|
|
72
95
|
## Attributes — `<bds-dropdown-menu>`
|
|
73
96
|
|
|
@@ -83,20 +106,34 @@ Or in HTML without a bundler:
|
|
|
83
106
|
| `value` | string | `""` | Value emitted in `bds-select` event detail |
|
|
84
107
|
| `disabled` | boolean | `false` | Prevents interaction; item is excluded from keyboard navigation |
|
|
85
108
|
| `destructive` | boolean | `false` | Renders the item in a destructive (error colour) style |
|
|
109
|
+
| `shortcut` | string | `""` | Shortcut as display text at the inline end; `aria-hidden`, the consumer wires the actual key |
|
|
110
|
+
|
|
111
|
+
## Attributes — `<bds-dropdown-menu-group>`
|
|
112
|
+
|
|
113
|
+
| Attribute | Type | Default | Description |
|
|
114
|
+
|-----------|------|---------|-------------|
|
|
115
|
+
| `label` | string | `""` | Visible group label and accessible name of the group |
|
|
86
116
|
|
|
87
117
|
## Slots — `<bds-dropdown-menu>`
|
|
88
118
|
|
|
89
119
|
| Slot | Description |
|
|
90
120
|
|------|-------------|
|
|
91
121
|
| `trigger` | The activating element (typically a `<button>`) |
|
|
92
|
-
| `(default)` | `<bds-dropdown-menu-item>` elements |
|
|
122
|
+
| `(default)` | `<bds-dropdown-menu-item>` or `<bds-dropdown-menu-group>` elements |
|
|
93
123
|
|
|
94
124
|
## Slots — `<bds-dropdown-menu-item>`
|
|
95
125
|
|
|
96
126
|
| Slot | Description |
|
|
97
127
|
|------|-------------|
|
|
128
|
+
| `icon` | Optional decorative icon before the label |
|
|
98
129
|
| `(default)` | Item label text |
|
|
99
130
|
|
|
131
|
+
## Slots — `<bds-dropdown-menu-group>`
|
|
132
|
+
|
|
133
|
+
| Slot | Description |
|
|
134
|
+
|------|-------------|
|
|
135
|
+
| `(default)` | `<bds-dropdown-menu-item>` elements |
|
|
136
|
+
|
|
100
137
|
## Events
|
|
101
138
|
|
|
102
139
|
| Event | Fired by | Bubbles | Detail | Description |
|
|
@@ -116,6 +153,23 @@ Or in HTML without a bundler:
|
|
|
116
153
|
</bds-dropdown-menu>
|
|
117
154
|
```
|
|
118
155
|
|
|
156
|
+
## Usage with groups
|
|
157
|
+
|
|
158
|
+
```html
|
|
159
|
+
<bds-dropdown-menu>
|
|
160
|
+
<bds-button slot="trigger" variant="outline">Acties</bds-button>
|
|
161
|
+
<bds-dropdown-menu-group label="Bewerken">
|
|
162
|
+
<bds-dropdown-menu-item value="edit" shortcut="⌘E">
|
|
163
|
+
<span slot="icon">✎</span>Bewerken
|
|
164
|
+
</bds-dropdown-menu-item>
|
|
165
|
+
<bds-dropdown-menu-item value="duplicate">Dupliceren</bds-dropdown-menu-item>
|
|
166
|
+
</bds-dropdown-menu-group>
|
|
167
|
+
<bds-dropdown-menu-group label="Gevaarlijk">
|
|
168
|
+
<bds-dropdown-menu-item value="delete" destructive>Verwijderen</bds-dropdown-menu-item>
|
|
169
|
+
</bds-dropdown-menu-group>
|
|
170
|
+
</bds-dropdown-menu>
|
|
171
|
+
```
|
|
172
|
+
|
|
119
173
|
## Accessibility
|
|
120
174
|
|
|
121
175
|
- The slotted trigger receives `aria-haspopup="menu"`, `aria-controls` (pointing at the panel's id), and `aria-expanded` kept in sync with open/close state
|
|
@@ -125,3 +179,5 @@ Or in HTML without a bundler:
|
|
|
125
179
|
- Disabled items are excluded from keyboard navigation
|
|
126
180
|
- Focus returns to the trigger element on close
|
|
127
181
|
- The panel is an absolutely-positioned shadow-DOM element (not the native Popover API), so it can be clipped by an ancestor's `overflow` or stacking context
|
|
182
|
+
- `<bds-dropdown-menu-group>` renders a `role="group"` in its shadow root named by its visible label (`aria-labelledby` within the same shadow root); the label is not focusable and keyboard navigation skips it
|
|
183
|
+
- The item `shortcut` is `aria-hidden`; the consumer wires the actual key
|
|
@@ -16,7 +16,7 @@ function BdsDropdownMenu({
|
|
|
16
16
|
return React.createElement(
|
|
17
17
|
'bds-dropdown-menu',
|
|
18
18
|
{ placement },
|
|
19
|
-
React.createElement('button', { slot: 'trigger',
|
|
19
|
+
React.createElement('bds-button', { slot: 'trigger', variant: 'outline' }, triggerLabel),
|
|
20
20
|
children ?? [
|
|
21
21
|
React.createElement('bds-dropdown-menu-item', { key: 'edit', value: 'edit' }, 'Edit'),
|
|
22
22
|
React.createElement('bds-dropdown-menu-item', { key: 'duplicate', value: 'duplicate' }, 'Duplicate'),
|
|
@@ -28,7 +28,7 @@ function BdsDropdownMenu({
|
|
|
28
28
|
const meta = {
|
|
29
29
|
title: 'Web Components/Interaction/DropdownMenu',
|
|
30
30
|
component: BdsDropdownMenu,
|
|
31
|
-
tags: ['!stable', '
|
|
31
|
+
tags: ['!stable', 'alpha'],
|
|
32
32
|
parameters: { layout: 'centered' },
|
|
33
33
|
argTypes: {
|
|
34
34
|
placement: {
|
|
@@ -51,10 +51,10 @@ export const WithDestructiveItem: Story = {
|
|
|
51
51
|
React.createElement(
|
|
52
52
|
'bds-dropdown-menu',
|
|
53
53
|
{ placement: 'bottom-start' },
|
|
54
|
-
React.createElement('button', { slot: 'trigger',
|
|
54
|
+
React.createElement('bds-button', { slot: 'trigger', variant: 'outline' }, 'Manage'),
|
|
55
55
|
React.createElement('bds-dropdown-menu-item', { value: 'edit' }, 'Edit'),
|
|
56
56
|
React.createElement('bds-dropdown-menu-item', { value: 'duplicate' }, 'Duplicate'),
|
|
57
|
-
React.createElement('bds-dropdown-menu-item', { value: 'delete', destructive:
|
|
57
|
+
React.createElement('bds-dropdown-menu-item', { value: 'delete', destructive: true }, 'Delete'),
|
|
58
58
|
),
|
|
59
59
|
};
|
|
60
60
|
|
|
@@ -63,13 +63,38 @@ export const WithDisabledItem: Story = {
|
|
|
63
63
|
React.createElement(
|
|
64
64
|
'bds-dropdown-menu',
|
|
65
65
|
{ placement: 'bottom-start' },
|
|
66
|
-
React.createElement('button', { slot: 'trigger',
|
|
66
|
+
React.createElement('bds-button', { slot: 'trigger', variant: 'outline' }, 'Actions'),
|
|
67
67
|
React.createElement('bds-dropdown-menu-item', { value: 'view' }, 'View'),
|
|
68
|
-
React.createElement('bds-dropdown-menu-item', { value: 'export', disabled:
|
|
68
|
+
React.createElement('bds-dropdown-menu-item', { value: 'export', disabled: true }, 'Export (unavailable)'),
|
|
69
69
|
React.createElement('bds-dropdown-menu-item', { value: 'share' }, 'Share'),
|
|
70
70
|
),
|
|
71
71
|
};
|
|
72
72
|
|
|
73
|
+
export const WithGroups: Story = {
|
|
74
|
+
render: () =>
|
|
75
|
+
React.createElement(
|
|
76
|
+
'bds-dropdown-menu',
|
|
77
|
+
{ placement: 'bottom-start' },
|
|
78
|
+
React.createElement('bds-button', { slot: 'trigger', variant: 'outline' }, 'Acties'),
|
|
79
|
+
React.createElement(
|
|
80
|
+
'bds-dropdown-menu-group',
|
|
81
|
+
{ label: 'Bewerken' },
|
|
82
|
+
React.createElement(
|
|
83
|
+
'bds-dropdown-menu-item',
|
|
84
|
+
{ value: 'edit', shortcut: '⌘E' },
|
|
85
|
+
React.createElement('span', { slot: 'icon' }, '✎'),
|
|
86
|
+
'Bewerken',
|
|
87
|
+
),
|
|
88
|
+
React.createElement('bds-dropdown-menu-item', { value: 'duplicate', shortcut: '⌘D' }, 'Dupliceren'),
|
|
89
|
+
),
|
|
90
|
+
React.createElement(
|
|
91
|
+
'bds-dropdown-menu-group',
|
|
92
|
+
{ label: 'Gevaarlijk' },
|
|
93
|
+
React.createElement('bds-dropdown-menu-item', { value: 'delete', destructive: true }, 'Verwijderen'),
|
|
94
|
+
),
|
|
95
|
+
),
|
|
96
|
+
};
|
|
97
|
+
|
|
73
98
|
export const AllPlacements: Story = {
|
|
74
99
|
render: () => (
|
|
75
100
|
<div style={{ display: 'grid', gridTemplateColumns: 'repeat(2, auto)', gap: '6rem', padding: '5rem' }}>
|
|
@@ -80,7 +105,7 @@ export const AllPlacements: Story = {
|
|
|
80
105
|
React.createElement(
|
|
81
106
|
'bds-dropdown-menu',
|
|
82
107
|
{ placement: p },
|
|
83
|
-
React.createElement('button', { slot: 'trigger',
|
|
108
|
+
React.createElement('bds-button', { slot: 'trigger', variant: 'outline' }, p),
|
|
84
109
|
React.createElement('bds-dropdown-menu-item', { value: 'a' }, 'Item A'),
|
|
85
110
|
React.createElement('bds-dropdown-menu-item', { value: 'b' }, 'Item B'),
|
|
86
111
|
),
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsPopover.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic popover custom element. A non-modal floating panel anchored to a trigger element. Uses CSS Anchor Positioning for automatic repositioning when near viewport edges.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -24,7 +24,7 @@ function BdsPopover({
|
|
|
24
24
|
const meta = {
|
|
25
25
|
title: 'Web Components/Interaction/Popover',
|
|
26
26
|
component: BdsPopover,
|
|
27
|
-
tags: ['!stable', '
|
|
27
|
+
tags: ['!stable', 'alpha'],
|
|
28
28
|
parameters: { layout: 'centered' },
|
|
29
29
|
argTypes: {
|
|
30
30
|
placement: { control: 'select', options: ['bottom', 'top', 'left', 'right'] },
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsSkipLink.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Skip Navigation Link custom element. Visually hidden until focused, allowing keyboard users to jump directly to the main content area and bypass repeated navigation.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -7,7 +7,7 @@ import * as Stories from './BdsTabs.stories';
|
|
|
7
7
|
|
|
8
8
|
Framework-agnostic Tabs custom element. Coordinates `<bds-tab>` and `<bds-tab-panel>` children by DOM order, with full keyboard navigation.
|
|
9
9
|
|
|
10
|
-
> **Status:
|
|
10
|
+
> **Status: alpha** — API may change before stable release.
|
|
11
11
|
|
|
12
12
|
## Installation
|
|
13
13
|
|
|
@@ -102,6 +102,11 @@ across every state; set `--tab_color--active` to theme only the selected tab.
|
|
|
102
102
|
| `--tab_color--active` | Text colour override for the selected tab |
|
|
103
103
|
| `--tab_border-color--active` | Bottom-border colour override for the selected tab |
|
|
104
104
|
| `--tab_color--hover` | Text colour override on hover (unselected, enabled tabs) |
|
|
105
|
+
| `--tab_color--inactive` | Text colour override for unselected tabs (default: `--bds-color_on-bg--muted`) |
|
|
106
|
+
| `--tab_font-weight` | Tab font weight override (all states) |
|
|
107
|
+
| `--tab_font-weight--inactive` | Font weight override for unselected tabs (default: `--bds-font_weight--medium`) |
|
|
108
|
+
| `--tab_font-weight--active` | Font weight override for the selected tab (default: `--bds-font_weight--bold`) |
|
|
109
|
+
| `--tab_indicator-width` | Thickness of the bottom indicator line (default: `3px`) |
|
|
105
110
|
|
|
106
111
|
## Usage in plain HTML
|
|
107
112
|
|
|
@@ -125,6 +130,10 @@ Tabs and panels are matched by DOM order (first tab → first panel, etc.):
|
|
|
125
130
|
</bds-tabs>
|
|
126
131
|
```
|
|
127
132
|
|
|
133
|
+
## Layout stability
|
|
134
|
+
|
|
135
|
+
The slotted label is mirrored into a `data-label` attribute on an inner wrapper, and a hidden `::after` repeats it at the active weight (`--tab_font-weight--active`). The tab keeps its bold width, so selecting a tab does not shift the row. The copy is invisible and not read by screen readers.
|
|
136
|
+
|
|
128
137
|
## Accessibility
|
|
129
138
|
|
|
130
139
|
- The tab list container has `role="tablist"`
|