uikit-react-public 0.17.4 → 0.21.8

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 (280) hide show
  1. package/README.md +2 -4
  2. package/dist/components/Accordion/Accordion.Heading.d.ts +1 -0
  3. package/dist/components/AppHeader/AppHeader.d.ts +1 -1
  4. package/dist/components/AppHeader/AppHeaderBottom.d.ts +1 -1
  5. package/dist/components/AppHeader/AppHeaderNav.d.ts +1 -1
  6. package/dist/components/AppHeader/AppHeaderTop.d.ts +1 -1
  7. package/dist/components/Breadcrumbs/Breadcrumb.d.ts +3 -4
  8. package/dist/components/Breadcrumbs/Breadcrumbs.d.ts +1 -1
  9. package/dist/components/Breadcrumbs/Breadcrumbs.stories.d.ts +1 -1
  10. package/dist/components/Button/Button.d.ts +7 -3
  11. package/dist/components/Button/Button.stories.d.ts +17 -7
  12. package/dist/components/Button/style/buttonAccentStyle.d.ts +4 -0
  13. package/dist/components/Button/style/buttonPrimaryDestructiveStyle.d.ts +4 -0
  14. package/dist/components/Button/style/buttonPrimaryStyle.d.ts +4 -0
  15. package/dist/components/Button/style/buttonPrimarySubtleStyle.d.ts +4 -0
  16. package/dist/components/Button/style/buttonPrimaryWarningStyle.d.ts +4 -0
  17. package/dist/components/Button/style/buttonSecondaryDestructiveStyle.d.ts +4 -0
  18. package/dist/components/Button/style/buttonSecondaryStyle.d.ts +4 -0
  19. package/dist/components/Button/style/buttonSecondarySubtleStyle.d.ts +4 -0
  20. package/dist/components/Button/style/buttonTertiaryDestructiveStyle.d.ts +4 -0
  21. package/dist/components/Button/style/buttonTertiaryNoPaddingStyle.d.ts +4 -0
  22. package/dist/components/Button/style/buttonTertiaryStyle.d.ts +4 -0
  23. package/dist/components/Checkbox/Checkbox.d.ts +1 -0
  24. package/dist/components/FooterNew/BackToTop.d.ts +8 -0
  25. package/dist/components/FooterNew/Footer.d.ts +23 -0
  26. package/dist/components/FooterNew/FooterColumn.d.ts +8 -0
  27. package/dist/components/FooterNew/FooterLinks.d.ts +7 -0
  28. package/dist/components/FooterNew/FooterNavLink.d.ts +8 -0
  29. package/dist/components/FooterNew/LegalAndCopyright.d.ts +14 -0
  30. package/dist/components/FooterNew/LogoAddressAndSocial.d.ts +10 -0
  31. package/dist/components/FooterNew/SocialLink.d.ts +8 -0
  32. package/dist/components/FooterNew/__tests__/Footer.test.d.ts +1 -0
  33. package/dist/components/FooterNew/index.d.ts +2 -0
  34. package/dist/components/HeaderNew/Header.d.ts +18 -0
  35. package/dist/components/HeaderNew/HeaderBorder.d.ts +7 -0
  36. package/dist/components/HeaderNew/HeaderLogo.d.ts +9 -0
  37. package/dist/components/HeaderNew/HeaderMenuContainer.d.ts +7 -0
  38. package/dist/components/HeaderNew/HeaderTitle.d.ts +9 -0
  39. package/dist/components/HeaderNew/__tests__/Header.test.d.ts +1 -0
  40. package/dist/components/HeaderNew/constants.d.ts +3 -0
  41. package/dist/components/HeaderNew/index.d.ts +3 -0
  42. package/dist/components/HeadingNew/Heading.d.ts +13 -0
  43. package/dist/components/HeadingNew/index.d.ts +2 -0
  44. package/dist/components/Icon/svgImports.d.ts +7 -881
  45. package/dist/components/Link/BaseLink.d.ts +14 -5
  46. package/dist/components/Link/Link.d.ts +8 -3
  47. package/dist/components/Link/Link.stories.d.ts +3 -1
  48. package/dist/components/MenuNew/Menu.context.d.ts +14 -0
  49. package/dist/components/MenuNew/Menu.d.ts +20 -0
  50. package/dist/components/MenuNew/MenuContent.d.ts +9 -0
  51. package/dist/components/MenuNew/MenuItem.d.ts +10 -0
  52. package/dist/components/MenuNew/MenuSection.d.ts +7 -0
  53. package/dist/components/MenuNew/index.d.ts +6 -0
  54. package/dist/components/MenuNew/trigger/ButtonMenuTrigger.d.ts +8 -0
  55. package/dist/components/MenuNew/trigger/IconMenuTrigger.d.ts +8 -0
  56. package/dist/components/Overlay/Overlay.stories.d.ts +12 -12
  57. package/dist/components/ParagraphNew/Paragraph.d.ts +13 -0
  58. package/dist/components/ParagraphNew/index.d.ts +4 -0
  59. package/dist/components/Select/Select.d.ts +2 -1
  60. package/dist/components/Select/Select.stories.d.ts +13 -1
  61. package/dist/components/Select/Select.types.d.ts +40 -13
  62. package/dist/components/Select/subcomponents/CustomSelect.d.ts +3 -3
  63. package/dist/components/Select/subcomponents/FilterInput.d.ts +3 -1
  64. package/dist/components/Select/subcomponents/NativeSelect.d.ts +2 -2
  65. package/dist/components/Select/subcomponents/VisibleField.d.ts +4 -1
  66. package/dist/components/Spinner/Spinner.d.ts +2 -0
  67. package/dist/components/StandaloneLink/StandaloneLink.d.ts +8 -5
  68. package/dist/components/StandaloneLink/StandaloneLink.stories.d.ts +3 -1
  69. package/dist/components/Table/Table.d.ts +3 -3
  70. package/dist/components/Table/Table.stories.d.ts +3 -3
  71. package/dist/components/Table/Table.types.d.ts +1 -0
  72. package/dist/components/Table/subcomponents/Cell/Cell.d.ts +5 -1
  73. package/dist/components/Table/subcomponents/Cell/Cell.stories.d.ts +15 -13
  74. package/dist/components/Table/subcomponents/Cell/CellContent.d.ts +5 -1
  75. package/dist/components/Table/subcomponents/HeadCell/HeadCell.d.ts +2 -1
  76. package/dist/components/Table/subcomponents/HeadCell/HeadCell.stories.d.ts +14 -13
  77. package/dist/components/Table/subcomponents/HeadCell/HeadCellContent.d.ts +2 -1
  78. package/dist/components/Table/subcomponents/__tests__/Row.test.d.ts +1 -0
  79. package/dist/components/UclLogoNew/UclLogo.d.ts +8 -0
  80. package/dist/components/UclLogoNew/index.d.ts +2 -0
  81. package/dist/components/index.d.ts +12 -0
  82. package/dist/index.js +20909 -16022
  83. package/dist/theme/__tests__/fonts.test.d.ts +1 -0
  84. package/dist/theme/common/themeCommon.d.ts +904 -0
  85. package/dist/theme/fonts.d.ts +18 -0
  86. package/dist/theme/index.d.ts +6 -3
  87. package/dist/theme/light/lightColour.d.ts +126 -0
  88. package/dist/theme/light/lightTheme.d.ts +3 -0
  89. package/dist/theme/original/color.d.ts +166 -0
  90. package/dist/theme/original/defaultTheme.d.ts +1340 -0
  91. package/dist/theme/original/originalColourNewStructure.d.ts +126 -0
  92. package/dist/theme/useTheme.d.ts +2174 -0
  93. package/dist/utils/addAlphaToHex.d.ts +5 -0
  94. package/dist/utils/scrollToTop.d.ts +2 -0
  95. package/lib/components/Accordion/Accordion.Heading.tsx +51 -39
  96. package/lib/components/Accordion/Accordion.Panel.tsx +0 -4
  97. package/lib/components/Accordion/Accordion.tsx +34 -28
  98. package/lib/components/Accordion/__tests__/__snapshots__/Accordion.test.tsx.snap +12 -10
  99. package/lib/components/Alert/Alert.tsx +12 -12
  100. package/lib/components/Alert/__tests__/__snapshots__/Alert.test.tsx.snap +13 -39
  101. package/lib/components/AppHeader/AppHeader.tsx +6 -11
  102. package/lib/components/AppHeader/AppHeaderBottom.tsx +2 -3
  103. package/lib/components/AppHeader/AppHeaderNav.tsx +2 -3
  104. package/lib/components/AppHeader/AppHeaderTop.tsx +1 -1
  105. package/lib/components/AppHeader/__tests__/__snapshots__/AppHeader.test.tsx.snap +2 -2
  106. package/lib/components/AppMenu/__tests__/__snapshots__/AppMenu.test.tsx.snap +6 -19
  107. package/lib/components/Badge/Badge.stories.tsx +1 -1
  108. package/lib/components/Breadcrumbs/Breadcrumb.tsx +26 -12
  109. package/lib/components/Breadcrumbs/Breadcrumbs.tsx +1 -1
  110. package/lib/components/Breadcrumbs/__tests__/Breadcrumbs.test.tsx +9 -27
  111. package/lib/components/Breadcrumbs/__tests__/__snapshots__/Breadcrumbs.test.tsx.snap +24 -20
  112. package/lib/components/Button/Button.mdx +32 -279
  113. package/lib/components/Button/Button.stories.tsx +43 -50
  114. package/lib/components/Button/Button.tsx +165 -25
  115. package/lib/components/Button/__tests__/Button.test.tsx +49 -15
  116. package/lib/components/Button/__tests__/__snapshots__/Button.test.tsx.snap +80 -73
  117. package/lib/components/Button/style/buttonAccentStyle.ts +53 -0
  118. package/lib/components/Button/style/buttonPrimaryDestructiveStyle.ts +55 -0
  119. package/lib/components/Button/style/buttonPrimaryStyle.ts +53 -0
  120. package/lib/components/Button/style/buttonPrimarySubtleStyle.ts +64 -0
  121. package/lib/components/Button/style/buttonPrimaryWarningStyle.ts +56 -0
  122. package/lib/components/Button/style/buttonSecondaryDestructiveStyle.ts +63 -0
  123. package/lib/components/Button/style/buttonSecondaryStyle.ts +62 -0
  124. package/lib/components/Button/style/buttonSecondarySubtleStyle.ts +72 -0
  125. package/lib/components/Button/style/buttonTertiaryDestructiveStyle.ts +65 -0
  126. package/lib/components/Button/style/buttonTertiaryNoPaddingStyle.ts +52 -0
  127. package/lib/components/Button/style/buttonTertiaryStyle.ts +62 -0
  128. package/lib/components/Calendar/Calendar.stories.tsx +33 -13
  129. package/lib/components/Calendar/Calendar.tsx +2 -2
  130. package/lib/components/Calendar/__tests__/__snapshots__/Calendar.test.tsx.snap +99 -95
  131. package/lib/components/Calendar/subcomponents/AcademicWeek.tsx +2 -1
  132. package/lib/components/Calendar/subcomponents/AcademicWeeks.tsx +2 -3
  133. package/lib/components/Calendar/subcomponents/ColumnHeading.tsx +3 -7
  134. package/lib/components/Calendar/subcomponents/Controls.tsx +1 -1
  135. package/lib/components/Calendar/subcomponents/Day.stories.tsx +1 -1
  136. package/lib/components/Calendar/subcomponents/Day.tsx +7 -9
  137. package/lib/components/Calendar/subcomponents/EventDot.tsx +4 -8
  138. package/lib/components/Checkbox/Checkbox.stories.tsx +1 -1
  139. package/lib/components/Checkbox/Checkbox.tsx +12 -10
  140. package/lib/components/Checkbox/__tests__/Checkbox.test.tsx +29 -0
  141. package/lib/components/Checkbox/__tests__/__snapshots__/Checkbox.test.tsx.snap +4 -4
  142. package/lib/components/Datepicker/__tests__/Datepicker.test.tsx +117 -0
  143. package/lib/components/Datepicker/__tests__/__snapshots__/Datepicker.test.tsx.snap +16 -44
  144. package/lib/components/Datepicker/subcomponents/CustomDatepicker.tsx +10 -1
  145. package/lib/components/Datepicker/subcomponents/VisibleField.tsx +24 -23
  146. package/lib/components/Dialog/BaseDialog.tsx +2 -2
  147. package/lib/components/Dialog/Dialog.stories.tsx +1 -1
  148. package/lib/components/Divider/__tests__/__snapshots__/Breadcrumbs.test.tsx.snap +12 -12
  149. package/lib/components/FeedbackDialog/FeedbackDialog.stories.tsx +1 -1
  150. package/lib/components/FeedbackDialog/FeedbackDialog.tsx +4 -6
  151. package/lib/components/Field/CharacterCount.tsx +2 -2
  152. package/lib/components/Field/ErrorText.tsx +1 -1
  153. package/lib/components/Field/Field.tsx +1 -1
  154. package/lib/components/Field/HelperText.tsx +3 -1
  155. package/lib/components/FileInput/FileInput.stories.tsx +1 -1
  156. package/lib/components/FileInput/__tests__/__snapshots__/FileInput.test.tsx.snap +4 -20
  157. package/lib/components/Footer/__tests__/__snapshots__/Footer.test.tsx.snap +70 -79
  158. package/lib/components/FooterNew/BackToTop.tsx +83 -0
  159. package/lib/components/FooterNew/Footer.tsx +110 -0
  160. package/lib/components/FooterNew/FooterColumn.tsx +79 -0
  161. package/lib/components/FooterNew/FooterLinks.tsx +44 -0
  162. package/lib/components/FooterNew/FooterNavLink.tsx +63 -0
  163. package/lib/components/FooterNew/LegalAndCopyright.tsx +150 -0
  164. package/lib/components/FooterNew/LogoAddressAndSocial.tsx +154 -0
  165. package/lib/components/FooterNew/SocialLink.tsx +108 -0
  166. package/lib/components/FooterNew/__tests__/Footer.test.tsx +51 -0
  167. package/lib/components/FooterNew/__tests__/__snapshots__/Footer.test.tsx.snap +1107 -0
  168. package/lib/components/FooterNew/index.ts +2 -0
  169. package/lib/components/HeaderDraft/__tests__/__snapshots__/Header.test.tsx.snap +3 -2
  170. package/lib/components/HeaderNew/Header.tsx +93 -0
  171. package/lib/components/HeaderNew/HeaderBorder.tsx +55 -0
  172. package/lib/components/HeaderNew/HeaderLogo.tsx +70 -0
  173. package/lib/components/HeaderNew/HeaderMenuContainer.tsx +35 -0
  174. package/lib/components/HeaderNew/HeaderTitle.tsx +53 -0
  175. package/lib/components/HeaderNew/__tests__/Header.test.tsx +42 -0
  176. package/lib/components/HeaderNew/__tests__/__snapshots__/Header.test.tsx.snap +79 -0
  177. package/lib/components/HeaderNew/constants.ts +3 -0
  178. package/lib/components/HeaderNew/index.ts +7 -0
  179. package/lib/components/HeadingNew/Heading.tsx +208 -0
  180. package/lib/components/HeadingNew/index.ts +2 -0
  181. package/lib/components/Icon/__tests__/__snapshots__/Icon.test.tsx.snap +16 -12
  182. package/lib/components/Icon/svgImports.ts +318 -296
  183. package/lib/components/IconButton/IconButton.tsx +3 -4
  184. package/lib/components/IconButton/__tests__/__snapshots__/IconButton.test.tsx.snap +12 -9
  185. package/lib/components/Link/BaseLink.tsx +114 -71
  186. package/lib/components/Link/Link.stories.tsx +1 -1
  187. package/lib/components/Link/Link.tsx +120 -109
  188. package/lib/components/Link/__tests__/__snapshots__/link.test.tsx.snap +2 -2
  189. package/lib/components/MenuNew/Menu.context.tsx +149 -0
  190. package/lib/components/MenuNew/Menu.tsx +75 -0
  191. package/lib/components/MenuNew/MenuContent.tsx +140 -0
  192. package/lib/components/MenuNew/MenuItem.tsx +101 -0
  193. package/lib/components/MenuNew/MenuSection.tsx +47 -0
  194. package/lib/components/MenuNew/index.ts +8 -0
  195. package/lib/components/MenuNew/trigger/ButtonMenuTrigger.tsx +42 -0
  196. package/lib/components/MenuNew/trigger/IconMenuTrigger.tsx +40 -0
  197. package/lib/components/Pagination/Pagination.stories.tsx +1 -1
  198. package/lib/components/Pagination/PaginationControls.tsx +4 -5
  199. package/lib/components/Pagination/PaginationInfo.tsx +2 -3
  200. package/lib/components/ParagraphNew/Paragraph.tsx +200 -0
  201. package/lib/components/ParagraphNew/index.ts +6 -0
  202. package/lib/components/Radio/Radio.stories.tsx +1 -1
  203. package/lib/components/Radio/Radio.tsx +8 -8
  204. package/lib/components/Radio/__tests__/__snapshots__/Radio.test.tsx.snap +4 -4
  205. package/lib/components/Search/__tests__/__snapshots__/Search.test.tsx.snap +12 -32
  206. package/lib/components/Select/Select.mdx +23 -0
  207. package/lib/components/Select/Select.stories.tsx +43 -10
  208. package/lib/components/Select/Select.tsx +14 -3
  209. package/lib/components/Select/Select.types.ts +53 -16
  210. package/lib/components/Select/__tests__/Select.test.tsx +250 -1
  211. package/lib/components/Select/__tests__/__snapshots__/Select.test.tsx.snap +5 -4
  212. package/lib/components/Select/subcomponents/CustomOption.tsx +10 -3
  213. package/lib/components/Select/subcomponents/CustomSelect.tsx +110 -10
  214. package/lib/components/Select/subcomponents/FilterInput.tsx +13 -3
  215. package/lib/components/Select/subcomponents/NativeSelect.tsx +10 -18
  216. package/lib/components/Select/subcomponents/Panel.tsx +2 -2
  217. package/lib/components/Select/subcomponents/VisibleField.tsx +48 -3
  218. package/lib/components/Snackbar/__tests__/__snapshots__/Snackbar.test.tsx.snap +9 -15
  219. package/lib/components/Spinner/Spinner.tsx +24 -5
  220. package/lib/components/Spinner/__tests__/Spinner.test.tsx +35 -5
  221. package/lib/components/Spinner/__tests__/__snapshots__/Spinner.test.tsx.snap +40 -16
  222. package/lib/components/StandaloneLink/StandaloneLink.stories.tsx +1 -1
  223. package/lib/components/StandaloneLink/StandaloneLink.tsx +180 -163
  224. package/lib/components/StandaloneLink/__tests__/__snapshots__/StandaloneLink.test.tsx.snap +2 -2
  225. package/lib/components/Table/Table.stories.tsx +1 -1
  226. package/lib/components/Table/Table.tsx +2 -0
  227. package/lib/components/Table/Table.types.ts +1 -0
  228. package/lib/components/Table/__tests__/Table.test.tsx +19 -0
  229. package/lib/components/Table/__tests__/__snapshots__/Table.test.tsx.snap +7 -3
  230. package/lib/components/Table/subcomponents/Cell/Cell.stories.tsx +1 -1
  231. package/lib/components/Table/subcomponents/Cell/Cell.tsx +23 -2
  232. package/lib/components/Table/subcomponents/Cell/CellContent.tsx +12 -1
  233. package/lib/components/Table/subcomponents/Cell/__tests__/Cell.test.tsx +106 -0
  234. package/lib/components/Table/subcomponents/Cell/__tests__/__snapshots__/Cell.test.tsx.snap +4 -3
  235. package/lib/components/Table/subcomponents/HeadCell/HeadCell.stories.tsx +1 -1
  236. package/lib/components/Table/subcomponents/HeadCell/HeadCell.tsx +28 -6
  237. package/lib/components/Table/subcomponents/HeadCell/HeadCellContent.tsx +3 -0
  238. package/lib/components/Table/subcomponents/HeadCell/__tests__/HeadCell.test.tsx +221 -2
  239. package/lib/components/Table/subcomponents/HeadCell/__tests__/__snapshots__/HeadCell.test.tsx.snap +6 -4
  240. package/lib/components/Table/subcomponents/Row.tsx +2 -2
  241. package/lib/components/Table/subcomponents/SortIcon.tsx +1 -0
  242. package/lib/components/Table/subcomponents/__tests__/Row.test.tsx +59 -0
  243. package/lib/components/Tabs/Tab.tsx +3 -3
  244. package/lib/components/Tabs/Tabs.stories.tsx +1 -1
  245. package/lib/components/Tabs/Tabs.tsx +5 -3
  246. package/lib/components/Tabs/__tests__/__snapshots__/Tabs.test.tsx.snap +4 -4
  247. package/lib/components/Timepicker/Timepicker.stories.tsx +1 -1
  248. package/lib/components/Toggle/Toggle.tsx +5 -5
  249. package/lib/components/Toggle/ToggleHandle.tsx +2 -3
  250. package/lib/components/Tooltip/Tooltip.tsx +2 -2
  251. package/lib/components/Tooltip/__tests__/__snapshots__/tooltip.test.tsx.snap +2 -2
  252. package/lib/components/UclLogoNew/UclLogo.tsx +42 -0
  253. package/lib/components/UclLogoNew/index.ts +2 -0
  254. package/lib/components/WeekPicker/WeekPicker.stories.tsx +3 -5
  255. package/lib/components/common/Common.mdx +0 -1
  256. package/lib/components/index.ts +19 -1
  257. package/lib/theme/Colours.mdx +1 -1
  258. package/lib/theme/Theme.mdx +1 -1
  259. package/lib/theme/Typography.mdx +1 -1
  260. package/lib/theme/__tests__/fonts.test.ts +37 -0
  261. package/lib/theme/common/themeCommon.ts +515 -0
  262. package/lib/theme/fonts.ts +110 -0
  263. package/lib/theme/index.ts +6 -6
  264. package/lib/theme/light/lightColour.ts +232 -0
  265. package/lib/theme/light/lightTheme.ts +37 -0
  266. package/lib/theme/{defaultTheme.ts → original/color.ts} +17 -199
  267. package/lib/theme/original/defaultTheme.ts +207 -0
  268. package/lib/theme/original/originalColourNewStructure.ts +185 -0
  269. package/lib/theme/useTheme.tsx +72 -15
  270. package/lib/types/assets.d.ts +10 -0
  271. package/lib/utils/addAlphaToHex.ts +29 -0
  272. package/lib/utils/scrollToTop.ts +5 -0
  273. package/package.json +11 -6
  274. package/dist/components/Button/buttonPrimaryStyle.d.ts +0 -4
  275. package/dist/components/Button/buttonSecondaryStyle.d.ts +0 -4
  276. package/dist/components/Button/buttonTertiaryStyle.d.ts +0 -4
  277. package/dist/theme/defaultTheme.d.ts +0 -274
  278. package/lib/components/Button/buttonPrimaryStyle.ts +0 -62
  279. package/lib/components/Button/buttonSecondaryStyle.ts +0 -65
  280. package/lib/components/Button/buttonTertiaryStyle.ts +0 -54
