@adobe-commerce/elsie 1.0.0-alpha04071347

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 (340) hide show
  1. package/.elsie.js +21 -0
  2. package/.eslintrc.js +18 -0
  3. package/README.md +52 -0
  4. package/__mocks__/svg.js +11 -0
  5. package/bin/builders/build/index.js +20 -0
  6. package/bin/builders/generate/api/index.js +65 -0
  7. package/bin/builders/generate/api/templates/function.js +9 -0
  8. package/bin/builders/generate/api/templates/index.js +7 -0
  9. package/bin/builders/generate/api/templates/story.js +23 -0
  10. package/bin/builders/generate/api/templates/unit-test.js +15 -0
  11. package/bin/builders/generate/component/index.js +87 -0
  12. package/bin/builders/generate/component/templates/Component.js +43 -0
  13. package/bin/builders/generate/component/templates/css.js +24 -0
  14. package/bin/builders/generate/component/templates/index.js +8 -0
  15. package/bin/builders/generate/component/templates/stories.js +46 -0
  16. package/bin/builders/generate/component/templates/unit-test.js +19 -0
  17. package/bin/builders/generate/config/index.js +54 -0
  18. package/bin/builders/generate/config/templates/elsie.js +29 -0
  19. package/bin/builders/generate/container/index.js +65 -0
  20. package/bin/builders/generate/container/templates/Component.js +18 -0
  21. package/bin/builders/generate/container/templates/index.js +8 -0
  22. package/bin/builders/generate/container/templates/stories.js +34 -0
  23. package/bin/builders/generate/container/templates/unit-test.js +19 -0
  24. package/bin/builders/generate/index.js +283 -0
  25. package/bin/builders/gql/createOrClearDirectory.js +33 -0
  26. package/bin/builders/gql/getSchemaRef.js +25 -0
  27. package/bin/builders/gql/index.js +71 -0
  28. package/bin/builders/lint/index.js +5 -0
  29. package/bin/builders/serve/index.js +44 -0
  30. package/bin/builders/storybook/index.js +5 -0
  31. package/bin/builders/test/index.js +5 -0
  32. package/bin/index.js +26 -0
  33. package/bin/lib/cli.js +8 -0
  34. package/bin/lib/config.js +12 -0
  35. package/bin/lib/log-message.js +11 -0
  36. package/bin/lib/string.js +26 -0
  37. package/bin/lib/validate-typeof.js +28 -0
  38. package/bin/lib/write-file.js +30 -0
  39. package/bin/lib/write-parent-index.js +45 -0
  40. package/config/eslint.js +113 -0
  41. package/config/jest.js +90 -0
  42. package/config/prettier.js +16 -0
  43. package/config/setEnvVars.js +14 -0
  44. package/config/storybook/addon.js +130 -0
  45. package/config/storybook/components/FileTree/FileTree.jsx +192 -0
  46. package/config/storybook/components/FileTree/index.js +10 -0
  47. package/config/storybook/components/Flex/Flex.jsx +21 -0
  48. package/config/storybook/components/Flex/Flex.module.css +29 -0
  49. package/config/storybook/components/Flex/index.js +10 -0
  50. package/config/storybook/components/OptionsTable/OptionsTable.jsx +88 -0
  51. package/config/storybook/components/OptionsTable/OptionsTable.module.css +104 -0
  52. package/config/storybook/components/OptionsTable/index.js +10 -0
  53. package/config/storybook/components/Panel/Panel.module.css +56 -0
  54. package/config/storybook/components/Panel/Panel.tsx +46 -0
  55. package/config/storybook/components/Panel/index.ts +10 -0
  56. package/config/storybook/components/Screenshot/Screenshot.jsx +23 -0
  57. package/config/storybook/components/Screenshot/Screenshot.module.css +28 -0
  58. package/config/storybook/components/Screenshot/index.js +10 -0
  59. package/config/storybook/components/Steps/Steps.jsx +21 -0
  60. package/config/storybook/components/Steps/Steps.module.css +43 -0
  61. package/config/storybook/components/Steps/index.js +10 -0
  62. package/config/storybook/components/StoryWrapper/StoryWrapper.jsx +18 -0
  63. package/config/storybook/components/StoryWrapper/StoryWrapper.module.css +22 -0
  64. package/config/storybook/components/StoryWrapper/index.js +10 -0
  65. package/config/storybook/components/Summary/Summary.jsx +19 -0
  66. package/config/storybook/components/Summary/Summary.module.css +20 -0
  67. package/config/storybook/components/Summary/index.js +10 -0
  68. package/config/storybook/components/Variants/Variants.js +57 -0
  69. package/config/storybook/components/Variants/docs.css +48 -0
  70. package/config/storybook/components/Variants/index.js +10 -0
  71. package/config/storybook/components/video/index.jsx +28 -0
  72. package/config/storybook/manager.js +23 -0
  73. package/config/storybook/preview.jsx +88 -0
  74. package/config/storybook/theming/fonts.css +68 -0
  75. package/config/storybook/theming/logo.svg +19 -0
  76. package/config/storybook/theming/manager.css +63 -0
  77. package/config/storybook/theming/preview.css +93 -0
  78. package/config/storybook/theming/theme.js +61 -0
  79. package/config/tsconfig-base.json +16 -0
  80. package/config/tsconfig-preact.json +15 -0
  81. package/config/vite.mjs +306 -0
  82. package/package.json +113 -0
  83. package/post-release.sh +5 -0
  84. package/src/components/Accordion/Accordion.css +88 -0
  85. package/src/components/Accordion/Accordion.stories.tsx +582 -0
  86. package/src/components/Accordion/Accordion.tsx +177 -0
  87. package/src/components/Accordion/index.ts +11 -0
  88. package/src/components/ActionButton/ActionButton.css +100 -0
  89. package/src/components/ActionButton/ActionButton.stories.tsx +169 -0
  90. package/src/components/ActionButton/ActionButton.tsx +53 -0
  91. package/src/components/ActionButton/index.ts +10 -0
  92. package/src/components/ActionButtonGroup/ActionButtonGroup.css +77 -0
  93. package/src/components/ActionButtonGroup/ActionButtonGroup.stories.tsx +97 -0
  94. package/src/components/ActionButtonGroup/ActionButtonGroup.tsx +91 -0
  95. package/src/components/ActionButtonGroup/index.ts +10 -0
  96. package/src/components/AlertBanner/AlertBanner.css +144 -0
  97. package/src/components/AlertBanner/AlertBanner.stories.tsx +165 -0
  98. package/src/components/AlertBanner/AlertBanner.tsx +90 -0
  99. package/src/components/AlertBanner/index.ts +11 -0
  100. package/src/components/Breadcrumbs/Breadcrumbs.css +60 -0
  101. package/src/components/Breadcrumbs/Breadcrumbs.stories.tsx +195 -0
  102. package/src/components/Breadcrumbs/Breadcrumbs.tsx +71 -0
  103. package/src/components/Breadcrumbs/index.ts +11 -0
  104. package/src/components/Button/Button.css +213 -0
  105. package/src/components/Button/Button.mdx +133 -0
  106. package/src/components/Button/Button.stories.tsx +398 -0
  107. package/src/components/Button/Button.tsx +121 -0
  108. package/src/components/Button/index.ts +11 -0
  109. package/src/components/Card/Card.css +34 -0
  110. package/src/components/Card/Card.stories.tsx +76 -0
  111. package/src/components/Card/Card.tsx +34 -0
  112. package/src/components/Card/index.ts +10 -0
  113. package/src/components/CartItem/CartItem.css +509 -0
  114. package/src/components/CartItem/CartItem.stories.tsx +628 -0
  115. package/src/components/CartItem/CartItem.tsx +467 -0
  116. package/src/components/CartItem/CartItemSkeleton.tsx +38 -0
  117. package/src/components/CartItem/index.ts +12 -0
  118. package/src/components/CartList/CartList.css +35 -0
  119. package/src/components/CartList/CartList.stories.tsx +111 -0
  120. package/src/components/CartList/CartList.tsx +40 -0
  121. package/src/components/CartList/index.ts +11 -0
  122. package/src/components/Checkbox/Checkbox.css +255 -0
  123. package/src/components/Checkbox/Checkbox.stories.tsx +290 -0
  124. package/src/components/Checkbox/Checkbox.tsx +138 -0
  125. package/src/components/Checkbox/index.ts +10 -0
  126. package/src/components/ColorSwatch/ColorSwatch.css +132 -0
  127. package/src/components/ColorSwatch/ColorSwatch.stories.tsx +274 -0
  128. package/src/components/ColorSwatch/ColorSwatch.tsx +127 -0
  129. package/src/components/ColorSwatch/index.ts +11 -0
  130. package/src/components/ContentGrid/ContentGrid.css +54 -0
  131. package/src/components/ContentGrid/ContentGrid.stories.tsx +137 -0
  132. package/src/components/ContentGrid/ContentGrid.tsx +57 -0
  133. package/src/components/ContentGrid/index.ts +11 -0
  134. package/src/components/Divider/Divider.css +22 -0
  135. package/src/components/Divider/Divider.stories.tsx +62 -0
  136. package/src/components/Divider/Divider.tsx +33 -0
  137. package/src/components/Divider/index.ts +11 -0
  138. package/src/components/Field/Field.css +83 -0
  139. package/src/components/Field/Field.stories.tsx +238 -0
  140. package/src/components/Field/Field.tsx +84 -0
  141. package/src/components/Field/index.ts +10 -0
  142. package/src/components/Header/Header.css +56 -0
  143. package/src/components/Header/Header.stories.tsx +180 -0
  144. package/src/components/Header/Header.tsx +81 -0
  145. package/src/components/Header/index.ts +11 -0
  146. package/src/components/Icon/Icon.css +26 -0
  147. package/src/components/Icon/Icon.stories.helpers.jsx +21 -0
  148. package/src/components/Icon/Icon.stories.tsx +98 -0
  149. package/src/components/Icon/Icon.tsx +112 -0
  150. package/src/components/Icon/index.ts +10 -0
  151. package/src/components/IllustratedMessage/IllustratedMessage.css +61 -0
  152. package/src/components/IllustratedMessage/IllustratedMessage.stories.tsx +126 -0
  153. package/src/components/IllustratedMessage/IllustratedMessage.tsx +78 -0
  154. package/src/components/IllustratedMessage/index.ts +11 -0
  155. package/src/components/Image/Image.css +52 -0
  156. package/src/components/Image/Image.stories.tsx +89 -0
  157. package/src/components/Image/Image.tsx +66 -0
  158. package/src/components/Image/index.ts +10 -0
  159. package/src/components/ImageSwatch/ImageSwatch.css +154 -0
  160. package/src/components/ImageSwatch/ImageSwatch.stories.tsx +310 -0
  161. package/src/components/ImageSwatch/ImageSwatch.tsx +123 -0
  162. package/src/components/ImageSwatch/index.ts +11 -0
  163. package/src/components/InLineAlert/InLineAlert.css +116 -0
  164. package/src/components/InLineAlert/InLineAlert.stories.tsx +326 -0
  165. package/src/components/InLineAlert/InLineAlert.tsx +128 -0
  166. package/src/components/InLineAlert/index.ts +11 -0
  167. package/src/components/Incrementer/Incrementer.css +165 -0
  168. package/src/components/Incrementer/Incrementer.stories.tsx +172 -0
  169. package/src/components/Incrementer/Incrementer.tsx +192 -0
  170. package/src/components/Incrementer/index.ts +10 -0
  171. package/src/components/Input/Input.css +304 -0
  172. package/src/components/Input/Input.stories.tsx +155 -0
  173. package/src/components/Input/Input.tsx +166 -0
  174. package/src/components/Input/index.ts +11 -0
  175. package/src/components/InputDate/InputDate.css +56 -0
  176. package/src/components/InputDate/InputDate.stories.tsx +117 -0
  177. package/src/components/InputDate/InputDate.tsx +120 -0
  178. package/src/components/InputDate/index.ts +11 -0
  179. package/src/components/InputPassword/InputPassword.css +31 -0
  180. package/src/components/InputPassword/InputPassword.stories.tsx +148 -0
  181. package/src/components/InputPassword/InputPassword.tsx +135 -0
  182. package/src/components/InputPassword/PasswordStatusIndicator/PasswordStatusIndicator.css +31 -0
  183. package/src/components/InputPassword/PasswordStatusIndicator/PasswordStatusIndicator.tsx +96 -0
  184. package/src/components/InputPassword/PasswordStatusIndicator/index.ts +11 -0
  185. package/src/components/InputPassword/index.ts +11 -0
  186. package/src/components/Modal/Modal.css +125 -0
  187. package/src/components/Modal/Modal.stories.tsx +250 -0
  188. package/src/components/Modal/Modal.tsx +157 -0
  189. package/src/components/Modal/index.ts +10 -0
  190. package/src/components/Pagination/Pagination.css +95 -0
  191. package/src/components/Pagination/Pagination.stories.tsx +117 -0
  192. package/src/components/Pagination/Pagination.tsx +149 -0
  193. package/src/components/Pagination/index.ts +11 -0
  194. package/src/components/Picker/Picker.css +220 -0
  195. package/src/components/Picker/Picker.stories.tsx +318 -0
  196. package/src/components/Picker/Picker.tsx +203 -0
  197. package/src/components/Picker/index.ts +10 -0
  198. package/src/components/Price/Price.css +57 -0
  199. package/src/components/Price/Price.stories.tsx +110 -0
  200. package/src/components/Price/Price.tsx +75 -0
  201. package/src/components/Price/index.ts +10 -0
  202. package/src/components/PriceRange/PriceRange.css +66 -0
  203. package/src/components/PriceRange/PriceRange.stories.tsx +240 -0
  204. package/src/components/PriceRange/PriceRange.tsx +248 -0
  205. package/src/components/PriceRange/index.ts +11 -0
  206. package/src/components/ProgressSpinner/ProgressSpinner.css +91 -0
  207. package/src/components/ProgressSpinner/ProgressSpinner.stories.tsx +300 -0
  208. package/src/components/ProgressSpinner/ProgressSpinner.tsx +86 -0
  209. package/src/components/ProgressSpinner/index.ts +11 -0
  210. package/src/components/RadioButton/RadioButton.css +134 -0
  211. package/src/components/RadioButton/RadioButton.stories.tsx +126 -0
  212. package/src/components/RadioButton/RadioButton.tsx +86 -0
  213. package/src/components/RadioButton/index.ts +11 -0
  214. package/src/components/Skeleton/Skeleton.css +145 -0
  215. package/src/components/Skeleton/Skeleton.stories.tsx +265 -0
  216. package/src/components/Skeleton/Skeleton.tsx +133 -0
  217. package/src/components/Skeleton/index.ts +10 -0
  218. package/src/components/Tag/Tag.css +26 -0
  219. package/src/components/Tag/Tag.stories.tsx +103 -0
  220. package/src/components/Tag/Tag.tsx +38 -0
  221. package/src/components/Tag/index.ts +11 -0
  222. package/src/components/TextArea/TextArea.css +140 -0
  223. package/src/components/TextArea/TextArea.stories.tsx +130 -0
  224. package/src/components/TextArea/TextArea.tsx +89 -0
  225. package/src/components/TextArea/index.ts +11 -0
  226. package/src/components/TextSwatch/TextSwatch.css +152 -0
  227. package/src/components/TextSwatch/TextSwatch.stories.tsx +277 -0
  228. package/src/components/TextSwatch/TextSwatch.tsx +131 -0
  229. package/src/components/TextSwatch/index.ts +11 -0
  230. package/src/components/ToggleButton/ToggleButton.css +95 -0
  231. package/src/components/ToggleButton/ToggleButton.stories.tsx +190 -0
  232. package/src/components/ToggleButton/ToggleButton.tsx +75 -0
  233. package/src/components/ToggleButton/index.ts +11 -0
  234. package/src/components/UIProvider/UIProvider.css +140 -0
  235. package/src/components/UIProvider/UIProvider.tsx +61 -0
  236. package/src/components/UIProvider/debugger.css +47 -0
  237. package/src/components/UIProvider/index.ts +10 -0
  238. package/src/components/UIProvider/normalize.css +26 -0
  239. package/src/components/index.ts +49 -0
  240. package/src/docs/API/event-bus.mdx +52 -0
  241. package/src/docs/API/graphql.mdx +214 -0
  242. package/src/docs/API/initializer.mdx +119 -0
  243. package/src/docs/API/render.mdx +125 -0
  244. package/src/docs/Design/colors.mdx +202 -0
  245. package/src/docs/Design/designBlocks.jsx +87 -0
  246. package/src/docs/Design/getTokenData.ts +28 -0
  247. package/src/docs/Design/grid.mdx +365 -0
  248. package/src/docs/Design/overview.mdx +69 -0
  249. package/src/docs/Design/shapes.mdx +100 -0
  250. package/src/docs/Design/spacing.mdx +22 -0
  251. package/src/docs/Design/typography.mdx +126 -0
  252. package/src/docs/Utilities/classList.mdx +52 -0
  253. package/src/docs/Utilities/debounce.mdx +49 -0
  254. package/src/docs/Utilities/deepmerge.mdx +12 -0
  255. package/src/docs/Utilities/getFormErrors.mdx +41 -0
  256. package/src/docs/Utilities/getFormValues.mdx +38 -0
  257. package/src/docs/assets/Banner.png +0 -0
  258. package/src/docs/assets/Colors.png +0 -0
  259. package/src/docs/assets/DropinBanner.png +0 -0
  260. package/src/docs/assets/ShapeStyles.png +0 -0
  261. package/src/docs/assets/Spacing.png +0 -0
  262. package/src/docs/assets/Typography.png +0 -0
  263. package/src/docs/cli-usage.mdx +181 -0
  264. package/src/docs/components/overview.mdx +124 -0
  265. package/src/docs/quick-start.mdx +245 -0
  266. package/src/docs/slots.mdx +211 -0
  267. package/src/docs/welcome.mdx +52 -0
  268. package/src/i18n/en_US.json +146 -0
  269. package/src/i18n/index.ts +26 -0
  270. package/src/icons/Add.svg +9 -0
  271. package/src/icons/AddressBook.svg +3 -0
  272. package/src/icons/Bulk.svg +24 -0
  273. package/src/icons/Burger.svg +5 -0
  274. package/src/icons/Card.svg +7 -0
  275. package/src/icons/Cart.svg +11 -0
  276. package/src/icons/Check.svg +8 -0
  277. package/src/icons/CheckWithCircle.svg +4 -0
  278. package/src/icons/ChevronDown.svg +3 -0
  279. package/src/icons/ChevronRight.svg +8 -0
  280. package/src/icons/ChevronUp.svg +3 -0
  281. package/src/icons/Close.svg +4 -0
  282. package/src/icons/Coupon.svg +3 -0
  283. package/src/icons/Date.svg +4 -0
  284. package/src/icons/Delivery.svg +11 -0
  285. package/src/icons/EmptyBox.svg +3 -0
  286. package/src/icons/Eye.svg +3 -0
  287. package/src/icons/EyeClose.svg +3 -0
  288. package/src/icons/Gift.svg +3 -0
  289. package/src/icons/GiftCard.svg +3 -0
  290. package/src/icons/Heart.svg +3 -0
  291. package/src/icons/HeartFilled.svg +3 -0
  292. package/src/icons/InfoFilled.svg +3 -0
  293. package/src/icons/Locker.svg +11 -0
  294. package/src/icons/Minus.svg +3 -0
  295. package/src/icons/Order.svg +6 -0
  296. package/src/icons/OrderError.svg +15 -0
  297. package/src/icons/OrderSuccess.svg +15 -0
  298. package/src/icons/PaymentError.svg +16 -0
  299. package/src/icons/Placeholder.svg +3 -0
  300. package/src/icons/PlaceholderFilled.svg +4 -0
  301. package/src/icons/Search.svg +9 -0
  302. package/src/icons/SearchFilled.svg +10 -0
  303. package/src/icons/Sort.svg +12 -0
  304. package/src/icons/Star.svg +8 -0
  305. package/src/icons/Trash.svg +7 -0
  306. package/src/icons/User.svg +5 -0
  307. package/src/icons/View.svg +14 -0
  308. package/src/icons/Wallet.svg +6 -0
  309. package/src/icons/Warning.svg +12 -0
  310. package/src/icons/WarningFilled.svg +3 -0
  311. package/src/icons/WarningWithCircle.svg +4 -0
  312. package/src/icons/index.ts +42 -0
  313. package/src/lib/classes.ts +34 -0
  314. package/src/lib/config.ts +24 -0
  315. package/src/lib/debounce.ts +16 -0
  316. package/src/lib/deepmerge.ts +45 -0
  317. package/src/lib/deviceUtils.ts +16 -0
  318. package/src/lib/form-values.ts +31 -0
  319. package/src/lib/i18n.ts +18 -0
  320. package/src/lib/image-params-keymap.ts +36 -0
  321. package/src/lib/index.ts +24 -0
  322. package/src/lib/initializer.ts +134 -0
  323. package/src/lib/is-number.ts +12 -0
  324. package/src/lib/render.tsx +138 -0
  325. package/src/lib/resolve-image.ts +101 -0
  326. package/src/lib/signals.ts +11 -0
  327. package/src/lib/slot.tsx +434 -0
  328. package/src/lib/tests.tsx +47 -0
  329. package/src/lib/types.ts +16 -0
  330. package/src/lib/vcomponent.tsx +42 -0
  331. package/static/assets/images/Card.png +0 -0
  332. package/static/assets/images/example.jpg +0 -0
  333. package/static/assets/images/index.ts +11 -0
  334. package/static/dropin.png +0 -0
  335. package/static/favicon.svg +14 -0
  336. package/storybook-stories.js +21 -0
  337. package/tests/__mocks__/browserMocks.ts +28 -0
  338. package/tests/__mocks__/fileMocks.ts +12 -0
  339. package/tests/__mocks__/styleMock.ts +0 -0
  340. package/types/icons.d.ts +18 -0
