@scottish-government/designsystem-react 0.10.2 → 0.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (175) hide show
  1. package/@types/components/Accordion.d.ts +3 -2
  2. package/@types/components/ButtonGroup.d.ts +5 -0
  3. package/@types/components/PageHeader.d.ts +2 -1
  4. package/@types/components/RadioButton.d.ts +2 -2
  5. package/@types/components/SearchFacets.d.ts +18 -0
  6. package/@types/components/SearchFilters.d.ts +14 -0
  7. package/@types/components/SearchResult.d.ts +30 -0
  8. package/@types/components/SearchSort.d.ts +9 -0
  9. package/@types/components/SideNavigation.d.ts +1 -1
  10. package/CHANGELOG.md +39 -5
  11. package/dist/common/AbstractNotificationBanner.d.ts +9 -0
  12. package/dist/common/ActionLink.d.ts +5 -0
  13. package/dist/common/ConditionalWrapper.d.ts +8 -0
  14. package/dist/common/FileIcon.d.ts +6 -0
  15. package/dist/common/HintText.d.ts +5 -0
  16. package/dist/common/Icon.d.ts +6 -0
  17. package/dist/common/ScreenReaderText.d.ts +5 -0
  18. package/dist/common/WrapperTag.d.ts +8 -0
  19. package/dist/components/Accordion/Accordion.d.ts +10 -0
  20. package/dist/components/Accordion/Accordion.jsx +8 -3
  21. package/dist/components/AspectBox/AspectBox.d.ts +6 -0
  22. package/dist/components/BackToTop/BackToTop.d.ts +5 -0
  23. package/dist/components/Breadcrumbs/Breadcrumbs.d.ts +9 -0
  24. package/dist/components/Button/Button.d.ts +5 -0
  25. package/dist/components/ButtonGroup/ButtonGroup.d.ts +5 -0
  26. package/dist/components/ButtonGroup/ButtonGroup.jsx +13 -0
  27. package/dist/components/CategoryItem/CategoryItem.d.ts +5 -0
  28. package/dist/components/CategoryList/CategoryList.d.ts +6 -0
  29. package/dist/components/Checkbox/Checkbox.d.ts +5 -0
  30. package/dist/components/Checkbox/CheckboxGroup.d.ts +6 -0
  31. package/dist/components/ConfirmationMessage/ConfirmationMessage.d.ts +5 -0
  32. package/dist/components/ContentsNav/ContentsNav.d.ts +10 -0
  33. package/dist/components/CookieBanner/CookieBanner.d.ts +9 -0
  34. package/dist/components/DatePicker/DatePicker.d.ts +5 -0
  35. package/dist/components/Details/Details.d.ts +5 -0
  36. package/dist/components/ErrorMessage/ErrorMessage.d.ts +5 -0
  37. package/dist/components/ErrorSummary/ErrorSummary.d.ts +9 -0
  38. package/dist/components/FileDownload/FileDownload.d.ts +5 -0
  39. package/dist/components/HideThisPage/HideThisPage.d.ts +6 -0
  40. package/dist/components/InsetText/InsetText.d.ts +5 -0
  41. package/dist/components/NotificationBanner/NotificationBanner.d.ts +9 -0
  42. package/dist/components/NotificationPanel/NotificationPanel.d.ts +5 -0
  43. package/dist/components/PageHeader/PageHeader.d.ts +5 -0
  44. package/dist/components/PageHeader/PageHeader.jsx +2 -2
  45. package/dist/components/PageMetadata/PageMetadata.d.ts +9 -0
  46. package/dist/components/Pagination/Pagination.d.ts +7 -0
  47. package/dist/components/PhaseBanner/PhaseBanner.d.ts +5 -0
  48. package/dist/components/Question/Question.d.ts +5 -0
  49. package/dist/components/RadioButton/RadioButton.d.ts +5 -0
  50. package/dist/components/RadioButton/RadioGroup.d.ts +6 -0
  51. package/dist/components/RadioButton/RadioGroup.jsx +1 -1
  52. package/dist/components/SearchFacets/SearchFacets.d.ts +14 -0
  53. package/dist/components/SearchFacets/SearchFacets.jsx +101 -0
  54. package/dist/components/SearchFilters/SearchFilters.d.ts +16 -0
  55. package/dist/components/SearchFilters/SearchFilters.jsx +63 -0
  56. package/dist/components/SearchResult/SearchResult.d.ts +28 -0
  57. package/dist/components/SearchResult/SearchResult.jsx +93 -0
  58. package/dist/components/SearchSort/SearchSort.d.ts +10 -0
  59. package/dist/components/SearchSort/SearchSort.jsx +28 -0
  60. package/dist/components/Select/Select.d.ts +5 -0
  61. package/dist/components/SequentialNavigation/SequentialNavigation.d.ts +13 -0
  62. package/dist/components/SequentialNavigation/SequentialNavigation.jsx +0 -1
  63. package/dist/components/SideNavigation/SideNavigation.d.ts +13 -0
  64. package/dist/components/SideNavigation/SideNavigation.jsx +2 -2
  65. package/dist/components/SiteFooter/SiteFooter.d.ts +22 -0
  66. package/dist/components/SiteHeader/SiteHeader.d.ts +22 -0
  67. package/dist/components/SiteHeader/SiteHeader.jsx +0 -1
  68. package/dist/components/SiteNavigation/SiteNavigation.d.ts +9 -0
  69. package/dist/components/SiteSearch/SiteSearch.d.ts +5 -0
  70. package/dist/components/SkipLinks/SkipLinks.d.ts +10 -0
  71. package/dist/components/SkipLinks/SkipLinks.jsx +42 -0
  72. package/dist/components/SummaryCard/SummaryCard.d.ts +10 -0
  73. package/dist/components/SummaryList/SummaryList.d.ts +18 -0
  74. package/dist/components/Table/Table.d.ts +5 -0
  75. package/dist/components/Tabs/Tabs.d.ts +10 -0
  76. package/dist/components/Tag/Tag.d.ts +5 -0
  77. package/dist/components/TaskList/TaskList.d.ts +13 -0
  78. package/dist/components/TextInput/TextInput.d.ts +5 -0
  79. package/dist/components/Textarea/Textarea.d.ts +5 -0
  80. package/dist/components/WarningText/WarningText.d.ts +5 -0
  81. package/dist/hooks/useTracking.d.ts +1 -0
  82. package/dist/images/documents/audio.d.ts +4 -0
  83. package/dist/images/documents/csv.d.ts +4 -0
  84. package/dist/images/documents/excel.d.ts +4 -0
  85. package/dist/images/documents/file.d.ts +4 -0
  86. package/dist/images/documents/generic.d.ts +4 -0
  87. package/dist/images/documents/geodata.d.ts +4 -0
  88. package/dist/images/documents/ical.d.ts +4 -0
  89. package/dist/images/documents/ico.d.ts +4 -0
  90. package/dist/images/documents/image.d.ts +4 -0
  91. package/dist/images/documents/index.d.ts +22 -0
  92. package/dist/images/documents/odf.d.ts +4 -0
  93. package/dist/images/documents/odg.d.ts +4 -0
  94. package/dist/images/documents/odp.d.ts +4 -0
  95. package/dist/images/documents/ods.d.ts +4 -0
  96. package/dist/images/documents/odt.d.ts +4 -0
  97. package/dist/images/documents/pdf.d.ts +4 -0
  98. package/dist/images/documents/ppt.d.ts +4 -0
  99. package/dist/images/documents/rtf.d.ts +4 -0
  100. package/dist/images/documents/text.d.ts +4 -0
  101. package/dist/images/documents/video.d.ts +4 -0
  102. package/dist/images/documents/word.d.ts +4 -0
  103. package/dist/images/documents/xml.d.ts +4 -0
  104. package/dist/images/documents/zip.d.ts +4 -0
  105. package/dist/images/icons/arrow_upward.d.ts +4 -0
  106. package/dist/images/icons/calendar_today.d.ts +4 -0
  107. package/dist/images/icons/cancel.d.ts +4 -0
  108. package/dist/images/icons/check_circle.d.ts +4 -0
  109. package/dist/images/icons/chevron_left.d.ts +4 -0
  110. package/dist/images/icons/chevron_right.d.ts +4 -0
  111. package/dist/images/icons/close.d.ts +4 -0
  112. package/dist/images/icons/description.d.ts +4 -0
  113. package/dist/images/icons/double_chevron_left.d.ts +4 -0
  114. package/dist/images/icons/double_chevron_right.d.ts +4 -0
  115. package/dist/images/icons/error.d.ts +4 -0
  116. package/dist/images/icons/expand_less.d.ts +4 -0
  117. package/dist/images/icons/expand_more.d.ts +4 -0
  118. package/dist/images/icons/index.d.ts +17 -0
  119. package/dist/images/icons/list.d.ts +4 -0
  120. package/dist/images/icons/menu.d.ts +4 -0
  121. package/dist/images/icons/priority_high.d.ts +4 -0
  122. package/dist/images/icons/search.d.ts +4 -0
  123. package/dist/tsconfig.tsbuildinfo +1 -1
  124. package/dist/utils/context.d.ts +4 -0
  125. package/package.json +6 -6
  126. package/src/components/Accordion/Accordion.Item.stories.tsx +10 -9
  127. package/src/components/Accordion/Accordion.stories.tsx +4 -4
  128. package/src/components/Accordion/Accordion.test.tsx +48 -14
  129. package/src/components/Accordion/Accordion.tsx +12 -1
  130. package/src/components/Breadcrumbs/Breadcrumbs.Item.stories.tsx +8 -1
  131. package/src/components/Button/Button.stories.tsx +1 -1
  132. package/src/components/ButtonGroup/ButtonGroup.stories.tsx +41 -0
  133. package/src/components/ButtonGroup/ButtonGroup.test.tsx +45 -0
  134. package/src/components/ButtonGroup/ButtonGroup.tsx +20 -0
  135. package/src/components/ContentsNav/ContentsNav.Item.stories.tsx +8 -0
  136. package/src/components/ErrorSummary/ErrorSummary.Item.stories.tsx +7 -0
  137. package/src/components/PageHeader/PageHeader.tsx +2 -1
  138. package/src/components/PageMetadata/PageMetadata.Item.stories.tsx +9 -0
  139. package/src/components/RadioButton/RadioGroup.tsx +2 -2
  140. package/src/components/SearchFacets/SearchFacets.Group.stories.tsx +56 -0
  141. package/src/components/SearchFacets/SearchFacets.Item.stories.tsx +53 -0
  142. package/src/components/SearchFacets/SearchFacets.stories.tsx +38 -0
  143. package/src/components/SearchFacets/SearchFacets.test.tsx +214 -0
  144. package/src/components/SearchFacets/SearchFacets.tsx +99 -0
  145. package/src/components/SearchFilters/SearchFilters.Panel.stories.tsx +201 -0
  146. package/src/components/SearchFilters/SearchFilters.stories.tsx +137 -0
  147. package/src/components/SearchFilters/SearchFilters.test.tsx +161 -0
  148. package/src/components/SearchFilters/SearchFilters.tsx +89 -0
  149. package/src/components/SearchResult/SearchResult.stories.tsx +111 -0
  150. package/src/components/SearchResult/SearchResult.test.tsx +215 -0
  151. package/src/components/SearchResult/SearchResult.tsx +137 -0
  152. package/src/components/SearchSort/SearchSort.stories.tsx +32 -0
  153. package/src/components/SearchSort/SearchSort.test.tsx +129 -0
  154. package/src/components/SearchSort/SearchSort.tsx +45 -0
  155. package/src/components/SequentialNavigation/SequentialNavigation.Next.stories.tsx +1 -1
  156. package/src/components/SequentialNavigation/SequentialNavigation.Previous.stories.tsx +1 -1
  157. package/src/components/SequentialNavigation/SequentialNavigation.tsx +0 -1
  158. package/src/components/SideNavigation/SideNavigation.Item.stories.tsx +9 -0
  159. package/src/components/SideNavigation/SideNavigation.List.stories.tsx +7 -0
  160. package/src/components/SideNavigation/SideNavigation.tsx +2 -1
  161. package/src/components/SiteFooter/SiteFooter.License.stories.tsx +7 -0
  162. package/src/components/SiteFooter/SiteFooter.Link.stories.tsx +9 -0
  163. package/src/components/SiteFooter/SiteFooter.Org.stories.tsx +7 -0
  164. package/src/components/SiteHeader/SiteHeader.tsx +0 -2
  165. package/src/components/SiteNavigation/SiteNavigation.Item.stories.tsx +10 -0
  166. package/src/components/SkipLinks/SkipLinks.Item.stories.tsx +11 -1
  167. package/src/components/SkipLinks/SkipLinks.tsx +10 -0
  168. package/src/components/SummaryCard/SummaryCard.Action.stories.tsx +7 -0
  169. package/src/components/SummaryCard/SummaryCard.stories.tsx +7 -0
  170. package/src/components/SummaryList/SummaryList.Item.stories.tsx +15 -0
  171. package/src/components/SummaryList/SummaryList.Value.stories.tsx +5 -2
  172. package/src/components/Tabs/Tabs.Item.stories.tsx +4 -1
  173. package/src/components/TaskList/TaskList.Group.stories.tsx +9 -0
  174. package/src/components/TaskList/TaskList.Item.stories.tsx +7 -0
  175. package/tsconfig.json +14 -14
