@boostdev/design-system-components 1.1.2 → 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (213) hide show
  1. package/AGENTS.md +38 -14
  2. package/dist/client.cjs +85 -103
  3. package/dist/client.css +610 -601
  4. package/dist/client.d.cts +13 -16
  5. package/dist/client.d.ts +13 -16
  6. package/dist/client.js +95 -113
  7. package/dist/index.cjs +85 -103
  8. package/dist/index.css +610 -601
  9. package/dist/index.d.cts +13 -16
  10. package/dist/index.d.ts +13 -16
  11. package/dist/index.js +95 -113
  12. package/dist/native/index.cjs +9 -8
  13. package/dist/native/index.d.cts +1 -1
  14. package/dist/native/index.d.ts +1 -1
  15. package/dist/native/index.js +9 -8
  16. package/dist/web-components/{chunk-K5CE6HSB.js → chunk-2FGATTGT.js} +79 -17
  17. package/dist/web-components/{chunk-O4UFI2RX.js → chunk-3REOIRDW.js} +13 -11
  18. package/dist/web-components/{chunk-5IPHEONG.js → chunk-6I2DBFQ7.js} +1 -0
  19. package/dist/web-components/{chunk-VM3YHGQ2.js → chunk-AJSXNDAP.js} +1 -2
  20. package/dist/web-components/{chunk-LSC4N56Q.js → chunk-BX3IPVOB.js} +1 -2
  21. package/dist/web-components/{chunk-CAPI25CU.js → chunk-DZRSJGPB.js} +3 -3
  22. package/dist/web-components/{chunk-VSS5ITNE.js → chunk-EBJM3VD4.js} +1 -3
  23. package/dist/web-components/{chunk-O7I63SQX.js → chunk-HHHRF2PS.js} +6 -12
  24. package/dist/web-components/{chunk-OTX4COSV.js → chunk-JUKB3BUP.js} +3 -4
  25. package/dist/web-components/{chunk-IQGLIQSO.js → chunk-N6IMUOY4.js} +2 -5
  26. package/dist/web-components/{chunk-CJ5ZOO42.js → chunk-OCODKRVZ.js} +68 -44
  27. package/dist/web-components/{chunk-QDRH46TF.js → chunk-QLZ2362S.js} +1 -3
  28. package/dist/web-components/{chunk-IK3PTFZ4.js → chunk-T6AETZRP.js} +1 -3
  29. package/dist/web-components/{chunk-4BX6AWXX.js → chunk-X3FKVHLK.js} +2 -4
  30. package/dist/web-components/{chunk-A67LCT7C.js → chunk-XNA6WTXG.js} +3 -4
  31. package/dist/web-components/{chunk-XIENXR7H.js → chunk-YRXCVKHV.js} +1 -3
  32. package/dist/web-components/{chunk-6T3RKUKG.js → chunk-ZTC6GRP7.js} +1 -2
  33. package/dist/web-components/globals.js +1 -1
  34. package/dist/web-components/index.d.ts +571 -1
  35. package/dist/web-components/index.js +1515 -18
  36. package/dist/web-components/interaction/bds-accordion.js +1 -1
  37. package/dist/web-components/interaction/bds-button.d.ts +2 -2
  38. package/dist/web-components/interaction/bds-button.js +1 -1
  39. package/dist/web-components/interaction/bds-collapsible.js +1 -1
  40. package/dist/web-components/interaction/bds-dialog.js +1 -1
  41. package/dist/web-components/interaction/bds-drawer.js +1 -1
  42. package/dist/web-components/interaction/form/bds-checkbox.js +1 -1
  43. package/dist/web-components/interaction/form/bds-combobox.js +1 -1
  44. package/dist/web-components/interaction/form/bds-number-input.js +1 -1
  45. package/dist/web-components/interaction/form/bds-radio.js +1 -1
  46. package/dist/web-components/interaction/form/bds-segmented-control.d.ts +20 -3
  47. package/dist/web-components/interaction/form/bds-segmented-control.js +1 -1
  48. package/dist/web-components/interaction/form/bds-select.js +1 -1
  49. package/dist/web-components/interaction/form/bds-switch.js +1 -1
  50. package/dist/web-components/interaction/form/bds-textarea.js +1 -1
  51. package/dist/web-components/ui/bds-alert.js +1 -1
  52. package/dist/web-components/ui/bds-card.js +1 -1
  53. package/dist/web-components/ui/bds-notification-banner.js +1 -1
  54. package/package.json +2 -2
  55. package/src/components/interaction/Button/Button.module.css +12 -11
  56. package/src/components/interaction/Button/Button.native.tsx +10 -9
  57. package/src/components/interaction/Button/Button.tsx +1 -1
  58. package/src/components/interaction/Command/Command.module.css +3 -7
  59. package/src/components/interaction/Dialog/Dialog.module.css +7 -5
  60. package/src/components/interaction/Drawer/Drawer.module.css +48 -25
  61. package/src/components/interaction/Drawer/Drawer.tsx +21 -17
  62. package/src/components/interaction/DropdownMenu/DropdownMenu.module.css +1 -3
  63. package/src/components/interaction/Popover/Popover.module.css +1 -3
  64. package/src/components/interaction/form/Checkbox/Checkbox.module.css +1 -3
  65. package/src/components/interaction/form/Combobox/Combobox.module.css +2 -6
  66. package/src/components/interaction/form/FormInput/FormInput.module.css +1 -3
  67. package/src/components/interaction/form/NumberInput/NumberInput.module.css +16 -4
  68. package/src/components/interaction/form/Radio/Radio.module.css +6 -16
  69. package/src/components/interaction/form/SegmentedControl/SegmentedControl.mdx +74 -25
  70. package/src/components/interaction/form/SegmentedControl/SegmentedControl.module.css +65 -36
  71. package/src/components/interaction/form/SegmentedControl/SegmentedControl.spec.tsx +127 -56
  72. package/src/components/interaction/form/SegmentedControl/SegmentedControl.stories.tsx +89 -72
  73. package/src/components/interaction/form/SegmentedControl/SegmentedControl.tsx +40 -62
  74. package/src/components/interaction/form/SegmentedControl/index.ts +1 -1
  75. package/src/components/interaction/form/Select/Select.module.css +2 -4
  76. package/src/components/interaction/form/Switch/Switch.module.css +5 -7
  77. package/src/components/interaction/form/Switch/Switch.native.spec.tsx +9 -9
  78. package/src/components/interaction/form/Switch/Switch.native.tsx +2 -2
  79. package/src/components/interaction/form/Textarea/Textarea.module.css +1 -3
  80. package/src/components/interaction/form/atoms/InputContainer.stories.tsx +64 -0
  81. package/src/components/interaction/form/atoms/Label.stories.tsx +33 -0
  82. package/src/components/interaction/form/atoms/Message.stories.tsx +33 -0
  83. package/src/components/layout/Card/Card.module.css +1 -3
  84. package/src/components/ui/Accordion/Accordion.module.css +1 -2
  85. package/src/components/ui/Alert/Alert.module.css +1 -2
  86. package/src/components/ui/Calendar/Calendar.module.css +2 -5
  87. package/src/components/ui/Carousel/Carousel.module.css +1 -3
  88. package/src/components/ui/NotificationBanner/NotificationBanner.module.css +1 -2
  89. package/src/components/ui/Pagination/Pagination.module.css +1 -2
  90. package/src/components/ui/SkipLink/SkipLink.module.css +1 -2
  91. package/src/components/ui/Table/Table.module.css +1 -2
  92. package/src/css/bdc.css +16 -11
  93. package/src/index.ts +1 -1
  94. package/src/stories/Introduction.mdx +2 -1
  95. package/src/web-components/globals.ts +3 -3
  96. package/src/web-components/index.ts +12 -0
  97. package/src/web-components/interaction/BdsAccordion.mdx +103 -0
  98. package/src/web-components/interaction/BdsAccordion.stories.tsx +94 -0
  99. package/src/web-components/interaction/BdsCollapsible.mdx +116 -0
  100. package/src/web-components/interaction/BdsCollapsible.stories.tsx +68 -0
  101. package/src/web-components/interaction/BdsDialog.mdx +110 -0
  102. package/src/web-components/interaction/BdsDialog.stories.tsx +157 -0
  103. package/src/web-components/interaction/BdsDrawer.mdx +108 -0
  104. package/src/web-components/interaction/BdsDrawer.stories.tsx +196 -0
  105. package/src/web-components/interaction/BdsDropdownMenu.mdx +108 -0
  106. package/src/web-components/interaction/BdsDropdownMenu.stories.tsx +91 -0
  107. package/src/web-components/interaction/BdsSkipLink.mdx +90 -0
  108. package/src/web-components/interaction/BdsSkipLink.stories.tsx +68 -0
  109. package/src/web-components/interaction/BdsTabs.mdx +117 -0
  110. package/src/web-components/interaction/BdsTabs.stories.tsx +94 -0
  111. package/src/web-components/interaction/BdsTooltip.mdx +104 -0
  112. package/src/web-components/interaction/BdsTooltip.stories.tsx +87 -0
  113. package/src/web-components/interaction/bds-accordion.ts +1 -2
  114. package/src/web-components/interaction/bds-button.ts +15 -13
  115. package/src/web-components/interaction/bds-collapsible.ts +1 -0
  116. package/src/web-components/interaction/bds-dialog.ts +2 -5
  117. package/src/web-components/interaction/bds-drawer.ts +70 -44
  118. package/src/web-components/interaction/bds-dropdown-menu-item.ts +124 -0
  119. package/src/web-components/interaction/bds-dropdown-menu.spec.ts +102 -0
  120. package/src/web-components/interaction/bds-dropdown-menu.ts +200 -0
  121. package/src/web-components/interaction/form/BdsCheckbox.mdx +76 -0
  122. package/src/web-components/interaction/form/BdsCheckbox.stories.tsx +72 -0
  123. package/src/web-components/interaction/form/BdsCheckboxGroup.mdx +70 -0
  124. package/src/web-components/interaction/form/BdsCheckboxGroup.stories.tsx +81 -0
  125. package/src/web-components/interaction/form/BdsCombobox.mdx +71 -0
  126. package/src/web-components/interaction/form/BdsCombobox.stories.tsx +93 -0
  127. package/src/web-components/interaction/form/BdsFileInput.mdx +79 -0
  128. package/src/web-components/interaction/form/BdsFileInput.stories.tsx +69 -0
  129. package/src/web-components/interaction/form/BdsFormInput.mdx +98 -0
  130. package/src/web-components/interaction/form/BdsFormInput.stories.tsx +139 -0
  131. package/src/web-components/interaction/form/BdsNumberInput.mdx +70 -0
  132. package/src/web-components/interaction/form/BdsNumberInput.stories.tsx +68 -0
  133. package/src/web-components/interaction/form/BdsRadio.mdx +72 -0
  134. package/src/web-components/interaction/form/BdsRadio.stories.tsx +58 -0
  135. package/src/web-components/interaction/form/BdsRadioGroup.mdx +73 -0
  136. package/src/web-components/interaction/form/BdsRadioGroup.stories.tsx +88 -0
  137. package/src/web-components/interaction/form/BdsSegmentedControl.mdx +95 -0
  138. package/src/web-components/interaction/form/BdsSegmentedControl.stories.tsx +102 -0
  139. package/src/web-components/interaction/form/BdsSelect.mdx +76 -0
  140. package/src/web-components/interaction/form/BdsSelect.stories.tsx +84 -0
  141. package/src/web-components/interaction/form/BdsSlider.mdx +77 -0
  142. package/src/web-components/interaction/form/BdsSlider.stories.tsx +68 -0
  143. package/src/web-components/interaction/form/BdsSwitch.mdx +72 -0
  144. package/src/web-components/interaction/form/BdsSwitch.stories.tsx +58 -0
  145. package/src/web-components/interaction/form/BdsTextarea.mdx +73 -0
  146. package/src/web-components/interaction/form/BdsTextarea.stories.tsx +70 -0
  147. package/src/web-components/interaction/form/bds-checkbox-group.spec.ts +55 -0
  148. package/src/web-components/interaction/form/bds-checkbox-group.ts +117 -0
  149. package/src/web-components/interaction/form/bds-checkbox.ts +1 -3
  150. package/src/web-components/interaction/form/bds-combobox.ts +1 -3
  151. package/src/web-components/interaction/form/bds-form-input.spec.ts +83 -0
  152. package/src/web-components/interaction/form/bds-form-input.ts +268 -0
  153. package/src/web-components/interaction/form/bds-number-input.ts +3 -4
  154. package/src/web-components/interaction/form/bds-radio-group.spec.ts +62 -0
  155. package/src/web-components/interaction/form/bds-radio-group.ts +142 -0
  156. package/src/web-components/interaction/form/bds-radio.ts +6 -12
  157. package/src/web-components/interaction/form/bds-segmented-control.ts +96 -20
  158. package/src/web-components/interaction/form/bds-select.ts +2 -4
  159. package/src/web-components/interaction/form/bds-switch.ts +3 -4
  160. package/src/web-components/interaction/form/bds-textarea.ts +1 -3
  161. package/src/web-components/ui/BdsAvatar.mdx +76 -0
  162. package/src/web-components/ui/BdsAvatar.stories.tsx +48 -0
  163. package/src/web-components/ui/BdsBreadcrumb.mdx +66 -0
  164. package/src/web-components/ui/BdsBreadcrumb.stories.tsx +49 -0
  165. package/src/web-components/ui/BdsButtonGroup.mdx +69 -0
  166. package/src/web-components/ui/BdsButtonGroup.stories.tsx +66 -0
  167. package/src/web-components/ui/BdsCalendar.mdx +93 -0
  168. package/src/web-components/ui/BdsCalendar.stories.tsx +63 -0
  169. package/src/web-components/ui/BdsCard.mdx +88 -0
  170. package/src/web-components/ui/BdsCard.stories.tsx +67 -0
  171. package/src/web-components/ui/BdsCarousel.mdx +83 -0
  172. package/src/web-components/ui/BdsCarousel.stories.tsx +96 -0
  173. package/src/web-components/ui/BdsDescriptionList.mdx +64 -0
  174. package/src/web-components/ui/BdsDescriptionList.stories.tsx +64 -0
  175. package/src/web-components/ui/BdsIconWrapper.mdx +70 -0
  176. package/src/web-components/ui/BdsIconWrapper.stories.tsx +81 -0
  177. package/src/web-components/ui/BdsLink.mdx +79 -0
  178. package/src/web-components/ui/BdsLink.stories.tsx +63 -0
  179. package/src/web-components/ui/BdsLoading.mdx +58 -0
  180. package/src/web-components/ui/BdsLoading.stories.tsx +35 -0
  181. package/src/web-components/ui/BdsNotificationBanner.mdx +85 -0
  182. package/src/web-components/ui/BdsNotificationBanner.stories.tsx +84 -0
  183. package/src/web-components/ui/BdsPagination.mdx +74 -0
  184. package/src/web-components/ui/BdsPagination.stories.tsx +36 -0
  185. package/src/web-components/ui/BdsProgress.mdx +70 -0
  186. package/src/web-components/ui/BdsProgress.stories.tsx +96 -0
  187. package/src/web-components/ui/BdsProgressCircle.mdx +70 -0
  188. package/src/web-components/ui/BdsProgressCircle.stories.tsx +57 -0
  189. package/src/web-components/ui/BdsRating.mdx +61 -0
  190. package/src/web-components/ui/BdsRating.stories.tsx +45 -0
  191. package/src/web-components/ui/BdsSectionHeader.mdx +72 -0
  192. package/src/web-components/ui/BdsSectionHeader.stories.tsx +54 -0
  193. package/src/web-components/ui/BdsSeparator.mdx +77 -0
  194. package/src/web-components/ui/BdsSeparator.stories.tsx +55 -0
  195. package/src/web-components/ui/BdsSkeleton.mdx +61 -0
  196. package/src/web-components/ui/BdsSkeleton.stories.tsx +50 -0
  197. package/src/web-components/ui/BdsTable.mdx +81 -0
  198. package/src/web-components/ui/BdsTable.stories.tsx +83 -0
  199. package/src/web-components/ui/BdsTypography.mdx +74 -0
  200. package/src/web-components/ui/BdsTypography.stories.tsx +52 -0
  201. package/src/web-components/ui/bds-alert.ts +1 -2
  202. package/src/web-components/ui/bds-button-group.spec.ts +40 -0
  203. package/src/web-components/ui/bds-button-group.ts +78 -0
  204. package/src/web-components/ui/bds-calendar.spec.ts +91 -0
  205. package/src/web-components/ui/bds-calendar.ts +427 -0
  206. package/src/web-components/ui/bds-card.ts +1 -3
  207. package/src/web-components/ui/bds-carousel.spec.ts +64 -0
  208. package/src/web-components/ui/bds-carousel.ts +296 -0
  209. package/src/web-components/ui/bds-notification-banner.ts +1 -2
  210. package/src/web-components/ui/bds-pagination.spec.ts +67 -0
  211. package/src/web-components/ui/bds-pagination.ts +197 -0
  212. package/src/web-components/ui/bds-table.spec.ts +45 -0
  213. package/src/web-components/ui/bds-table.ts +96 -0