@@ -0,0 +1,200 @@
1
+ import { memo, HTMLAttributes, JSX } from 'react';
2
+ import { css, cx } from '@emotion/css';
3
+ import useTheme from '../../theme/useTheme';
4
+ import marginsStyle, { MarginProps } from '../common/marginsStyle';
5
+
6
+ export const NAME = 'ucl-uikit-paragrah';
7
+
8
+ export type ParagraphLevel =
9
+ | 'lg'
10
+ | 'lg-medium'
11
+ | 'lg-semibold'
12
+ | 'lg-bold'
13
+ | 'md'
14
+ | 'md-medium'
15
+ | 'md-semibold'
16
+ | 'md-semibold'
17
+ | 'md-medium-numeric'
18
+ | 'sm'
19
+ | 'sm-medium'
20
+ | 'sm-semibold'
21
+ | 'xs'
22
+ | 'xs-medium';
23
+
24
+ export interface ParagraphBaseProps extends HTMLAttributes<HTMLParagraphElement> {
25
+ level?: ParagraphLevel;
26
+ as?: 'p' | 'div' | 'span';
27
+ testId?: string;
28
+ ref?: React.Ref<HTMLParagraphElement>;
29
+ }
30
+
31
+ export type ParagraphProps = ParagraphBaseProps & MarginProps;
32
+
33
+ const Paragraph = ({
34
+ level = 'md',
35
+ as = 'p',
36
+ testId = NAME,
37
+ className,
38
+ ref,
39
+ ...props
40
+ }: ParagraphProps) => {
41
+ const [theme] = useTheme();
42
+
43
+ const {
44
+ typography: {
45
+ body: {
46
+ lg,
47
+ lgMedium,
48
+ lgSemibold,
49
+ lgBold,
50
+ md,
51
+ mdMedium,
52
+ mdSemibold,
53
+ mdMediumNumeric,
54
+ sm,
55
+ smMedium,
56
+ smSemibold,
57
+ xs,
58
+ xsMedium,
59
+ },
60
+ },
61
+ } = theme;
62
+
63
+ const baseStyle = css`
64
+ font-family: ${md.fontFamily};
65
+ font-feature-settings: ${md.fontSettings};
66
+ color: ${theme.colour.text.default};
67
+ margin: 0;
68
+ `;
69
+
70
+ const lgStyle = css`
71
+ font-size: ${lg.fontSize}px;
72
+ font-weight: ${lg.fontWeight};
73
+ line-height: ${lg.lineHeight}%;
74
+ `;
75
+
76
+ const lgMediumStyle = css`
77
+ font-size: ${lgMedium.fontSize}px;
78
+ font-weight: ${lgMedium.fontWeight};
79
+ line-height: ${lgMedium.lineHeight}%;
80
+ `;
81
+
82
+ const lgSemiboldStyle = css`
83
+ font-size: ${lgSemibold.fontSize}px;
84
+ font-weight: ${lgSemibold.fontWeight};
85
+ line-height: ${lgSemibold.lineHeight}%;
86
+ `;
87
+
88
+ const lgBoldStyle = css`
89
+ font-size: ${lgBold.fontSize}px;
90
+ font-weight: ${lgBold.fontWeight};
91
+ line-height: ${lgBold.lineHeight}%;
92
+ `;
93
+
94
+ const mdStyle = css`
95
+ font-size: ${md.fontSize}px;
96
+ font-weight: ${md.fontWeight};
97
+ line-height: ${md.lineHeight}%;
98
+ `;
99
+
100
+ const mdMediumStyle = css`
101
+ font-size: ${mdMedium.fontSize}px;
102
+ font-weight: ${mdMedium.fontWeight};
103
+ line-height: ${mdMedium.lineHeight}%;
104
+ `;
105
+
106
+ const mdSemiboldStyle = css`
107
+ font-size: ${mdSemibold.fontSize}px;
108
+ font-weight: ${mdSemibold.fontWeight};
109
+ line-height: ${mdSemibold.lineHeight}%;
110
+ `;
111
+
112
+ const mdMediumNumericStyle = css`
113
+ font-size: ${mdMediumNumeric.fontSize}px;
114
+ font-weight: ${mdMediumNumeric.fontWeight};
115
+ line-height: ${mdMediumNumeric.lineHeight}%;
116
+ `;
117
+
118
+ const smStyle = css`
119
+ font-size: ${sm.fontSize}px;
120
+ font-weight: ${sm.fontWeight};
121
+ line-height: ${sm.lineHeight}%;
122
+ `;
123
+
124
+ const smMediumStyle = css`
125
+ font-size: ${smMedium.fontSize}px;
126
+ font-weight: ${smMedium.fontWeight};
127
+ line-height: ${smMedium.lineHeight}%;
128
+ `;
129
+
130
+ const smSemiboldStyle = css`
131
+ font-size: ${smSemibold.fontSize}px;
132
+ font-weight: ${smSemibold.fontWeight};
133
+ line-height: ${smSemibold.lineHeight}%;
134
+ `;
135
+
136
+ const xsStyle = css`
137
+ font-size: ${xs.fontSize}px;
138
+ font-weight: ${xs.fontWeight};
139
+ line-height: ${xs.lineHeight}%;
140
+ `;
141
+
142
+ const xsMediumStyle = css`
143
+ font-size: ${xsMedium.fontSize}px;
144
+ font-weight: ${xsMedium.fontWeight};
145
+ line-height: ${xsMedium.lineHeight}%;
146
+ `;
147
+
148
+ const style = cx(
149
+ NAME,
150
+ baseStyle,
151
+ level === 'lg' && lgStyle,
152
+ level === 'lg-medium' && lgMediumStyle,
153
+ level === 'lg-semibold' && lgSemiboldStyle,
154
+ level === 'lg-bold' && lgBoldStyle,
155
+ level === 'md' && mdStyle,
156
+ level === 'md-medium' && mdMediumStyle,
157
+ level === 'md-semibold' && mdSemiboldStyle,
158
+ level === 'md-medium-numeric' && mdMediumNumericStyle,
159
+ level === 'sm' && smStyle,
160
+ level === 'sm-medium' && smMediumStyle,
161
+ level === 'sm-semibold' && smSemiboldStyle,
162
+ level === 'xs' && xsStyle,
163
+ level === 'xs-medium' && xsMediumStyle,
164
+ marginsStyle(props, theme),
165
+ className
166
+ );
167
+
168
+ const paragraphTag = as as keyof JSX.IntrinsicElements;
169
+
170
+ return (
171
+ <>
172
+ {paragraphTag === 'p' && (
173
+ <p
174
+ ref={ref}
175
+ className={style}
176
+ data-testid={testId}
177
+ {...props}
178
+ />
179
+ )}
180
+ {paragraphTag === 'div' && (
181
+ <div
182
+ ref={ref as React.Ref<HTMLDivElement>}
183
+ className={style}
184
+ data-testid={testId}
185
+ {...props}
186
+ />
187
+ )}
188
+ {paragraphTag === 'span' && (
189
+ <span
190
+ ref={ref as React.Ref<HTMLSpanElement>}
191
+ className={style}
192
+ data-testid={testId}
193
+ {...props}
194
+ />
195
+ )}
196
+ </>
197
+ );
198
+ };
199
+
200
+ export default memo(Paragraph);
@@ -0,0 +1,6 @@
1
+ export { default } from './Paragraph';
2
+ export type { ParagraphProps } from './Paragraph';
3
+ // TODO: Remove aliased export in future breaking release
4
+ // <Paragraph> will be used in place of <Text> in the future
5
+ export { default as Text } from './Paragraph';
6
+ export type { ParagraphProps as TextProps } from './Paragraph';
@@ -4,7 +4,7 @@ import { useArgs } from '@storybook/preview-api';
4
4
  import Radio from './Radio';