@@ -6,9 +6,17 @@ import Accordion from './Accordion';
6
6
  const meta = {
7
7
  title: 'Components/Accordion/Accordion.Item',
8
8
  component: Accordion.Item,
9
+ decorators: [(Story) => <div className="ds_accordion"><Story /></div>],
9
10
  argTypes: {
11
+ heading: {
12
+ description: 'Heading of the accordion item',
13
+ type: {
14
+ name: 'string',
15
+ required: true
16
+ }
17
+ },
10
18
  headingLevel: argTypes.headingLevel({
11
- description: 'Heading level for the component\'s title. It is best to set this on the parent Accordion.'
19
+ description: 'Heading level for the component\'s heading. It is best to set this on the parent Accordion.'
12
20
  }),
13
21
  id: {
14
22
  description: 'ID to use for the accordion item if you want to override the automatically generated default',
@@ -18,19 +26,12 @@ const meta = {
18
26
  description: 'Makes the accordion item display in an open state on page load',
19
27
  control: 'boolean',
20
28
  },
21
- title: {
22
- description: 'Title of the accordion item',
23
- type: {
24
- name: 'string',
25
- required: true
26
- }
27
- },
28
29
  children: {
29
30
  control: false
30
31
  }
31
32
  },
32
33
  args: {
33
- title: 'Healthcare for veterans',
34
+ heading: 'Healthcare for veterans',
34
35
  children: <>
35
36
  <p>
36
37
  Veterans are entitled to the same healthcare as any citizen. And there are health care options and support available specifically for veterans.
@@ -8,7 +8,7 @@ const meta = {
8
8
  component: Accordion,
9
9
  argTypes: {
10
10
  headingLevel: argTypes.headingLevel({
11
- description: 'Heading level to use for the accordion items\' titles'
11
+ description: 'Heading level to use for the accordion items\' headings'
12
12
  }),
13
13
  hideOpenAll: {
14
14
  control: 'boolean',
@@ -21,7 +21,7 @@ const meta = {
21
21
  },
22
22
  args: {
23
23
  children: <>
24
- <Accordion.Item id='accordion-1' title='Healthcare for veterans'>
24
+ <Accordion.Item id='accordion-1' heading='Healthcare for veterans'>
25
25
  <p>
26
26
  Veterans are entitled to the same healthcare as any citizen. And there are health care options and support available specifically for veterans.
27
27
  </p>
@@ -29,12 +29,12 @@ const meta = {
29
29
  If you have a health condition that's related to your service, you're entitled to priority treatment based on clinical need.
30
30
  </p>
31
31
  </Accordion.Item>
32
- <Accordion.Item id='accordion-2' title='Employability for veterans'>
32
+ <Accordion.Item id='accordion-2' heading='Employability for veterans'>
33
33
  <p>
34
34
  If you're looking for a job, there are several organisations that can help you <a href="#accordion-link">find a job or develop new skills</a>.
35
35
  </p>
36
36
  </Accordion.Item>
37
- <Accordion.Item id='accordion-3' title='Housing for veterans'>
37
+ <Accordion.Item id='accordion-3' heading='Housing for veterans'>
38
38
  <p>
39
39
  If you need <a href="#accordion-link"> help finding a place to live</a> there's support specifically for veterans.
40
40
  </p>
@@ -1,4 +1,4 @@
1
- import { test, expect } from 'vitest';
1
+ import { test, expect, vi } from 'vitest';
2
2
  import { render, screen, within } from '@testing-library/react';
3
3
  import Accordion from './Accordion';
4
4
 
@@ -13,17 +13,17 @@ test('accordion renders correctly', () => {
13
13
 
14
14
  render(
15
15
  <Accordion id={ACCORDION_ID} data-testid={ACCORDION_ID}>
16
- <Accordion.Item id="accordion-1" title="Healthcare for veterans">
16
+ <Accordion.Item id="accordion-1" heading="Healthcare for veterans">
17
17
  <p>Veterans are entitled to the same healthcare as any citizen. And there
18
18
  are health care options and support available specifically for veterans.</p>
19
19
  <p>If you have a health condition that’s related to your service, you’re
20
20
  entitled to priority treatment based on clinical need.</p>
21
21
  </Accordion.Item>
22
- <Accordion.Item isOpen id="accordion-2" title="Employability for veterans">
22
+ <Accordion.Item isOpen id="accordion-2" heading="Employability for veterans">
23
23
  <p>If you&apos;re looking for a job, there are several organisations that can help
24
24
  you <a href="#accordion-link">find a job or develop new skills</a>.</p>
25
25
  </Accordion.Item>
26
- <Accordion.Item id="accordion-3" title="Housing for veterans">
26
+ <Accordion.Item id="accordion-3" heading="Housing for veterans">
27
27
  <p>If you need <a href="#accordion-link">help finding a place to live</a>{' '}
28
28
  there&apos;s support specifically for veterans.</p>
29
29
  </Accordion.Item>
@@ -48,17 +48,17 @@ test('accordion renders correctly', () => {
48
48
  test('accordion without open all', () => {
49
49
  render(
50
50
  <Accordion id={ACCORDION_ID} data-testid={ACCORDION_ID} hideOpenAll>
51
- <Accordion.Item id="accordion-1" title="Healthcare for veterans">
51
+ <Accordion.Item id="accordion-1" heading="Healthcare for veterans">
52
52
  <p>Veterans are entitled to the same healthcare as any citizen. And there
53
53
  are health care options and support available specifically for veterans.</p>
54
54
  <p>If you have a health condition that’s related to your service, you’re
55
55
  entitled to priority treatment based on clinical need.</p>
56
56
  </Accordion.Item>
57
- <Accordion.Item id="accordion-2" title="Employability for veterans">
57
+ <Accordion.Item id="accordion-2" heading="Employability for veterans">
58
58
  <p>If you&apos;re looking for a job, there are several organisations that can help
59
59
  you <a href="#accordion-link">find a job or develop new skills</a>.</p>
60
60
  </Accordion.Item>
61
- <Accordion.Item id="accordion-3" title="Housing for veterans">
61
+ <Accordion.Item id="accordion-3" heading="Housing for veterans">
62
62
  <p>If you need <a href="#accordion-link">help finding a place to live</a>{' '}
63
63
  there&apos;s support specifically for veterans.</p>
64
64
  </Accordion.Item>
@@ -86,7 +86,7 @@ test('accordion with custom heading level', () => {
86
86
 
87
87
  render(
88
88
  <Accordion id={ACCORDION_ID} data-testid={ACCORDION_ID} headingLevel={HEADING_LEVEL}>
89
- <Accordion.Item id="accordion-1" title="Healthcare for veterans">
89
+ <Accordion.Item id="accordion-1" heading="Healthcare for veterans">
90
90
  <p>Veterans are entitled to the same healthcare as any citizen. And there
91
91
  are health care options and support available specifically for veterans.</p>
92
92
  <p>If you have a health condition that’s related to your service, you’re
@@ -121,7 +121,7 @@ test('passing additional CSS classes', () => {
121
121
 
122
122
  test('accordion item renders correctly', () => {
123
123
  render(
124
- <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} title={TITLE_TEXT}>
124
+ <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} heading={TITLE_TEXT}>
125
125
  <p>{CONTENT_TEXT}</p>
126
126
  </Accordion.Item>
127
127
  );
@@ -159,13 +159,13 @@ test('accordion item renders correctly', () => {
159
159
  test('accordion items without ID are given unique IDs', () => {
160
160
  render(
161
161
  <Accordion id={ACCORDION_ID} data-testid={ACCORDION_ID} hideOpenAll>
162
- <Accordion.Item data-testid="item1" title="Healthcare for veterans">
162
+ <Accordion.Item data-testid="item1" heading="Healthcare for veterans">
163
163
  <p>Veterans are entitled to the same healthcare as any citizen. And there
164
164
  are health care options and support available specifically for veterans.</p>
165
165
  <p>If you have a health condition that’s related to your service, you’re
166
166
  entitled to priority treatment based on clinical need.</p>
167
167
  </Accordion.Item>
168
- <Accordion.Item data-testid="item2" title="Employability for veterans">
168
+ <Accordion.Item data-testid="item2" heading="Employability for veterans">
169
169
  <p>If you&apos;re looking for a job, there are several organisations that can help
170
170
  you <a href="#accordion-link">find a job or develop new skills</a>.</p>
171
171
  </Accordion.Item>
@@ -182,7 +182,7 @@ test('accordion items without ID are given unique IDs', () => {
182
182
 
183
183
  test('open accordion item', () => {
184
184
  render(
185
- <Accordion.Item isOpen id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} title={TITLE_TEXT}>
185
+ <Accordion.Item isOpen id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} heading={TITLE_TEXT}>
186
186
  <p>{CONTENT_TEXT}</p>
187
187
  </Accordion.Item>
188
188
  );
@@ -193,9 +193,43 @@ test('open accordion item', () => {
193
193
  expect(input).toHaveAttribute('checked');
194
194
  });
195
195
 
196
+ test('small accordion item', () => {
197
+ render(
198
+ <Accordion isSmall data-testid={ACCORDION_ID}>
199
+ <Accordion.Item id={ACCORDION_ITEM_ID} heading={TITLE_TEXT}>
200
+ <p>{CONTENT_TEXT}</p>
201
+ </Accordion.Item>
202
+ </Accordion>
203
+ );
204
+
205
+ const accordionItem = screen.getByTestId(ACCORDION_ID);
206
+
207
+ expect(accordionItem).toHaveClass('ds_accordion--small');
208
+ });
209
+
210
+ test('deprecated title prop still works with warning', () => {
211
+ const consoleWarnSpy = vi.spyOn(console, 'warn').mockImplementation(() => {});
212
+
213
+ render(
214
+ <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} title={TITLE_TEXT}>
215
+ <p>{CONTENT_TEXT}</p>
216
+ </Accordion.Item>
217
+ );
218
+
219
+ const header = document.querySelector('.ds_accordion-item__header');
220
+ const title = header?.querySelector('.ds_accordion-item__title');
221
+
222
+ expect(title?.textContent).toEqual(TITLE_TEXT);
223
+ expect(consoleWarnSpy).toHaveBeenCalledWith(
224
+ 'Warning: Using the `title` prop for heading text on an Accordion.Item is deprecated and will be removed in a future release. Please use the `heading` prop instead.'
225
+ );
226
+
227
+ consoleWarnSpy.mockRestore();
228
+ });
229
+
196
230
  test('passing additional props to accordion item', () => {
197
231
  render(
198
- <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} title="Healthcare for veterans" data-test="foo">
232
+ <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} heading="Healthcare for veterans" data-test="foo">
199
233
  <p>Veterans are entitled to the same healthcare as any citizen. And there
200
234
  are health care options and support available specifically for veterans.</p>
201
235
  <p>If you have a health condition that’s related to your service, you’re
@@ -209,7 +243,7 @@ test('passing additional props to accordion item', () => {
209
243
 
210
244
  test('passing additional CSS classes', () => {
211
245
  render(
212
- <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} title="Healthcare for veterans" className="foo">
246
+ <Accordion.Item id={ACCORDION_ITEM_ID} data-testid={ACCORDION_ITEM_ID} heading="Healthcare for veterans" className="foo">
213
247
  <p>Veterans are entitled to the same healthcare as any citizen. And there
214
248
  are health care options and support available specifically for veterans.</p>
215
249
  <p>If you have a health condition that’s related to your service, you’re
@@ -11,6 +11,7 @@ const AccordionItem = ({
11
11
  className,
12
12
  id: rawId,
13
13
  isOpen = false,
14
+ heading,
14
15
  title,
15
16
  ...props
16
17
  }: SGDS.Component.Accordion.Item) => {
@@ -19,6 +20,14 @@ const AccordionItem = ({
19
20
 
20
21
  let headingLevel = useContext(AccordionHeadingLevelContext);
21
22
 
23
+ if (title) {
24
+ console.warn(
25
+ 'Warning: Using the `title` prop for heading text on an Accordion.Item is deprecated and will be removed in a future release. Please use the `heading` prop instead.'
26
+ );
27
+
28
+ heading = heading || title;
29
+ }
30
+
22
31
  return (
23
32
  <div
24
33
  className={[
@@ -44,7 +53,7 @@ const AccordionItem = ({
44
53
  className="ds_accordion-item__title"
45
54
  tagName={headingLevel}
46
55
  >
47
- {title}
56
+ {heading}
48
57
  </WrapperTag>
49
58
  <span className="ds_accordion-item__indicator" />
50
59
  <label
@@ -66,6 +75,7 @@ const Accordion = ({
66
75
  className,
67
76
  headingLevel = 'h3',
68
77
  hideOpenAll,
78
+ isSmall,
69
79
  ...props
70
80
  }: SGDS.Component.Accordion) => {
71
81
  const ref = useRef(null);
@@ -84,6 +94,7 @@ const Accordion = ({
84
94
  <div
85
95
  className={[
86
96
  'ds_accordion',
97
+ isSmall ? 'ds_accordion--small' : '',
87
98
  className
88
99
  ].join(' ')}
89
100
  ref={ref}
@@ -6,8 +6,15 @@ import Breadcrumbs from './Breadcrumbs';
6
6
  const meta = {
7
7
  title: 'Components/Breadcrumbs/Breadcrumb.Item',
8
8
  component: Breadcrumbs.Item,
9
+ decorators: [
10
+ Story => (
11
+ <Breadcrumbs>
12
+ <Story />
13
+ </Breadcrumbs>
14
+ )
15
+ ],
9
16
  argTypes: {
10
- href: argTypes.href(),
17
+ href: argTypes.href({type: {name: 'string', required: true}}),
11
18
  isHidden: {
12
19
  description: 'Applies a visually-hidden CSS class',
13
20
  control: 'boolean'
@@ -2,7 +2,7 @@ import type { Meta, StoryObj } from '@storybook/react-vite';
2
2
  import Button from './Button';
3
3
 
4
4
  const meta = {
5
- title: 'Components/Button',
5
+ title: 'Components/Buttons/Button',
6
6
  component: Button,
7
7
  parameters: {
8
8
  controls: { sort: 'alpha' }
@@ -0,0 +1,41 @@
1
+ import type { Meta, StoryObj } from '@storybook/react-vite';
2
+ import ButtonGroup from './ButtonGroup';
3
+ import Button from '../Button/Button';
4
+
5
+ const meta = {
6
+ title: 'Components/Buttons/ButtonGroup',
7
+ component: ButtonGroup,
8
+ parameters: {
9
+ controls: { sort: 'alpha' }
10
+ },
11
+ argTypes: {
12
+ isInline: {
13
+ description: 'Force inline buttons on small screens',
14
+ control: 'boolean',
15
+ table: {
16
+ type: {
17
+ summary: 'boolean'
18
+ }
19
+ }
20
+ }
21
+ },
22
+ args: {
23
+ children: <>
24
+ <Button buttonStyle="secondary">Button one</Button>
25
+ <Button buttonStyle="secondary">Button two</Button>
26
+ <Button buttonStyle="secondary">Button three</Button>
27
+ </>
28
+ }
29
+ } satisfies Meta<typeof ButtonGroup>;
30
+
31
+ export default meta;
32
+ type Story = StoryObj<typeof meta>;
33
+
34
+ export const Default: Story = {
35
+ };
36
+
37
+ export const Inline: Story = {
38
+ args: {
39
+ isInline: true
40
+ }
41
+ };
@@ -0,0 +1,45 @@
1
+ import { test, expect } from 'vitest';
2
+ import { render, screen } from '@testing-library/react';
3
+ import ButtonGroup from './ButtonGroup';
4
+
5
+ test('renders correctly', () => {
6
+ render(
7
+ <ButtonGroup data-testid="button-group">
8
+ </ButtonGroup>
9
+ );
10
+
11
+ const buttonGroup = screen.getByTestId('button-group');
12
+ expect(buttonGroup).toBeInTheDocument();
13
+ expect(buttonGroup).toHaveClass('ds_button-group');
14
+ expect(buttonGroup.tagName).toEqual('DIV');
15
+ });
16
+
17
+ test('inline button group', () => {
18
+ render(
19
+ <ButtonGroup isInline data-testid="button-group">
20
+
21
+ </ButtonGroup>
22
+ );
23
+ const buttonGroup = screen.getByTestId('button-group');
24
+ expect(buttonGroup).toHaveClass('ds_button-group--inline');
25
+ });
26
+
27
+ test('passing additional props', () => {
28
+ render(
29
+ <ButtonGroup data-test="foo" data-testid="button-group">
30
+ </ButtonGroup>
31
+ );
32
+
33
+ const buttonGroup = screen.getByTestId('button-group');
34
+ expect(buttonGroup.dataset.test).toEqual('foo');
35
+ });
36
+
37
+ test('passing additional CSS classes', () => {
38
+ render(
39
+ <ButtonGroup className="foo" data-testid="button-group">
40
+ </ButtonGroup>
41
+ );
42
+
43
+ const buttonGroup = screen.getByTestId('button-group');
44
+ expect(buttonGroup).toHaveClass('foo', 'ds_button-group');
45
+ });
@@ -0,0 +1,20 @@
1
+ const ButtonGroup = ({
2
+ children,
3
+ className,
4
+ isInline,
5
+ ...props
6
+ }: SGDS.Component.ButtonGroup) => {
7
+ return (
8
+ <div className={[
9
+ "ds_button-group",
10
+ isInline ? "ds_button-group--inline" : undefined,
11
+ className
12
+ ].join(' ')} { ...props } >
13
+ {children}
14
+ </div>
15
+ );
16
+ };
17
+
18
+ ButtonGroup.displayName = 'ButtonGroup';
19
+
20
+ export default ButtonGroup;
@@ -6,7 +6,15 @@ import ContentsNav from './ContentsNav';
6
6
  const meta = {
7
7
  title: 'Components/ContentsNav/ContentsNav.Item',
8
8
  component: ContentsNav.Item,
9
+ decorators: [
10
+ Story => (
11
+ <ul className="ds_contents-nav__list">
12
+ <Story />
13
+ </ul>
14
+ )
15
+ ],
9
16
  argTypes: {
17
+ href: argTypes.href({type: {name: 'string', required: true}}),
10
18
  isCurrent: argTypes.isCurrent(),
11
19
  linkComponent: argTypes.linkComponent(),
12
20
  children: argTypes.children()
@@ -6,6 +6,13 @@ import ErrorSummary from './ErrorSummary';
6
6
  const meta = {
7
7
  title: 'Components/ErrorSummary/ErrorSummary.Item',
8
8
  component: ErrorSummary.Item,
9
+ decorators: [
10
+ Story => (
11
+ <ul className="ds_error-summary__list">
12
+ <Story />
13
+ </ul>
14
+ )
15
+ ],
9
16
  argTypes: {
10
17
  fragmentId: {
11
18
  description: 'ID of the question or field to link to',
@@ -3,6 +3,7 @@ const PageHeader = ({
3
3
  className,
4
4
  label,
5
5
  title,
6
+ titleId,
6
7
  ...props
7
8
  }: SGDS.Component.PageHeader) => {
8
9
  return (
@@ -14,7 +15,7 @@ const PageHeader = ({
14
15
  {...props}
15
16
  >
16
17
  {label && <span className="ds_page-header__label ds_content-label">{label}</span>}
17
- <h1 className="ds_page-header__title">{title}</h1>
18
+ <h1 id={titleId} className="ds_page-header__title">{title}</h1>
18
19
 
19
20
  {children}
20
21
  </header>
@@ -6,6 +6,15 @@ import Metadata from './PageMetadata';
6
6
  const meta = {
7
7
  title: 'Components/PageMetadata/PageMetadata.Item',
8
8
  component: Metadata.Item,
9
+ decorators: [
10
+ Story => (
11
+ <Metadata>
12
+ <dl className="ds_page-metadata__list">
13
+ <Story />
14
+ </dl>
15
+ </Metadata>
16
+ )
17
+ ],
9
18
  argTypes: {
10
19
  children: argTypes.children(),
11
20
  name: {
@@ -6,7 +6,7 @@ const RadioGroup = ({
6
6
  className,
7
7
  isInline,
8
8
  isSmall,
9
- name,
9
+ name = '',
10
10
  ...props
11
11
  }: SGDS.Component.RadioButton.Group) => {
12
12
  return (
@@ -19,7 +19,7 @@ const RadioGroup = ({
19
19
  ].join(' ')}
20
20
  {...props}
21
21
  >
22
- <CheckboxRadioContext value={{ isSmall: !!isSmall, name }}>
22
+ <CheckboxRadioContext value={{ isSmall: !!isSmall, name}}>
23
23
  {children}
24
24
  </CheckboxRadioContext>
25
25
  </div>
@@ -0,0 +1,56 @@
1
+ import type { Meta, StoryObj } from '@storybook/react-vite';
2
+ import argTypes from '../../../.storybook/sgdsArgTypes';
3
+
4
+ import Facets from './SearchFacets';
5
+ import { join } from 'path';
6
+
7
+ const meta = {
8
+ title: 'Components/Search results/Facets/Group',
9
+ component: Facets.Group,
10
+ decorators: [
11
+ (Story) => (
12
+ <div className="ds_facets">
13
+ <Story />
14
+ </div>
15
+ )
16
+ ],
17
+ argTypes: {
18
+ children: argTypes.children(),
19
+ joinContent: {
20
+ description: 'Content to display between the facet items when there are multiple items in the group',
21
+ type: 'string'
22
+ },
23
+ title: {
24
+ description: 'Title of the facet group',
25
+ type: {
26
+ name: 'string',
27
+ required: true
28
+ }
29
+ }
30
+ },
31
+ args: {
32
+ title: 'Content type'
33
+ }
34
+ } satisfies Meta<typeof Facets.Group>;
35
+
36
+ export default meta;
37
+ type Story = StoryObj<typeof meta>;
38
+
39
+ export const Default: Story = {
40
+ render: (args: any) => (
41
+ <Facets.Group {...args}>
42
+ <Facets.Item title="Advice and guidance" />
43
+ <Facets.Item title="Factsheet"/>
44
+ <Facets.Item title="Statistics" />
45
+ </Facets.Group>
46
+ )
47
+ };
48
+
49
+ export const CustomJoinContent: Story = {
50
+ render: (args: any) => (
51
+ <Facets.Group joinContent="and" title="Updated between">
52
+ <Facets.Item accessibleName="Updated after 01/10/2025" title="01/10/2025" />
53
+ <Facets.Item accessibleName="Updated before 31/10/2025" title="31/10/2025"/>
54
+ </Facets.Group>
55
+ )
56
+ };
@@ -0,0 +1,53 @@
1
+ import type { Meta, StoryObj } from '@storybook/react-vite';
2
+
3
+ import Facets from './SearchFacets';
4
+
5
+ const meta = {
6
+ title: 'Components/Search results/Facets/Item',
7
+ component: Facets.Item,
8
+ decorators: [
9
+ (Story) => (
10
+ <div className="ds_facets">
11
+ <Story />
12
+ </div>
13
+ )
14
+ ],
15
+ argTypes: {
16
+ accessibleName: {
17
+ description: 'Accessible name for the facet button. If not provided, the title will be used. This content becomes part of the facet button\'s aria-label attribute.',
18
+ type: 'string'
19
+ },
20
+ joinContent: {
21
+ description: 'Content to display before the facet button when there are multiple facets in a group. This should be provided to the parent Group instead.',
22
+ type: 'string'
23
+ },
24
+ onClick: {
25
+ description: 'Callback for when the facet button is clicked',
26
+ control: false
27
+ },
28
+ title: {
29
+ description: 'Text content of the facet button.',
30
+ type: {
31
+ name: 'string',
32
+ required: true
33
+ }
34
+ },
35
+ },
36
+ args: {
37
+ title: 'Advice and guidance'
38
+ }
39
+ } satisfies Meta<typeof Facets.Item>;
40
+
41
+ export default meta;
42
+ type Story = StoryObj<typeof meta>;
43
+
44
+ export const Default: Story = {
45
+
46
+ };
47
+
48
+ export const CustomAccessibleText: Story = {
49
+ args: {
50
+ accessibleName: 'Updated before 31st October 2025',
51
+ title: '31/10/2025'
52
+ }
53
+ }
@@ -0,0 +1,38 @@
1
+ import type { Meta, StoryObj } from '@storybook/react-vite';
2
+ import argTypes from '../../../.storybook/sgdsArgTypes';
3
+
4
+ import Facets from './SearchFacets';
5
+
6
+ const meta = {
7
+ title: 'Components/Search results/Facets',
8
+ component: Facets,
9
+ argTypes: {
10
+ children: argTypes.children()
11
+ },
12
+ args: {
13
+ title: 'Application incomplete'
14
+ }
15
+ } satisfies Meta<typeof Facets>;
16
+
17
+ export default meta;
18
+ type Story = StoryObj<typeof meta>;
19
+
20
+ export const Default: Story = {
21
+ render: (args: any) => (
22
+ <Facets {...args}>
23
+ <Facets.Group title="Content type">
24
+ <Facets.Item title="Advice and guidance" />
25
+ <Facets.Item title="Factsheet"/>
26
+ <Facets.Item title="Statistics" />
27
+ </Facets.Group>
28
+ <Facets.Group title="Topic">
29
+ <Facets.Item title="Children and families"/>
30
+ <Facets.Item title="Education"/>
31
+ </Facets.Group>
32
+ <Facets.Group title="Updated between" joinContent="and">
33
+ <Facets.Item accessibleName="Updated after 20/11/2023" title="20/11/2023"/>
34
+ <Facets.Item accessibleName="Updated before 02/04/2024" title="02/04/2024"/>
35
+ </Facets.Group>
36
+ </Facets>
37
+ )
38
+ };