@@ -0,0 +1,49 @@
1
+ import React from 'react';
2
+ import type { Meta, StoryObj } from '@storybook/react';
3
+ import type { BreadcrumbItem } from './bds-breadcrumb';
4
+ import '../index'; // auto-registers all custom elements
5
+
6
+ function BdsBreadcrumb({ items = [] }: { items?: BreadcrumbItem[] }) {
7
+ return React.createElement('bds-breadcrumb', { items });
8
+ }
9
+
10
+ const meta = {
11
+ title: 'Web Components/UI/Breadcrumb',
12
+ component: BdsBreadcrumb,
13
+ tags: ['!stable', 'experimental'],
14
+ parameters: { layout: 'centered' },
15
+ } satisfies Meta<typeof BdsBreadcrumb>;
16
+
17
+ export default meta;
18
+ type Story = StoryObj<typeof meta>;
19
+
20
+ export const Default: Story = {
21
+ args: {
22
+ items: [
23
+ { label: 'Home', href: '/' },
24
+ { label: 'Products', href: '/products' },
25
+ { label: 'Item' },
26
+ ],
27
+ },
28
+ };
29
+
30
+ export const Short: Story = {
31
+ args: {
32
+ items: [
33
+ { label: 'Home', href: '/' },
34
+ { label: 'Current Page' },
35
+ ],
36
+ },
37
+ };
38
+
39
+ export const Long: Story = {
40
+ args: {
41
+ items: [
42
+ { label: 'Home', href: '/' },
43
+ { label: 'Catalogue', href: '/catalogue' },
44
+ { label: 'Electronics', href: '/catalogue/electronics' },
45
+ { label: 'Phones', href: '/catalogue/electronics/phones' },
46
+ { label: 'Smartphone X' },
47
+ ],
48
+ },
49
+ };
@@ -0,0 +1,69 @@
1
+ import { Meta, Canvas, ArgTypes } from '@storybook/blocks';
2
+ import * as Stories from './BdsButtonGroup.stories';
3
+
4
+ <Meta of={Stories} />
5
+
6
+ # &lt;bds-button-group&gt;
7
+
8
+ Framework-agnostic Button Group custom element. Groups related `<bds-button>` elements in a flex container, collapsing adjacent border radii so they read as a single unit.
9
+
10
+ > **Status: experimental** — API may change before stable release.
11
+
12
+ ## Installation
13
+
14
+ ```js
15
+ import '@boostdev/components/web-components';
16
+ ```
17
+
18
+ ## When to use
19
+
20
+ - Toggle groups (Day / Week / Month), segmented actions, or sets of closely related operations
21
+ - Use `orientation="vertical"` for stacked navigation menus
22
+
23
+ ## Examples
24
+
25
+ ### Default (horizontal)
26
+ <Canvas of={Stories.Default} />
27
+
28
+ ### Horizontal
29
+ <Canvas of={Stories.Horizontal} />
30
+
31
+ ### Vertical
32
+ <Canvas of={Stories.Vertical} />
33
+
34
+ ## Props
35
+
36
+ <ArgTypes of={Stories} />
37
+
38
+ ## Attributes
39
+
40
+ | Attribute | Type | Default | Description |
41
+ |-----------|------|---------|-------------|
42
+ | `orientation` | `"horizontal" \| "vertical"` | `"horizontal"` | Flex direction of the group |
43
+ | `aria-label` | string | — | Accessible label for the group container |
44
+
45
+ ## Slots
46
+
47
+ | Slot | Description |
48
+ |------|-------------|
49
+ | `(default)` | `<bds-button>` elements |
50
+
51
+ ## Usage in plain HTML
52
+
53
+ ```html
54
+ <bds-button-group aria-label="View options">
55
+ <bds-button>Day</bds-button>
56
+ <bds-button>Week</bds-button>
57
+ <bds-button>Month</bds-button>
58
+ </bds-button-group>
59
+
60
+ <bds-button-group orientation="vertical" aria-label="Navigation">
61
+ <bds-button>Profile</bds-button>
62
+ <bds-button>Settings</bds-button>
63
+ </bds-button-group>
64
+ ```
65
+
66
+ ## Accessibility
67
+
68
+ - Renders a `<div role="group">` with the provided `aria-label`
69
+ - Always set `aria-label` to describe the purpose of the group
@@ -0,0 +1,66 @@
1
+ import React from 'react';
2
+ import type { Meta, StoryObj } from '@storybook/react';
3
+ import type { ButtonGroupOrientation } from './bds-button-group';
4
+ import '../index'; // auto-registers all custom elements
5
+
6
+ function BdsButtonGroup({
7
+ orientation = 'horizontal',
8
+ ariaLabel,
9
+ children,
10
+ }: {
11
+ orientation?: ButtonGroupOrientation;
12
+ ariaLabel?: string;
13
+ children?: React.ReactNode;
14
+ }) {
15
+ return React.createElement(
16
+ 'bds-button-group',
17
+ { orientation, 'aria-label': ariaLabel },
18
+ children,
19
+ );
20
+ }
21
+
22
+ const meta = {
23
+ title: 'Web Components/UI/ButtonGroup',
24
+ component: BdsButtonGroup,
25
+ tags: ['!stable', 'experimental'],
26
+ parameters: { layout: 'centered' },
27
+ argTypes: {
28
+ orientation: { control: 'radio', options: ['horizontal', 'vertical'] },
29
+ ariaLabel: { control: 'text' },
30
+ },
31
+ } satisfies Meta<typeof BdsButtonGroup>;
32
+
33
+ export default meta;
34
+ type Story = StoryObj<typeof meta>;
35
+
36
+ export const Default: Story = {
37
+ render: () =>
38
+ React.createElement(
39
+ 'bds-button-group',
40
+ { 'aria-label': 'View options' },
41
+ React.createElement('bds-button', null, 'Day'),
42
+ React.createElement('bds-button', null, 'Week'),
43
+ React.createElement('bds-button', null, 'Month'),
44
+ ),
45
+ };
46
+
47
+ export const Horizontal: Story = {
48
+ render: () =>
49
+ React.createElement(
50
+ 'bds-button-group',
51
+ { orientation: 'horizontal', 'aria-label': 'Actions' },
52
+ React.createElement('bds-button', null, 'Save'),
53
+ React.createElement('bds-button', { variant: 'ghost' }, 'Cancel'),
54
+ ),
55
+ };
56
+
57
+ export const Vertical: Story = {
58
+ render: () =>
59
+ React.createElement(
60
+ 'bds-button-group',
61
+ { orientation: 'vertical', 'aria-label': 'Navigation' },
62
+ React.createElement('bds-button', null, 'Profile'),
63
+ React.createElement('bds-button', null, 'Settings'),
64
+ React.createElement('bds-button', null, 'Logout'),
65
+ ),
66
+ };
@@ -0,0 +1,93 @@
1
+ import { Meta, Canvas, ArgTypes } from '@storybook/blocks';
2
+ import * as Stories from './BdsCalendar.stories';
3
+
4
+ <Meta of={Stories} />
5
+
6
+ # &lt;bds-calendar&gt;
7
+
8
+ Framework-agnostic Calendar date picker custom element. Renders a keyboard-navigable month grid for selecting a date. Participates in HTML forms via the Form-Associated Custom Elements API.
9
+
10
+ > **Status: experimental** — API may change before stable release.
11
+
12
+ ## Installation
13
+
14
+ ```js
15
+ import '@boostdev/components/web-components';
16
+ ```
17
+
18
+ ## When to use
19
+
20
+ - Date selection fields in forms where a visual calendar grid aids comprehension
21
+ - Pair with `min`/`max` to restrict selectable dates to a valid range
22
+
23
+ ## Examples
24
+
25
+ ### Default
26
+ <Canvas of={Stories.Default} />
27
+
28
+ ### With preselected value
29
+ <Canvas of={Stories.WithValue} />
30
+
31
+ ### With min/max range
32
+ <Canvas of={Stories.WithMinMax} />
33
+
34
+ ### Disabled
35
+ <Canvas of={Stories.Disabled} />
36
+
37
+ ### Inside a form
38
+ <Canvas of={Stories.FormField} />
39
+
40
+ ## Props
41
+
42
+ <ArgTypes of={Stories} />
43
+
44
+ ## Attributes
45
+
46
+ | Attribute | Type | Default | Description |
47
+ |-----------|------|---------|-------------|
48
+ | `name` | string | — | Form field name — required to participate in form submission |
49
+ | `value` | string | — | Selected date in ISO 8601 format (`YYYY-MM-DD`) |
50
+ | `min` | string | — | Minimum selectable date (ISO 8601) |
51
+ | `max` | string | — | Maximum selectable date (ISO 8601) |
52
+ | `disabled` | boolean | `false` | Disables all interaction |
53
+
54
+ ## Events
55
+
56
+ | Event | Detail | Description |
57
+ |-------|--------|-------------|
58
+ | `bds-date-select` | `{ date: string }` | Fired when the user selects a date; `date` is in `YYYY-MM-DD` format |
59
+
60
+ ## Usage in plain HTML
61
+
62
+ ```html
63
+ <bds-calendar name="birthday" value="2026-04-15"></bds-calendar>
64
+
65
+ <!-- With constraints -->
66
+ <bds-calendar name="departure" min="2026-04-01" max="2026-12-31"></bds-calendar>
67
+
68
+ <script>
69
+ document.querySelector('bds-calendar')
70
+ .addEventListener('bds-date-select', e => {
71
+ console.log('Selected date:', e.detail.date);
72
+ });
73
+ </script>
74
+ ```
75
+
76
+ ## Keyboard Navigation
77
+
78
+ | Key | Action |
79
+ |-----|--------|
80
+ | Arrow keys | Move focus between days |
81
+ | Home | Move to start of week |
82
+ | End | Move to end of week |
83
+ | Page Up | Navigate to previous month |
84
+ | Page Down | Navigate to next month |
85
+ | Enter / Space | Select focused date |
86
+
87
+ ## Accessibility
88
+
89
+ - Uses the ARIA grid pattern with `role="grid"` and `role="gridcell"` on day buttons
90
+ - The month/year label uses `aria-live="polite"` for screen reader announcements on navigation
91
+ - Each day carries `aria-selected` and `aria-current="date"` (today)
92
+ - Disabled days carry `aria-disabled="true"` and are not focusable
93
+ - Respects the `disabled` attribute at the host level
@@ -0,0 +1,63 @@
1
+ import React from 'react';
2
+ import type { Meta, StoryObj } from '@storybook/react';
3
+ import '../index'; // auto-registers all custom elements
4
+
5
+ function BdsCalendar({
6
+ name,
7
+ value,
8
+ min,
9
+ max,
10
+ disabled,
11
+ }: {
12
+ name?: string;
13
+ value?: string;
14
+ min?: string;
15
+ max?: string;
16
+ disabled?: boolean;
17
+ }) {
18
+ return React.createElement('bds-calendar', {
19
+ name,
20
+ value,
21
+ min,
22
+ max,
23
+ disabled: disabled || undefined,
24
+ });
25
+ }
26
+
27
+ const meta = {
28
+ title: 'Web Components/UI/Calendar',
29
+ component: BdsCalendar,
30
+ tags: ['!stable', 'experimental'],
31
+ parameters: { layout: 'centered' },
32
+ argTypes: {
33
+ value: { control: 'text' },
34
+ min: { control: 'text' },
35
+ max: { control: 'text' },
36
+ disabled: { control: 'boolean' },
37
+ },
38
+ } satisfies Meta<typeof BdsCalendar>;
39
+
40
+ export default meta;
41
+ type Story = StoryObj<typeof meta>;
42
+
43
+ export const Default: Story = { args: {} };
44
+ export const WithValue: Story = { args: { value: '2026-04-15' } };
45
+ export const WithMinMax: Story = {
46
+ args: { value: '2026-04-10', min: '2026-04-05', max: '2026-04-25' },
47
+ };
48
+ export const Disabled: Story = { args: { value: '2026-04-10', disabled: true } };
49
+ export const FormField: Story = {
50
+ render: () => (
51
+ <form
52
+ onSubmit={(e) => {
53
+ e.preventDefault();
54
+ const data = new FormData(e.currentTarget);
55
+ alert(`Selected: ${data.get('birthday') ?? 'none'}`);
56
+ }}
57
+ style={{ display: 'flex', flexDirection: 'column', gap: 16, alignItems: 'flex-start' }}
58
+ >
59
+ {React.createElement('bds-calendar', { name: 'birthday' })}
60
+ <button type="submit">Submit</button>
61
+ </form>
62
+ ),
63
+ };
@@ -0,0 +1,88 @@
1
+ import { Meta, Canvas, ArgTypes } from '@storybook/blocks';
2
+ import * as Stories from './BdsCard.stories';
3
+
4
+ <Meta of={Stories} />
5
+
6
+ # &lt;bds-card&gt;
7
+
8
+ Framework-agnostic Card layout custom element. A versatile container with three visual variants, configurable padding, text alignment, and an optional clickable mode.
9
+
10
+ > **Status: experimental** — API may change before stable release.
11
+
12
+ ## Installation
13
+
14
+ ```js
15
+ import '@boostdev/components/web-components';
16
+ ```
17
+
18
+ ## When to use
19
+
20
+ - Grouping related content visually (product listings, dashboard widgets, feature summaries)
21
+ - Use `clickable` to turn the entire card into an interactive button (e.g. navigation tiles)
22
+
23
+ ## Examples
24
+
25
+ ### All variants
26
+ <Canvas of={Stories.AllVariants} />
27
+
28
+ ### Default
29
+ <Canvas of={Stories.Default} />
30
+
31
+ ### Elevated
32
+ <Canvas of={Stories.Elevated} />
33
+
34
+ ### Outlined
35
+ <Canvas of={Stories.Outlined} />
36
+
37
+ ### Clickable
38
+ <Canvas of={Stories.Clickable} />
39
+
40
+ ## Props
41
+
42
+ <ArgTypes of={Stories} />
43
+
44
+ ## Attributes
45
+
46
+ | Attribute | Type | Default | Description |
47
+ |-----------|------|---------|-------------|
48
+ | `variant` | `"default" \| "elevated" \| "outlined"` | `"default"` | Shadow and border style |
49
+ | `padding` | `"none" \| "small" \| "medium" \| "large"` | `"medium"` | Inner padding |
50
+ | `text-align` | `"start" \| "center" \| "end"` | `"start"` | Text alignment |
51
+ | `clickable` | boolean | `false` | Renders the card as a `<button>` with hover/active effects |
52
+ | `aria-label` | string | — | Accessible label (recommended when `clickable` is set) |
53
+
54
+ ## Slots
55
+
56
+ | Slot | Description |
57
+ |------|-------------|
58
+ | `(default)` | Card content |
59
+
60
+ ## Events
61
+
62
+ | Event | Detail | Description |
63
+ |-------|--------|-------------|
64
+ | `bds-click` | — | Fired when the card button is clicked (only when `clickable` is set) |
65
+
66
+ ## CSS Custom Properties
67
+
68
+ | Property | Description |
69
+ |----------|-------------|
70
+ | `--card_color` | Card background colour |
71
+ | `--card_on-color` | Card text/foreground colour |
72
+
73
+ ## Usage in plain HTML
74
+
75
+ ```html
76
+ <bds-card variant="elevated" padding="large">
77
+ <p>Card content</p>
78
+ </bds-card>
79
+
80
+ <bds-card clickable aria-label="Open details">
81
+ <p>Clickable card</p>
82
+ </bds-card>
83
+ ```
84
+
85
+ ## Accessibility
86
+
87
+ - Static cards render as `<div>`; clickable cards render as `<button type="button">`
88
+ - Always provide `aria-label` on clickable cards to give a meaningful accessible name
@@ -0,0 +1,67 @@
1
+ import React from 'react';
2
+ import type { Meta, StoryObj } from '@storybook/react';
3
+ import type { CardVariant, CardPadding, CardTextAlign } from './bds-card';
4
+ import '../index'; // auto-registers all custom elements
5
+
6
+ function BdsCard({
7
+ variant = 'default',
8
+ padding = 'medium',
9
+ textAlign = 'start',
10
+ clickable,
11
+ ariaLabel,
12
+ children,
13
+ }: {
14
+ variant?: CardVariant;
15
+ padding?: CardPadding;
16
+ textAlign?: CardTextAlign;
17
+ clickable?: boolean;
18
+ ariaLabel?: string;
19
+ children?: React.ReactNode;
20
+ }) {
21
+ return React.createElement(
22
+ 'bds-card',
23
+ {
24
+ variant,
25
+ padding,
26
+ 'text-align': textAlign,
27
+ clickable: clickable || undefined,
28
+ 'aria-label': ariaLabel,
29
+ },
30
+ children,
31
+ );
32
+ }
33
+
34
+ const meta = {
35
+ title: 'Web Components/UI/Card',
36
+ component: BdsCard,
37
+ tags: ['!stable', 'experimental'],
38
+ parameters: { layout: 'centered' },
39
+ argTypes: {
40
+ variant: { control: 'select', options: ['default', 'elevated', 'outlined'] },
41
+ padding: { control: 'select', options: ['none', 'small', 'medium', 'large'] },
42
+ textAlign: { control: 'select', options: ['start', 'center', 'end'] },
43
+ clickable: { control: 'boolean' },
44
+ },
45
+ } satisfies Meta<typeof BdsCard>;
46
+
47
+ export default meta;
48
+ type Story = StoryObj<typeof meta>;
49
+
50
+ export const Default: Story = { args: { variant: 'default', padding: 'medium', children: 'Card content goes here.' } };
51
+ export const Elevated: Story = { args: { variant: 'elevated', padding: 'medium', children: 'Elevated card.' } };
52
+ export const Outlined: Story = { args: { variant: 'outlined', padding: 'medium', children: 'Outlined card.' } };
53
+ export const Clickable: Story = {
54
+ args: { variant: 'default', padding: 'medium', clickable: true, ariaLabel: 'Open details', children: 'Clickable card — hover me.' },
55
+ };
56
+
57
+ export const AllVariants: Story = {
58
+ render: () => (
59
+ <div style={{ display: 'flex', gap: 16, flexWrap: 'wrap', maxWidth: 600 }}>
60
+ {(['default', 'elevated', 'outlined'] as const).map(v =>
61
+ React.createElement('bds-card', { key: v, variant: v, padding: 'medium', style: 'width: 160px' },
62
+ React.createElement('p', { style: 'margin: 0' }, v),
63
+ ),
64
+ )}
65
+ </div>
66
+ ),
67
+ };
@@ -0,0 +1,83 @@
1
+ import { Meta, Canvas, ArgTypes } from '@storybook/blocks';
2
+ import * as Stories from './BdsCarousel.stories';
3
+
4
+ <Meta of={Stories} />
5
+
6
+ # &lt;bds-carousel&gt;
7
+
8
+ Framework-agnostic Carousel custom element. A scroll-snap based slider where each direct child becomes a slide. Supports dot indicators, looping, and custom previous/next buttons via named slots.
9
+
10
+ > **Status: experimental** — API may change before stable release.
11
+
12
+ ## Installation
13
+
14
+ ```js
15
+ import '@boostdev/components/web-components';
16
+ ```
17
+
18
+ ## When to use
19
+
20
+ - Cycling through a set of related content cards, images, or feature highlights
21
+ - Use `indicators` to help users understand how many slides exist and which one is active
22
+ - Use `loop` for continuous navigation without boundaries
23
+
24
+ ## Examples
25
+
26
+ ### Default
27
+ <Canvas of={Stories.Default} />
28
+
29
+ ### With indicators
30
+ <Canvas of={Stories.WithIndicators} />
31
+
32
+ ### Loop
33
+ <Canvas of={Stories.Loop} />
34
+
35
+ ## Props
36
+
37
+ <ArgTypes of={Stories} />
38
+
39
+ ## Attributes
40
+
41
+ | Attribute | Type | Default | Description |
42
+ |-----------|------|---------|-------------|
43
+ | `current-index` | number | `0` | Active slide index (0-based) |
44
+ | `indicators` | boolean | `false` | Shows dot indicator buttons below the slides |
45
+ | `loop` | boolean | `false` | Wraps from last slide to first and vice versa |
46
+
47
+ ## Slots
48
+
49
+ | Slot | Description |
50
+ |------|-------------|
51
+ | `(default)` | Slide content — each direct child is one slide |
52
+ | `prev` | Custom previous button (replaces the built-in button) |
53
+ | `next` | Custom next button (replaces the built-in button) |
54
+
55
+ ## Events
56
+
57
+ | Event | Detail | Description |
58
+ |-------|--------|-------------|
59
+ | `bds-slide-change` | `{ index: number }` | Fired when the active slide changes |
60
+
61
+ ## Usage in plain HTML
62
+
63
+ ```html
64
+ <bds-carousel indicators loop>
65
+ <div>Slide 1</div>
66
+ <div>Slide 2</div>
67
+ <div>Slide 3</div>
68
+ </bds-carousel>
69
+
70
+ <script>
71
+ document.querySelector('bds-carousel')
72
+ .addEventListener('bds-slide-change', e => {
73
+ console.log('Active slide:', e.detail.index);
74
+ });
75
+ </script>
76
+ ```
77
+
78
+ ## Accessibility
79
+
80
+ - The slide track has `role="region"` with `aria-label="Carousel"`
81
+ - Dot indicators carry `role="tab"` and `aria-selected`; the indicator list has `role="tablist"`
82
+ - Navigation buttons have descriptive `aria-label` values and are disabled at boundaries (unless `loop` is set)
83
+ - Smooth scroll is suppressed when `prefers-reduced-motion: reduce` is set
@@ -0,0 +1,96 @@
1
+ import React from 'react';
2
+ import type { Meta, StoryObj } from '@storybook/react';
3
+ import '../index'; // auto-registers all custom elements
4
+
5
+ function BdsCarousel({
6
+ currentIndex = 0,
7
+ indicators,
8
+ loop,
9
+ children,
10
+ }: {
11
+ currentIndex?: number;
12
+ indicators?: boolean;
13
+ loop?: boolean;
14
+ children?: React.ReactNode;
15
+ }) {
16
+ return React.createElement(
17
+ 'bds-carousel',
18
+ {
19
+ 'current-index': currentIndex,
20
+ indicators: indicators || undefined,
21
+ loop: loop || undefined,
22
+ },
23
+ children,
24
+ );
25
+ }
26
+
27
+ const slides = ['Slide 1', 'Slide 2', 'Slide 3'].map(label =>
28
+ React.createElement(
29
+ 'div',
30
+ {
31
+ key: label,
32
+ style: {
33
+ background: 'var(--bds-color_bg--subtle, #f3f4f6)',
34
+ display: 'flex',
35
+ alignItems: 'center',
36
+ justifyContent: 'center',
37
+ height: 160,
38
+ fontSize: '1.25rem',
39
+ fontWeight: 600,
40
+ borderRadius: 8,
41
+ },
42
+ },
43
+ label,
44
+ ),
45
+ );
46
+
47
+ const meta = {
48
+ title: 'Web Components/UI/Carousel',
49
+ component: BdsCarousel,
50
+ tags: ['!stable', 'experimental'],
51
+ parameters: { layout: 'padded' },
52
+ argTypes: {
53
+ currentIndex: { control: 'number' },
54
+ indicators: { control: 'boolean' },
55
+ loop: { control: 'boolean' },
56
+ },
57
+ } satisfies Meta<typeof BdsCarousel>;
58
+
59
+ export default meta;
60
+ type Story = StoryObj<typeof meta>;
61
+
62
+ export const Default: Story = {
63
+ render: () => (
64
+ <div style={{ width: 400 }}>
65
+ {React.createElement(
66
+ 'bds-carousel',
67
+ {},
68
+ ...slides,
69
+ )}
70
+ </div>
71
+ ),
72
+ };
73
+
74
+ export const WithIndicators: Story = {
75
+ render: () => (
76
+ <div style={{ width: 400 }}>
77
+ {React.createElement(
78
+ 'bds-carousel',
79
+ { indicators: true },
80
+ ...slides,
81
+ )}
82
+ </div>
83
+ ),
84
+ };
85
+
86
+ export const Loop: Story = {
87
+ render: () => (
88
+ <div style={{ width: 400 }}>
89
+ {React.createElement(
90
+ 'bds-carousel',
91
+ { indicators: true, loop: true },
92
+ ...slides,
93
+ )}
94
+ </div>
95
+ ),
96
+ };