5
5
 
6
6
  const meta = {
7
- title: 'Components/Work in progress/Radio',
7
+ title: 'Components/Radio',
8
8
  component: Radio,
9
9
  argTypes: {
10
10
  checked: { control: { type: 'boolean' } },
@@ -64,19 +64,19 @@ const Radio = forwardRef<Ref, RadioProps>(
64
64
  `;
65
65
 
66
66
  const checkedStyle = css`
67
- background-color: ${theme.color.interaction.blue70};
68
- border-color: ${theme.color.interaction.blue70};
69
- color: ${theme.color.neutral.white};
67
+ background-color: ${theme.colour.icon.brand};
68
+ border-color: ${theme.colour.icon.brand};
69
+ color: ${theme.colour.icon.inverse};
70
70
  `;
71
71
 
72
72
  const uncheckedStyle = css`
73
- background-color: ${theme.color.neutral.white};
74
- border-color: ${theme.color.neutral.grey60};
73
+ background-color: ${theme.colour.icon.inverse};
74
+ border-color: ${theme.colour.speciality.inputDefault};
75
75
  `;
76
76
 
77
77
  const disabledStyle = css`
78
- background-color: ${theme.color.neutral.grey20};
79
- border-color: ${theme.color.neutral.grey20};
78
+ background-color: ${theme.colour.icon.disabled};
79
+ border-color: ${theme.colour.icon.disabled};
80
80
  cursor: not-allowed;
81
81
  `;
82
82
 
@@ -112,7 +112,7 @@ const Radio = forwardRef<Ref, RadioProps>(
112
112
  width: 12px;
113
113
  height: 12px;
114
114
  border-radius: 50%;
115
- background-color: ${theme.color.neutral.white};
115
+ background-color: ${theme.colour.icon.inverse};
116
116
  user-select: none;
117
117
  pointer-events: none;
118
118
  `;
@@ -2,7 +2,7 @@
2
2
 
3
3
  exports[`Radio > snapshot: checked prop 1`] = `
4
4
  <span
5
- class="ucl-uikit-radio css-1q95rl4"
5
+ class="ucl-uikit-radio css-1y63xt7"
6
6
  >
7
7
  <input
8
8
  checked=""
@@ -11,14 +11,14 @@ exports[`Radio > snapshot: checked prop 1`] = `
11
11
  type="radio"
12
12
  />
13
13
  <div
14
- class="css-qvbxw4"
14
+ class="css-19pto6h"
15
15
  />
16
16
  </span>
17
17
  `;
18
18
 
19
19
  exports[`Radio > snapshot: no props 1`] = `
20
20
  <span
21
- class="ucl-uikit-radio css-12hblv5"
21
+ class="ucl-uikit-radio css-121ivaw"
22
22
  >
23
23
  <input
24
24
  class="css-19qtec1"
@@ -30,7 +30,7 @@ exports[`Radio > snapshot: no props 1`] = `
30
30
 
31
31
  exports[`Radio > snapshot: testId prop 1`] = `
32
32
  <span
33
- class="ucl-uikit-radio css-12hblv5"
33
+ class="ucl-uikit-radio css-121ivaw"
34
34
  >
35
35
  <input
36
36
  class="css-19qtec1"
@@ -28,6 +28,7 @@ exports[`Search > snapshot: no props 1`] = `
28
28
  class="ucl-uikit-icon css-148hpxb"
29
29
  data-testid="ucl-uikit-icon"
30
30
  fill="none"
31
+ focusable="false"
31
32
  height="24"
32
33
  stroke="currentColor"
33
34
  stroke-linecap="round"
@@ -37,17 +38,8 @@ exports[`Search > snapshot: no props 1`] = `
37
38
  width="24"
38
39
  xmlns="http://www.w3.org/2000/svg"
39
40
  >
40
- <line
41
- x1="18"
42
- x2="6"
43
- y1="6"
44
- y2="18"
45
- />
46
- <line
47
- x1="6"
48
- x2="18"
49
- y1="6"
50
- y2="18"
41
+ <path
42
+ d="M18 6 6 18M6 6l12 12"
51
43
  />
52
44
  </svg>
53
45
  </button>
@@ -63,6 +55,7 @@ exports[`Search > snapshot: no props 1`] = `
63
55
  class="ucl-uikit-icon css-148hpxb"
64
56
  data-testid="ucl-uikit-icon"
65
57
  fill="none"
58
+ focusable="false"
66
59
  height="24"
67
60
  stroke="currentColor"
68
61
  stroke-linecap="round"
@@ -77,11 +70,8 @@ exports[`Search > snapshot: no props 1`] = `
77
70
  cy="11"
78
71
  r="8"
79
72
  />
80
- <line
81
- x1="21"
82
- x2="16.65"
83
- y1="21"
84
- y2="16.65"
73
+ <path
74
+ d="m21 21-4.35-4.35"
85
75
  />
86
76
  </svg>
87
77
  </button>
@@ -117,6 +107,7 @@ exports[`Search > snapshot: testId prop 1`] = `
117
107
  class="ucl-uikit-icon css-148hpxb"
118
108
  data-testid="ucl-uikit-icon"
119
109
  fill="none"
110
+ focusable="false"
120
111
  height="24"
121
112
  stroke="currentColor"
122
113
  stroke-linecap="round"
@@ -126,17 +117,8 @@ exports[`Search > snapshot: testId prop 1`] = `
126
117
  width="24"
127
118
  xmlns="http://www.w3.org/2000/svg"
128
119
  >
129
- <line
130
- x1="18"
131
- x2="6"
132
- y1="6"
133
- y2="18"
134
- />
135
- <line
136
- x1="6"
137
- x2="18"
138
- y1="6"
139
- y2="18"
120
+ <path
121
+ d="M18 6 6 18M6 6l12 12"
140
122
  />
141
123
  </svg>
142
124
  </button>
@@ -152,6 +134,7 @@ exports[`Search > snapshot: testId prop 1`] = `
152
134
  class="ucl-uikit-icon css-148hpxb"
153
135
  data-testid="ucl-uikit-icon"
154
136
  fill="none"
137
+ focusable="false"
155
138
  height="24"
156
139
  stroke="currentColor"
157
140
  stroke-linecap="round"
@@ -166,11 +149,8 @@ exports[`Search > snapshot: testId prop 1`] = `
166
149
  cy="11"
167
150
  r="8"
168
151
  />
169
- <line
170
- x1="21"
171
- x2="16.65"
172
- y1="21"
173
- y2="16.65"
152
+ <path
153
+ d="m21 21-4.35-4.35"
174
154
  />
175
155
  </svg>
176
156
  </button>
@@ -32,6 +32,17 @@ export const usage = {
32
32
  onValueChange={handleChange}
33
33
  placeholder="Type to filter..."
34
34
  filterInputProps={{ 'aria-describedby': 'filter-hint' }}
35
+ />`,
36
+ clearable: `<Select
37
+ clearable
38
+ options={[
39
+ { label: 'Option one', value: '1' },
40
+ { label: 'Option two', value: '2' },
41
+ { label: 'Option three', value: '3' },
42
+ ]}
43
+ value={value}
44
+ onValueChange={handleChange}
45
+ placeholder="Clear selection"
35
46
  />`,
36
47
  selectionBehaviourCommit: `<Select
37
48
  selectionBehaviour="commit"
@@ -78,6 +89,7 @@ Key features:
78
89
  - Configurable keyboard selection behaviour via `selectionBehaviour` (`focus` or `commit`)
79
90
  - Optional native fallback (`native`)
80
91
  - Optional filterable dropdown (`filterable`) that lets users type to narrow options
92
+ - Optional clear action (`clearable`) in the custom variant
81
93
  - `filterInputProps` to forward additional attributes (e.g. `aria-describedby`) to the filter input
82
94
  - Support for long option text via `lineBreak`
83
95
  - Disabled state and placeholder support
@@ -132,6 +144,15 @@ Use `filterInputProps` to pass extra attributes to the input (e.g. `aria-describ
132
144
  source={{ code: usage.filterable }}
133
145
  />
134
146
 
147
+ ### Clearable
148
+ Adds a built-in clear button in the custom variant when a selection is present. Clearing calls `onValueChange(null, event)` and restores the placeholder text.
149
+
150
+ <Canvas
151
+ of={SelectStories.Clearable}
152
+ sourceState="shown"
153
+ source={{ code: usage.clearable }}
154
+ />
155
+
135
156
  ### Selection behaviour
136
157
  Use `selectionBehaviour` to control how keyboard navigation commits value in the custom variant:
137
158
  - `focus` (default): arrow keys move and commit immediately.
@@ -149,8 +170,10 @@ For very long labels, set `lineBreak` to allow breaking the text inside options.
149
170
  ## Accessibility
150
171
  - Custom variant exposes `role="combobox"` and `aria-expanded`, and listens for Enter/Space/Escape/arrow keys.
151
172
  - In `selectionBehaviour="commit"`, arrow keys move highlight without changing value until Enter/click.
173
+ - Tabbing away from an open custom dropdown closes it and lets focus move normally to the next or previous control.
152
174
  - Native variant leverages built-in browser semantics.
153
175
  - The filter input (when `filterable` is true) is focusable when the panel opens; Escape and arrow keys bubble to the parent so the dropdown still closes/navigates.
176
+ - In the custom variant, `clearable` emits `null` as the cleared value.
154
177
  - `filterInputProps` lets you forward ARIA hooks like `aria-describedby` to the filter input.
155
178
  - Standard HTML attributes (`id`, `title`, `data-*`) are forwarded to the combobox/native select.
156
179
 
@@ -25,9 +25,9 @@ const meta = {
25
25
  table: { type: { summary: 'OptionData[]' } },
26
26
  },
27
27
  value: {
28
- description: 'Selected value (string | number)',
28
+ description: 'Selected value (string | number | null)',
29
29
  control: { type: 'text' },
30
- table: { type: { summary: 'string | number' } },
30
+ table: { type: { summary: 'string | number | null' } },
31
31
  },
32
32
  onValueChange: {
33
33
  description:
@@ -35,7 +35,8 @@ const meta = {
35
35
  control: false,
36
36
  table: {
37
37
  type: {
38
- summary: '(value: string | number, ev: React.UIEvent) => void',
38
+ summary:
39
+ '(value: string | number | null, ev: React.SyntheticEvent) => void',
39
40
  },
40
41
  },
41
42
  },
@@ -67,6 +68,12 @@ const meta = {
67
68
  control: { type: 'boolean' },
68
69
  table: { type: { summary: 'boolean' } },
69
70
  },
71
+ clearable: {
72
+ description:
73
+ 'Show a clear action in the custom variant when a value is selected',
74
+ control: { type: 'boolean' },
75
+ table: { type: { summary: 'boolean' } },
76
+ },
70
77
  filterInputProps: {
71
78
  description:
72
79
  'Additional props to spread onto the filter input (when filterable)',
@@ -131,7 +138,7 @@ type Story = StoryObj<typeof meta>;
131
138
  export const Default: Story = {
132
139
  render: () => {
133
140
  const [args, updateArgs] = useArgs();
134
- const onValueChange = (value: string | number) => {
141
+ const onValueChange = (value: string | number | null) => {
135
142
  updateArgs({ value });
136
143
  };
137
144
  return (
@@ -176,7 +183,7 @@ export const Disabled: Story = {
176
183
  },
177
184
  render: () => {
178
185
  const [args, updateArgs] = useArgs();
179
- const onValueChange = (value: string | number) => {
186
+ const onValueChange = (value: string | number | null) => {
180
187
  updateArgs({ value });
181
188
  };
182
189
 
@@ -198,7 +205,7 @@ export const WithPlaceholder: Story = {
198
205
  args: { placeholder: 'Please select an option' },
199
206
  render: () => {
200
207
  const [args, updateArgs] = useArgs();
201
- const onValueChange = (value: string | number) => {
208
+ const onValueChange = (value: string | number | null) => {
202
209
  updateArgs({ value });
203
210
  };
204
211
 
@@ -227,7 +234,7 @@ export const SingleLongOption: Story = {
227
234
  },
228
235
  render: () => {
229
236
  const [args, updateArgs] = useArgs();
230
- const onValueChange = (value: string | number) => {
237
+ const onValueChange = (value: string | number | null) => {
231
238
  updateArgs({ value });
232
239
  };
233
240
 
@@ -268,7 +275,7 @@ export const ManyOptions: Story = {
268
275
  },
269
276
  render: () => {
270
277
  const [args, updateArgs] = useArgs();
271
- const onValueChange = (value: string | number) => {
278
+ const onValueChange = (value: string | number | null) => {
272
279
  updateArgs({ value });
273
280
  };
274
281
  return (
@@ -289,7 +296,8 @@ export const filterable: Story = {
289
296
  args: { filterable: true },
290
297
  render: () => {
291
298
  const [args, updateArgs] = useArgs();
292
- const onValueChange = (value: string | number) => updateArgs({ value });
299
+ const onValueChange = (value: string | number | null) =>
300
+ updateArgs({ value });
293
301
  return (
294
302
  <div style={storyWrapperStyle}>
295
303
  <Select
@@ -305,12 +313,37 @@ export const filterable: Story = {
305
313
  },
306
314
  };
307
315
 
316
+ export const Clearable: Story = {
317
+ args: {
318
+ clearable: true,
319
+ value: '2',
320
+ placeholder: 'Clear selection',
321
+ },
322
+ render: () => {
323
+ const [args, updateArgs] = useArgs();
324
+ const onValueChange = (value: string | number | null) =>
325
+ updateArgs({ value });
326
+ return (
327
+ <div style={storyWrapperStyle}>
328
+ <Select
329
+ {...args}
330
+ className={select400pxWidthClass}
331
+ options={args.options}
332
+ value={args.value}
333
+ onValueChange={onValueChange}
334
+ />
335
+ </div>
336
+ );
337
+ },
338
+ };
339
+
308
340
  export const SelectionBehaviourCommit: Story = {
309
341
  name: 'Selection behaviour: commit',
310
342
  args: { selectionBehaviour: 'commit' },
311
343
  render: () => {
312
344
  const [args, updateArgs] = useArgs();
313
- const onValueChange = (value: string | number) => updateArgs({ value });
345
+ const onValueChange = (value: string | number | null) =>
346
+ updateArgs({ value });
314
347
  return (
315
348
  <div style={storyWrapperStyle}>
316
349
  <Select
@@ -1,11 +1,18 @@
1
1
  import { NativeSelect, CustomSelect } from './subcomponents';
2
- import { SelectProps } from './Select.types';
2
+ import type { InternalSelectProps, SelectProps } from './Select.types';
3
3
 
4
- const Select = <T extends string | number = string>(props: SelectProps<T>) => {
4
+ type SelectComponent = <T extends string | number = string>(
5
+ props: SelectProps<T>
6
+ ) => React.JSX.Element;
7
+
8
+ const Select = (<T extends string | number = string>(
9
+ props: InternalSelectProps<T>
10
+ ) => {
5
11
  const {
6
12
  native,
7
13
  nativeHtmlAttributes,
8
14
  filterable,
15
+ clearable,
9
16
  onValueChange,
10
17
  ref,
11
18
  ...rest
@@ -15,6 +22,9 @@ const Select = <T extends string | number = string>(props: SelectProps<T>) => {
15
22
  if (filterable) {
16
23
  console.warn('filterable is not supported on native Select; ignoring.');
17
24
  }
25
+ if (clearable) {
26
+ console.warn('clearable is not supported on native Select; ignoring.');
27
+ }
18
28
  const { value, ...nativeRest } = rest;
19
29
  const {
20
30
  value: nativeAttrValue,
@@ -40,10 +50,11 @@ const Select = <T extends string | number = string>(props: SelectProps<T>) => {
40
50
  <CustomSelect<T>
41
51
  onValueChange={onValueChange}
42
52
  filterable={filterable}
53
+ clearable={clearable}
43
54
  ref={ref as React.Ref<HTMLDivElement>}
44
55
  {...rest}
45
56
  />
46
57
  );
47
- };
58
+ }) as SelectComponent;
48
59
 
49
60
  export default Select;