@@ -0,0 +1,238 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ // https://storybook.js.org/docs/7.0/preact/writing-stories/introduction
11
+ /* eslint-disable react/no-danger */
12
+ import type { Meta, StoryObj } from '@storybook/preact';
13
+ import {
14
+ Field,
15
+ FieldProps,
16
+ Picker,
17
+ Input,
18
+ Incrementer,
19
+ Checkbox,
20
+ } from '@adobe-commerce/elsie/components';
21
+ import { expect, within, userEvent } from '@storybook/test';
22
+
23
+ /**
24
+ * Use Field Labels to wrap form inputs with titles and help text.
25
+ */
26
+ const meta: Meta<FieldProps> = {
27
+ title: 'Components/Field',
28
+ component: Field,
29
+ argTypes: {
30
+ label: {
31
+ description: 'Label',
32
+ control: 'text',
33
+ },
34
+ hint: {
35
+ description: 'Helper Text',
36
+ control: 'text',
37
+ },
38
+ error: {
39
+ description: 'Error Text',
40
+ control: 'text',
41
+ },
42
+ success: {
43
+ description: 'Success Text',
44
+ control: 'text',
45
+ },
46
+ size: {
47
+ description: '',
48
+ options: ['medium', 'large'],
49
+ control: { type: 'radio' },
50
+ defaultValue: {
51
+ summary: 'medium',
52
+ },
53
+ },
54
+ disabled: {
55
+ description: 'Whether or not the field is disabled',
56
+ control: 'boolean',
57
+ defaultValue: {
58
+ summary: false,
59
+ },
60
+ },
61
+ },
62
+ };
63
+
64
+ export default meta;
65
+
66
+ type Story = StoryObj<FieldProps>;
67
+
68
+ /**
69
+ * ```ts
70
+ * import { Field } from '@adobe-commerce/elsie/components/Field';
71
+ * import { Input } from '@adobe-commerce/elsie/components/Input';
72
+ * ```
73
+ */
74
+ export const InputField: Story = {
75
+ render: (args) => (
76
+ <Field {...args}>
77
+ <Input name="inputField" placeholder="Input" />
78
+ </Field>
79
+ ),
80
+ args: {
81
+ label: 'Label',
82
+ hint: 'Helper Text',
83
+ error: '',
84
+ success: '',
85
+ size: 'medium',
86
+ disabled: false,
87
+ },
88
+ play: async ({ canvasElement }) => {
89
+ const canvas = within(canvasElement);
90
+ await userEvent.type(canvas.getByPlaceholderText('Input'), 'Test Content');
91
+ await expect(await canvas.findByDisplayValue('Test Content')).toBeVisible();
92
+ await expect(canvas.getByText('Label')).toBeVisible();
93
+ await expect(canvas.getByText('Helper Text')).toBeVisible();
94
+ },
95
+ };
96
+
97
+ /**
98
+ * ```ts
99
+ * import { Field } from '@adobe-commerce/elsie/components/Field';
100
+ * import { Incrementer } from '@adobe-commerce/elsie/components/Incrementer';
101
+ * ```
102
+ */
103
+ export const IncrementerField: Story = {
104
+ render: (args) => (
105
+ <Field {...args}>
106
+ <Incrementer name="incrementerField" value="0" min={0} max={100} />
107
+ </Field>
108
+ ),
109
+ args: {
110
+ label: 'Label',
111
+ hint: 'Helper Text',
112
+ error: '',
113
+ success: '',
114
+ size: 'medium',
115
+ disabled: false,
116
+ },
117
+ play: async () => {
118
+ const canvasElement = document.querySelector(
119
+ '#storybook-root'
120
+ ) as HTMLElement;
121
+ const canvas = within(canvasElement);
122
+ const decreaseButton = document.querySelector(
123
+ 'button[aria-label="Decrease Quantity"]'
124
+ ) as HTMLElement;
125
+ const inputField = document.querySelector('input') as HTMLElement;
126
+ const increaseButton = document.querySelector(
127
+ 'button[aria-label="Increase Quantity"]'
128
+ ) as HTMLElement;
129
+
130
+ // Without this wait test failing intermittently as click event is triggerning before even element fully loaded
131
+ await new Promise((resolve) => setTimeout(resolve, 500));
132
+ await userEvent.click(increaseButton);
133
+ await expect(await canvas.findByDisplayValue('1')).toBeTruthy();
134
+
135
+ await userEvent.click(decreaseButton);
136
+ await expect(await canvas.findByDisplayValue('0')).toBeTruthy();
137
+
138
+ await userEvent.type(inputField, '99');
139
+ await expect(await canvas.findByDisplayValue('99')).toBeTruthy();
140
+
141
+ await userEvent.click(increaseButton);
142
+ await expect(await canvas.findByDisplayValue('100')).toBeTruthy();
143
+
144
+ await userEvent.click(increaseButton);
145
+ await expect(await canvas.findByDisplayValue('100')).toBeTruthy();
146
+
147
+ await userEvent.click(decreaseButton);
148
+ await expect(await canvas.findByDisplayValue('99')).toBeTruthy();
149
+
150
+ await userEvent.clear(inputField);
151
+ await userEvent.type(inputField, '0');
152
+ await expect(await canvas.findByDisplayValue('0')).toBeTruthy();
153
+ },
154
+ };
155
+
156
+ /**
157
+ * ```ts
158
+ * import { Field } from '@adobe-commerce/elsie/components/Field';
159
+ * import { Picker } from '@adobe-commerce/elsie/components/Picker';
160
+ * ```
161
+ */
162
+ export const PickerField: Story = {
163
+ render: (args) => (
164
+ <Field {...args}>
165
+ <Picker
166
+ name="pickerField"
167
+ placeholder="Select an option"
168
+ options={[
169
+ {
170
+ value: 'option1',
171
+ text: 'Option 1',
172
+ },
173
+ {
174
+ value: 'option2',
175
+ text: 'Option 2',
176
+ disabled: true,
177
+ },
178
+ {
179
+ value: 'option3',
180
+ text: 'Option 3',
181
+ },
182
+ ]}
183
+ disabled={false}
184
+ />
185
+ </Field>
186
+ ),
187
+ args: {
188
+ label: 'Label',
189
+ hint: 'Helper Text',
190
+ error: '',
191
+ success: '',
192
+ size: 'medium',
193
+ disabled: false,
194
+ },
195
+ play: async ({ canvasElement }) => {
196
+ const canvas = within(canvasElement);
197
+
198
+ await userEvent.click(canvas.getByText('Select an option'));
199
+ await expect(canvas.getByText('Option 1')).toBeVisible();
200
+
201
+ await expect(canvas.getByText('Option 2')).toBeVisible();
202
+
203
+ const select = document.querySelector(
204
+ '.dropin-picker__select'
205
+ ) as HTMLSelectElement;
206
+
207
+ await userEvent.selectOptions(select, 'option3');
208
+
209
+ await expect(select.textContent).toContain('Option 3');
210
+ },
211
+ };
212
+
213
+ export const CheckboxField: Story = {
214
+ render: (args) => (
215
+ <Field {...args}>
216
+ <Checkbox
217
+ name="checkboxField"
218
+ label="Option"
219
+ description="Optional description text goes here"
220
+ />
221
+ </Field>
222
+ ),
223
+ args: {
224
+ label: 'Label',
225
+ hint: 'Helper Text',
226
+ error: '',
227
+ success: '',
228
+ size: 'medium',
229
+ disabled: false,
230
+ },
231
+ };
232
+
233
+ /**
234
+ * ```ts
235
+ * import { Field } from '@adobe-commerce/elsie/components/Field';
236
+ * import { TextSwatch } from '@adobe-commerce/elsie/components/TextSwatch';
237
+ * ```
238
+ */
@@ -0,0 +1,84 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ import '@adobe-commerce/elsie/components/Field/Field.css';
11
+ import { classes } from '@adobe-commerce/elsie/lib';
12
+ import { FunctionComponent, VNode } from 'preact';
13
+ import { HTMLAttributes } from 'preact/compat';
14
+
15
+ export interface FieldProps
16
+ extends Omit<HTMLAttributes<HTMLDivElement>, 'size'> {
17
+ label?: string;
18
+ error?: string;
19
+ hint?: string;
20
+ success?: string;
21
+ disabled?: boolean;
22
+ children?: VNode;
23
+ size?: 'medium' | 'large';
24
+ }
25
+
26
+ export const Field: FunctionComponent<FieldProps> = ({
27
+ className,
28
+ label,
29
+ error,
30
+ hint,
31
+ success,
32
+ size = 'medium',
33
+ disabled = false,
34
+ children,
35
+ ...props
36
+ }) => {
37
+ const id =
38
+ children?.props?.id ?? `dropin-field-${Math.random().toString(36)}`;
39
+ const ChildComponent =
40
+ children && typeof children.type !== 'string' ? children.type : null;
41
+
42
+ return (
43
+ <div {...props} className={classes(['dropin-field', className])}>
44
+ {label && (
45
+ <label
46
+ className={classes([
47
+ 'dropin-field__label',
48
+ ['dropin-field__label--disabled', disabled],
49
+ `dropin-field__label--${size}`,
50
+ ])}
51
+ htmlFor={id}
52
+ >
53
+ {label}
54
+ </label>
55
+ )}
56
+
57
+ <div className={classes(['dropin-field__content'])}>
58
+ {ChildComponent && children && (
59
+ <ChildComponent
60
+ {...children.props}
61
+ id={id}
62
+ key={children.key}
63
+ disabled={disabled}
64
+ size={size}
65
+ error={!!error}
66
+ success={!!success && !error}
67
+ />
68
+ )}
69
+ </div>
70
+
71
+ <div
72
+ className={classes([
73
+ 'dropin-field__hint',
74
+ [`dropin-field__hint--${size}`, size],
75
+ ['dropin-field__hint--error', !!error],
76
+ ['dropin-field__hint--success', !!success && !error],
77
+ ['dropin-field__hint--disabled', !!disabled],
78
+ ])}
79
+ >
80
+ {error || success || hint}
81
+ </div>
82
+ </div>
83
+ );
84
+ };
@@ -0,0 +1,10 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ export * from '@adobe-commerce/elsie/components/Field/Field';
@@ -0,0 +1,56 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ .dropin-header-container {
11
+ display: grid;
12
+ grid-template-columns: repeat(2, auto);
13
+ justify-content: space-between;
14
+ gap: 0px 0px;
15
+ grid-template-areas:
16
+ 'title actions'
17
+ 'divider divider';
18
+ width: 100%;
19
+ }
20
+
21
+ .dropin-header-container__title {
22
+ grid-area: title;
23
+ color: var(--color-neutral-800);
24
+ }
25
+
26
+ .dropin-header-container__title--medium {
27
+ font: var(--type-headline-2-strong-font);
28
+ letter-spacing: var(--type-headline-1-letter-spacing);
29
+ }
30
+
31
+ .dropin-header-container__title--large {
32
+ font: var(--type-headline-1-font);
33
+ letter-spacing: var(--type-headline-1-letter-spacing);
34
+ }
35
+
36
+ .dropin-header-container__actions {
37
+ grid-area: actions;
38
+ font: var(--type-body-2-strong-font);
39
+ letter-spacing: var(--type-body-2-strong-letter-spacing);
40
+ color: var(--color-brand-500);
41
+ align-self: center;
42
+ }
43
+
44
+ .dropin-header-container .dropin-header-container__divider {
45
+ grid-area: divider;
46
+ width: 100%;
47
+ border-top: 3px solid var(--color-neutral-400);
48
+ }
49
+
50
+ .dropin-header-container .dropin-header-container__divider--medium {
51
+ margin: var(--spacing-xsmall) 0 var(--spacing-medium) 0;
52
+ }
53
+
54
+ .dropin-header-container .dropin-header-container__divider--large {
55
+ margin: 22px 0 var(--spacing-medium) 0;
56
+ }
@@ -0,0 +1,180 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ // https://storybook.js.org/docs/7.0/preact/writing-stories/introduction
11
+ import type { Meta, StoryObj } from '@storybook/preact';
12
+ import { Header, HeaderProps } from '@adobe-commerce/elsie/components/Header';
13
+ import { Button } from '@adobe-commerce/elsie/components';
14
+ import { expect, userEvent, within } from '@storybook/test';
15
+
16
+ export default {
17
+ title: 'Components/Header',
18
+ component: Header,
19
+ parameters: {
20
+ layout: 'fullscreen',
21
+ },
22
+ args: {
23
+ title: 'Your Message',
24
+ size: 'medium',
25
+ divider: true,
26
+ },
27
+ argTypes: {
28
+ title: {
29
+ control: 'text',
30
+ description:
31
+ 'Enter the title name. Without this title, it will not be displayed.',
32
+ },
33
+ size: {
34
+ description: 'Size of the style',
35
+ control: { type: 'radio' },
36
+ type: 'string',
37
+ defaultValue: { summary: 'medium' },
38
+ options: ['medium', 'large'],
39
+ },
40
+
41
+ divider: {
42
+ control: 'boolean',
43
+ description: 'Show or hide Divider.',
44
+ },
45
+ cta: {
46
+ description:
47
+ 'A VNode component used to render a custom UI element, allowing for flexible content integration.',
48
+ options: ['Button', 'Link'],
49
+ mapping: {
50
+ Button: <button>Button</button>,
51
+ Link: <a href="#">Link</a>,
52
+ },
53
+ control: {
54
+ type: 'select',
55
+ labels: {
56
+ Button: 'Button element',
57
+ Link: 'Link element',
58
+ },
59
+ },
60
+ defaultValue: { summary: '<empty string>' },
61
+ },
62
+ level: {
63
+ description: 'Set the heading level',
64
+ options: [1, 2, 3, 4, 5, 6],
65
+ control: {
66
+ type: 'select',
67
+ labels: {
68
+ 1: 'h1',
69
+ 2: 'h2',
70
+ 3: 'h3',
71
+ 4: 'h4',
72
+ 5: 'h5',
73
+ 6: 'h6'
74
+ }
75
+ },
76
+ defaultValue: { summary: 2 },
77
+ },
78
+ },
79
+ } as Meta<HeaderProps>;
80
+
81
+ const Template: StoryObj<HeaderProps> = {
82
+ render: (args) => (
83
+ <div style={{ maxWidth: '1200px', padding: '40px' }}>
84
+ <Header {...args} />
85
+ </div>
86
+ ),
87
+ };
88
+
89
+ export const MediumSize = {
90
+ ...Template,
91
+ parameters: {
92
+ layout: 'fullscreen',
93
+ },
94
+ args: {
95
+ title: 'Shipping info',
96
+ size: 'medium',
97
+ divider: true,
98
+ cta: (
99
+ <Button variant="tertiary" style={{ paddingRight: 0 }}>
100
+ Print order details
101
+ </Button>
102
+ ),
103
+ level: 2,
104
+ },
105
+ play: async ({ canvasElement }) => {
106
+ const canvas = within(canvasElement);
107
+
108
+ await expect(canvas.getByText('Print order details')).toBeInTheDocument();
109
+
110
+ const button = canvas.getByRole('button', { name: /Print order details/i });
111
+ await userEvent.click(button);
112
+
113
+ await expect(canvas.getByText('Shipping info')).toBeInTheDocument();
114
+ },
115
+ };
116
+
117
+ export const LargeSize = {
118
+ ...Template,
119
+ parameters: {
120
+ layout: 'fullscreen',
121
+ },
122
+ args: {
123
+ title: 'Order A202405230825',
124
+ size: 'large',
125
+ divider: true,
126
+ cta: <a href="#">Print order details</a>,
127
+ level: 2,
128
+ },
129
+ };
130
+
131
+ export const WithoutLine = {
132
+ ...Template,
133
+ parameters: {
134
+ layout: 'fullscreen',
135
+ },
136
+ args: {
137
+ title: 'Medium Size',
138
+ size: 'medium',
139
+ divider: false,
140
+ cta: <button>Print order details</button>,
141
+ level: 2,
142
+ },
143
+ };
144
+
145
+ export const WithoutActions = {
146
+ ...Template,
147
+ parameters: {
148
+ layout: 'fullscreen',
149
+ },
150
+ args: {
151
+ title: 'Order complete',
152
+ size: 'medium',
153
+ divider: false,
154
+ cta: null,
155
+ level: 2,
156
+ },
157
+ };
158
+
159
+
160
+ export const HeadingLevels = {
161
+ ...Template,
162
+ parameters: {
163
+ layout: 'fullscreen',
164
+ },
165
+ args: {
166
+ title: 'Heading Levels',
167
+ size: 'medium',
168
+ divider: true,
169
+ level: 1,
170
+ },
171
+ argTypes: {
172
+ level: {
173
+ control: {
174
+ type: 'select',
175
+ options: [1, 2, 3, 4, 5, 6]
176
+ },
177
+ description: 'Set the heading level',
178
+ }
179
+ }
180
+ };
@@ -0,0 +1,81 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ import { ComponentChildren, FunctionComponent, VNode } from 'preact';
11
+ import { HTMLAttributes } from 'preact/compat';
12
+ import { classes, VComponent } from '@adobe-commerce/elsie/lib';
13
+ import { Divider } from '@adobe-commerce/elsie/components';
14
+ import '@adobe-commerce/elsie/components/Header/Header.css';
15
+
16
+ export interface HeaderProps extends HTMLAttributes<HTMLDivElement> {
17
+ title: string;
18
+ size?: 'medium' | 'large';
19
+ divider?: boolean;
20
+ cta?: VNode;
21
+ level?: 1 | 2 | 3 | 4 | 5 | 6;
22
+ }
23
+
24
+ const Heading = ({
25
+ level,
26
+ className,
27
+ children,
28
+ }: {
29
+ level?: 1 | 2 | 3 | 4 | 5 | 6;
30
+ className?: string;
31
+ children?: ComponentChildren;
32
+ }) => {
33
+ const HeadingTag = level && level >= 1 && level <= 6
34
+ ? `h${level}` as keyof JSX.IntrinsicElements
35
+ : 'span';
36
+
37
+ return <HeadingTag className={className}>{children as any}</HeadingTag>;
38
+ };
39
+
40
+ export const Header: FunctionComponent<HeaderProps> = ({
41
+ title = null,
42
+ size = 'medium',
43
+ cta,
44
+ divider = true,
45
+ className,
46
+ level,
47
+ ...props
48
+ }) => {
49
+ if (!title) return null;
50
+
51
+ return (
52
+ <div
53
+ {...props}
54
+ className={classes(['dropin-header-container', className])}
55
+ data-testid="dropin-header-container"
56
+ >
57
+ <Heading
58
+ className={classes([
59
+ 'dropin-header-container__title',
60
+ ['dropin-header-container__title--medium', size === 'medium'],
61
+ ['dropin-header-container__title--large', size === 'large'],
62
+ ])}
63
+ level={level}
64
+ >
65
+ {title}
66
+ </Heading>
67
+ {cta ? (
68
+ <VComponent node={cta} className="dropin-header-container__actions" />
69
+ ) : null}
70
+ {divider ? (
71
+ <Divider
72
+ className={classes([
73
+ 'dropin-header-container__divider',
74
+ ['dropin-header-container__divider--medium', size === 'medium'],
75
+ ['dropin-header-container__divider--large', size === 'large'],
76
+ ])}
77
+ />
78
+ ) : null}
79
+ </div>
80
+ );
81
+ };
@@ -0,0 +1,11 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ export * from '@adobe-commerce/elsie/components/Header/Header';
11
+ export { Header as default } from '@adobe-commerce/elsie/components/Header/Header';
@@ -0,0 +1,26 @@
1
+ /********************************************************************
2
+ * Copyright 2024 Adobe
3
+ * All Rights Reserved.
4
+ *
5
+ * NOTICE: Adobe permits you to use, modify, and distribute this
6
+ * file in accordance with the terms of the Adobe license agreement
7
+ * accompanying it.
8
+ *******************************************************************/
9
+
10
+ /* https://cssguidelin.es/#bem-like-naming */
11
+
12
+ .dropin-icon--shape-stroke-1 {
13
+ stroke-width: var(--shape-icon-stroke-1);
14
+ }
15
+
16
+ .dropin-icon--shape-stroke-2 {
17
+ stroke-width: var(--shape-icon-stroke-2);
18
+ }
19
+
20
+ .dropin-icon--shape-stroke-3 {
21
+ stroke-width: var(--shape-icon-stroke-3);
22
+ }
23
+
24
+ .dropin-icon--shape-stroke-4 {
25
+ stroke-width: var(--shape-icon-stroke-4);
26
+ }