@geotab/zenith 3.1.1-beta.6 → 3.2.0-beta.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 (430) hide show
  1. package/README.md +20 -0
  2. package/dist/advancedGroupsFilter/advancedGroupsFilter.js +136 -30
  3. package/dist/advancedGroupsFilter/advancedGroupsFilterForm.js +139 -34
  4. package/dist/advancedGroupsFilter/advancedGroupsFilterFormSection.js +352 -87
  5. package/dist/advancedGroupsFilter/advancedGroupsFilterSectionTooltip.d.ts +0 -1
  6. package/dist/advancedGroupsFilter/advancedGroupsFilterSectionTooltip.js +83 -9
  7. package/dist/alertRaw/alertRaw.js +175 -54
  8. package/dist/banner/bannerMultipLine.js +131 -23
  9. package/dist/banner/bannerSingleLine.js +110 -16
  10. package/dist/betaPill/betaPill.js +111 -20
  11. package/dist/bookmark/bookmark.js +95 -28
  12. package/dist/bulkEditControl/bulkEditControl.js +167 -34
  13. package/dist/calendar/calendar.js +943 -273
  14. package/dist/calendar/calendarUtils.js +157 -85
  15. package/dist/card/card.js +268 -123
  16. package/dist/chart/accessibleChart/accessibleChartNarrative.js +648 -555
  17. package/dist/chart/accessibleChart/accessibleChartTable.js +245 -86
  18. package/dist/chart/chart.js +36 -21
  19. package/dist/chart/chartAxis/chartAxis.js +85 -7
  20. package/dist/checkboxListWithAction/checkboxListWithAction.js +224 -69
  21. package/dist/chip/chip.js +195 -91
  22. package/dist/columnsSelector/columnsSelector.js +97 -12
  23. package/dist/columnsSelector/columnsTab/columnsTab.js +59 -15
  24. package/dist/columnsSelector/columnsTabGroup/columnsTabGroup.js +81 -34
  25. package/dist/comboboxSelected/comboboxSelected.js +1 -3
  26. package/dist/dataFeed/feedExpandControl/feedExpandControl.js +25 -10
  27. package/dist/dataGrid/columns/checkboxColumn/checkboxHeaderCell.js +92 -11
  28. package/dist/dataGrid/dataGrid.js +227 -117
  29. package/dist/dataGrid/emptySearchList/emptySearchList.js +56 -9
  30. package/dist/dataGrid/entitiesListActions/actions/columnsListButton.js +51 -7
  31. package/dist/dataGrid/entitiesListActions/actions/fullscreenButton.js +64 -18
  32. package/dist/dataGrid/withFlexibleColumns/components/columnSettings.js +84 -10
  33. package/dist/dataGrid/withFlexibleColumns/components/columnSettingsSidePanel.js +48 -16
  34. package/dist/dataGrid/withSelectableRows/components/bulkActions/bulkActions.js +223 -32
  35. package/dist/dataGrid/withSelectableRows/withSelectableRows.js +286 -213
  36. package/dist/dataGrid/withSortableColumns/columns/sortableColumnWrapper.js +178 -95
  37. package/dist/dateInputInner/dateInputInner.js +791 -476
  38. package/dist/dateInputInner/dateInputInnerControlBlock.js +125 -22
  39. package/dist/dateInputRaw/dateInputRaw.js +315 -104
  40. package/dist/dateInputRaw/utils/getLabel.js +38 -7
  41. package/dist/dateRangeInner/dateRangeInner.js +172 -58
  42. package/dist/dateRangeRaw/dateRangeRaw.js +601 -239
  43. package/dist/dateRangeRaw/utils/dateRangeUtils.js +629 -241
  44. package/dist/dateSelectionWrapper/dateSelectionWrapper.js +152 -14
  45. package/dist/dialog/dialogContent.js +123 -40
  46. package/dist/dropdownRaw/dropdownHelper.d.ts +2 -2
  47. package/dist/dropdownRaw/dropdownHelper.js +9 -9
  48. package/dist/dropdownRaw/dropdownList.js +447 -78
  49. package/dist/dropdownRaw/dropdownPopup.js +218 -20
  50. package/dist/dropdownRaw/dropdownRaw.js +866 -506
  51. package/dist/dropdownRaw/dropdownSearchableTrigger.js +223 -46
  52. package/dist/dropdownRaw/stateReducer/stateAction.d.ts +5 -1
  53. package/dist/dropdownRaw/stateReducer/stateActionType.d.ts +2 -1
  54. package/dist/dropdownRaw/stateReducer/stateActionType.js +1 -0
  55. package/dist/dropdownRaw/stateReducer/stateReducer.d.ts +6 -1
  56. package/dist/dropdownRaw/stateReducer/stateReducer.js +24 -12
  57. package/dist/dropdownRaw/stateReducer/stateReducerHelper.d.ts +2 -0
  58. package/dist/dropdownRaw/stateReducer/stateReducerHelper.js +20 -1
  59. package/dist/dropdownRaw/stateReducer/stateReducerTestData.d.ts +39 -0
  60. package/dist/dropdownRaw/stateReducer/stateReducerTestData.js +74 -0
  61. package/dist/dropdownRaw/types.d.ts +1 -0
  62. package/dist/favoriteButton/favoriteButton.js +59 -10
  63. package/dist/filters/components/filtersContainer.js +151 -64
  64. package/dist/filters/components/filtersEmptySelectedList.js +30 -4
  65. package/dist/filters/components/filtersSaveModal.js +140 -42
  66. package/dist/filters/components/filtersSavedChipComponent.js +318 -108
  67. package/dist/filters/components/filtersSearchItemData.js +127 -47
  68. package/dist/filters/components/filtersSearchList.js +381 -179
  69. package/dist/filters/components/filtersSelect.js +128 -61
  70. package/dist/filters/components/filtersSelectListItem.js +125 -13
  71. package/dist/filters/components/filtersSidePanel.js +510 -178
  72. package/dist/filters/filters.js +445 -268
  73. package/dist/filtersBar/components/filtersBarPeriodPicker/getRangeOption.js +729 -272
  74. package/dist/filtersBar/components/resetComponentButton.js +45 -5
  75. package/dist/filtersBar/filtersBarActions/filtersBarActions.js +126 -15
  76. package/dist/filtersBar/filtersBarSidePanel/components/filtersBarSidePanelRange/filtersBarSidePanelRange.js +155 -49
  77. package/dist/filtersBar/filtersBarSidePanel/filtersBarSidePanel.js +360 -104
  78. package/dist/filtersBar/filtersContainer/filtersContainer.js +204 -134
  79. package/dist/formField/components/formFieldWithLabel.d.ts +2 -1
  80. package/dist/formField/components/formFieldWithLabel.js +3 -2
  81. package/dist/formField/components/formFieldWithoutLabel.d.ts +2 -1
  82. package/dist/formField/components/formFieldWithoutLabel.js +3 -3
  83. package/dist/formField/components/trailingComponent.d.ts +8 -0
  84. package/dist/formField/components/trailingComponent.js +11 -0
  85. package/dist/formField/formField.js +12 -11
  86. package/dist/formField/hooks/useError.js +100 -36
  87. package/dist/formGroup/components/reviewListToggle/reviewListToggle.js +72 -7
  88. package/dist/formGroup/hooks/useToggle.js +37 -11
  89. package/dist/formGroup/utils/getControls.js +8 -7
  90. package/dist/formLayout/hooks/useError.js +55 -15
  91. package/dist/formLayout/hooks/useFormButtons.js +128 -27
  92. package/dist/formSection/components/formSectionModal.js +1 -1
  93. package/dist/formSection/formSection.js +1 -1
  94. package/dist/formSection/hooks/useError.js +70 -22
  95. package/dist/formStepper/components/formStep.js +65 -10
  96. package/dist/formStepper/formStepper.js +129 -33
  97. package/dist/formStepperButtons/formStepperButtons.js +184 -38
  98. package/dist/groupsFilter/groupsHelper.d.ts +1 -1
  99. package/dist/groupsFilterRaw/groupsFilterAdjustmentState.js +162 -17
  100. package/dist/groupsFilterRaw/groupsFilterBox.js +137 -32
  101. package/dist/groupsFilterRaw/groupsFilterCommon.js +75 -8
  102. package/dist/groupsFilterRaw/groupsFilterCurrentlySelectedState.js +184 -25
  103. package/dist/groupsFilterRaw/groupsFilterHelper.d.ts +2 -1
  104. package/dist/groupsFilterRaw/groupsFilterHelper.js +284 -168
  105. package/dist/groupsFilterRaw/groupsFilterInitialState.js +266 -18
  106. package/dist/groupsFilterRaw/groupsFilterMenu.js +124 -9
  107. package/dist/groupsFilterRaw/groupsFilterRaw.d.ts +1 -0
  108. package/dist/groupsFilterRaw/groupsFilterRaw.js +816 -308
  109. package/dist/groupsFilterRaw/groupsFilterTestData.d.ts +155 -2
  110. package/dist/groupsFilterRaw/groupsFilterTestData.js +153 -58
  111. package/dist/groupsFilterRaw/groupsFilterTrigger.js +139 -35
  112. package/dist/groupsFilterRaw/groupsHelper.js +739 -208
  113. package/dist/groupsFilterRaw/stateReducer/stateReducerHelper.js +3 -1
  114. package/dist/groupsFilterRaw/types.d.ts +1 -0
  115. package/dist/header/components/collapsedItemsControl/collapsedItemsControl.js +107 -52
  116. package/dist/header/components/mobileFilterControl/mobileFilterControl.js +62 -9
  117. package/dist/header/components/mobileSearchControl/mobileSearchControl.js +119 -14
  118. package/dist/header/headerBack.js +64 -20
  119. package/dist/index.css +110 -71
  120. package/dist/index.d.ts +1 -0
  121. package/dist/index.js +4 -1
  122. package/dist/list/itemData/itemDataInternal.js +216 -51
  123. package/dist/list/listItem/listItem.js +168 -55
  124. package/dist/menu/components/menuErrorItem.js +33 -5
  125. package/dist/mobileSheet/mobileSheet.js +195 -69
  126. package/dist/modal/modal.js +300 -142
  127. package/dist/nav/nav.js +1 -1
  128. package/dist/nav/navFooter/navFooter.js +82 -39
  129. package/dist/nav/navFooter/navFooterAction/navFooterAction.js +52 -13
  130. package/dist/nav/navHeader/navHeader.js +86 -36
  131. package/dist/nav/navHeader/navHeaderSearch/navHeaderSearch.js +88 -29
  132. package/dist/nav/navItem/navItem.d.ts +3 -3
  133. package/dist/nav/navItem/navItem.js +35 -33
  134. package/dist/nav/navMobileBar/navMobileBar.js +67 -21
  135. package/dist/notification/notification.js +124 -21
  136. package/dist/pagination/paginationArrow.js +81 -11
  137. package/dist/pagination/paginationText/paginationText.js +45 -11
  138. package/dist/pill/components/pillNonActionable/pillNonActionable.js +93 -24
  139. package/dist/pillBox/components/pillBoxItem.js +52 -9
  140. package/dist/pillBox/pillBox.js +121 -20
  141. package/dist/pillExpandable/pillExpandable.js +333 -139
  142. package/dist/rangeRaw/rangeRaw.js +486 -141
  143. package/dist/rangeRaw/utils/rangeHelper.js +209 -39
  144. package/dist/searchInputRaw/searchInputRaw.js +180 -65
  145. package/dist/skeleton/skeleton.js +51 -6
  146. package/dist/sortControl/sortControl.js +152 -42
  147. package/dist/stepperRaw/stepperRaw.js +116 -42
  148. package/dist/summary/summary.js +94 -8
  149. package/dist/table/actions/actionsMenu.js +171 -78
  150. package/dist/table/flexible/columnSettings.js +80 -10
  151. package/dist/table/flexible/columnsList.js +110 -43
  152. package/dist/table/flexible/columnsPopup.js +77 -20
  153. package/dist/table/nested/useNestedRows.js +167 -77
  154. package/dist/table/selectable/selectableHeader.js +180 -41
  155. package/dist/table/selectable/useSelectableRows.js +270 -191
  156. package/dist/table/sortable/sortableHeader.js +153 -75
  157. package/dist/tabs/tabs.js +227 -118
  158. package/dist/timePickerRaw/timePickerRaw.js +278 -58
  159. package/dist/toastRaw/toastRaw.js +138 -32
  160. package/dist/toggleButton/toggleButton.d.ts +0 -1
  161. package/dist/toggleButtonRaw/toggleButtonRaw.d.ts +1 -0
  162. package/dist/toggleButtonRaw/toggleButtonRaw.js +146 -40
  163. package/dist/utils/formatDate.js +1001 -117
  164. package/{esm/utils/localization/translations/cs-json.js → dist/utils/localization/translations/cs.json} +11 -12
  165. package/{esm/utils/localization/translations/da-DK-json.js → dist/utils/localization/translations/da-DK.json} +31 -23
  166. package/{esm/utils/localization/translations/de-json.js → dist/utils/localization/translations/de.json} +12 -13
  167. package/dist/utils/localization/translations/en.json +308 -0
  168. package/{esm/utils/localization/translations/es-json.js → dist/utils/localization/translations/es.json} +11 -12
  169. package/{esm/utils/localization/translations/fi-FI-json.js → dist/utils/localization/translations/fi-FI.json} +31 -23
  170. package/{esm/utils/localization/translations/fr-FR-json.js → dist/utils/localization/translations/fr-FR.json} +12 -12
  171. package/{esm/utils/localization/translations/fr-json.js → dist/utils/localization/translations/fr.json} +11 -12
  172. package/{esm/utils/localization/translations/hu-HU-json.js → dist/utils/localization/translations/hu-HU.json} +31 -23
  173. package/{esm/utils/localization/translations/id-json.js → dist/utils/localization/translations/id.json} +11 -13
  174. package/{esm/utils/localization/translations/it-json.js → dist/utils/localization/translations/it.json} +11 -12
  175. package/{esm/utils/localization/translations/ja-json.js → dist/utils/localization/translations/ja.json} +11 -12
  176. package/{esm/utils/localization/translations/ko-KR-json.js → dist/utils/localization/translations/ko-KR.json} +24 -23
  177. package/{esm/utils/localization/translations/ms-json.js → dist/utils/localization/translations/ms.json} +11 -12
  178. package/{esm/utils/localization/translations/nb-NO-json.js → dist/utils/localization/translations/nb-NO.json} +31 -23
  179. package/{esm/utils/localization/translations/nl-json.js → dist/utils/localization/translations/nl.json} +11 -12
  180. package/{esm/utils/localization/translations/pl-json.js → dist/utils/localization/translations/pl.json} +11 -12
  181. package/{esm/utils/localization/translations/pt-BR-json.js → dist/utils/localization/translations/pt-BR.json} +11 -12
  182. package/{esm/utils/localization/translations/sk-SK-json.js → dist/utils/localization/translations/sk-SK.json} +31 -23
  183. package/{esm/utils/localization/translations/sv-json.js → dist/utils/localization/translations/sv.json} +11 -12
  184. package/{esm/utils/localization/translations/th-json.js → dist/utils/localization/translations/th.json} +11 -12
  185. package/{esm/utils/localization/translations/tr-json.js → dist/utils/localization/translations/tr.json} +11 -12
  186. package/{esm/utils/localization/translations/zh-Hans-json.js → dist/utils/localization/translations/zh-Hans.json} +11 -12
  187. package/{esm/utils/localization/translations/zh-TW-json.js → dist/utils/localization/translations/zh-TW.json} +11 -23
  188. package/dist/utils/localization/translationsDictionary.d.ts +2 -0
  189. package/dist/utils/localization/translationsDictionary.js +63 -0
  190. package/dist/utils/localization/useLanguage.js +2 -74
  191. package/esm/advancedGroupsFilter/advancedGroupsFilter.js +130 -29
  192. package/esm/advancedGroupsFilter/advancedGroupsFilterForm.js +133 -33
  193. package/esm/advancedGroupsFilter/advancedGroupsFilterFormSection.js +317 -65
  194. package/esm/advancedGroupsFilter/advancedGroupsFilterSectionTooltip.d.ts +0 -1
  195. package/esm/advancedGroupsFilter/advancedGroupsFilterSectionTooltip.js +77 -8
  196. package/esm/alertRaw/alertRaw.js +165 -51
  197. package/esm/banner/bannerMultipLine.js +121 -20
  198. package/esm/banner/bannerSingleLine.js +100 -13
  199. package/esm/betaPill/betaPill.js +105 -19
  200. package/esm/bookmark/bookmark.js +89 -27
  201. package/esm/bulkEditControl/bulkEditControl.js +161 -33
  202. package/esm/calendar/calendar.js +937 -272
  203. package/esm/calendar/calendarUtils.js +151 -84
  204. package/esm/card/card.js +233 -101
  205. package/esm/chart/accessibleChart/accessibleChartNarrative.js +642 -554
  206. package/esm/chart/accessibleChart/accessibleChartTable.js +239 -85
  207. package/esm/chart/chart.js +30 -20
  208. package/esm/chart/chartAxis/chartAxis.js +79 -6
  209. package/esm/checkboxListWithAction/checkboxListWithAction.js +218 -68
  210. package/esm/chip/chip.js +189 -90
  211. package/esm/columnsSelector/columnsSelector.js +91 -11
  212. package/esm/columnsSelector/columnsTab/columnsTab.js +53 -14
  213. package/esm/columnsSelector/columnsTabGroup/columnsTabGroup.js +75 -33
  214. package/esm/comboboxSelected/comboboxSelected.js +1 -3
  215. package/esm/dataFeed/feedExpandControl/feedExpandControl.js +21 -9
  216. package/esm/dataGrid/columns/checkboxColumn/checkboxHeaderCell.js +86 -10
  217. package/esm/dataGrid/dataGrid.js +221 -116
  218. package/esm/dataGrid/emptySearchList/emptySearchList.js +50 -8
  219. package/esm/dataGrid/entitiesListActions/actions/columnsListButton.js +45 -6
  220. package/esm/dataGrid/entitiesListActions/actions/fullscreenButton.js +58 -17
  221. package/esm/dataGrid/withFlexibleColumns/components/columnSettings.js +78 -9
  222. package/esm/dataGrid/withFlexibleColumns/components/columnSettingsSidePanel.js +44 -15
  223. package/esm/dataGrid/withSelectableRows/components/bulkActions/bulkActions.js +217 -31
  224. package/esm/dataGrid/withSelectableRows/withSelectableRows.js +280 -212
  225. package/esm/dataGrid/withSortableColumns/columns/sortableColumnWrapper.js +172 -94
  226. package/esm/dateInputInner/dateInputInner.js +785 -475
  227. package/esm/dateInputInner/dateInputInnerControlBlock.js +119 -21
  228. package/esm/dateInputRaw/dateInputRaw.js +309 -103
  229. package/esm/dateInputRaw/utils/getLabel.js +32 -6
  230. package/esm/dateRangeInner/dateRangeInner.js +166 -57
  231. package/esm/dateRangeRaw/dateRangeRaw.js +595 -238
  232. package/esm/dateRangeRaw/utils/dateRangeUtils.js +622 -239
  233. package/esm/dateSelectionWrapper/dateSelectionWrapper.js +146 -13
  234. package/esm/dialog/dialogContent.js +117 -39
  235. package/esm/dropdownRaw/dropdownHelper.d.ts +2 -2
  236. package/esm/dropdownRaw/dropdownHelper.js +10 -10
  237. package/esm/dropdownRaw/dropdownList.js +412 -56
  238. package/esm/dropdownRaw/dropdownPopup.js +212 -19
  239. package/esm/dropdownRaw/dropdownRaw.js +862 -507
  240. package/esm/dropdownRaw/dropdownSearchableTrigger.js +217 -45
  241. package/esm/dropdownRaw/stateReducer/stateAction.d.ts +5 -1
  242. package/esm/dropdownRaw/stateReducer/stateActionType.d.ts +2 -1
  243. package/esm/dropdownRaw/stateReducer/stateActionType.js +1 -0
  244. package/esm/dropdownRaw/stateReducer/stateReducer.d.ts +6 -1
  245. package/esm/dropdownRaw/stateReducer/stateReducer.js +24 -12
  246. package/esm/dropdownRaw/stateReducer/stateReducerHelper.d.ts +2 -0
  247. package/esm/dropdownRaw/stateReducer/stateReducerHelper.js +18 -0
  248. package/esm/dropdownRaw/stateReducer/stateReducerTestData.d.ts +39 -0
  249. package/esm/dropdownRaw/stateReducer/stateReducerTestData.js +71 -0
  250. package/esm/dropdownRaw/types.d.ts +1 -0
  251. package/esm/favoriteButton/favoriteButton.js +53 -9
  252. package/esm/filters/components/filtersContainer.js +141 -61
  253. package/esm/filters/components/filtersEmptySelectedList.js +24 -3
  254. package/esm/filters/components/filtersSaveModal.js +134 -41
  255. package/esm/filters/components/filtersSavedChipComponent.js +312 -107
  256. package/esm/filters/components/filtersSearchItemData.js +121 -46
  257. package/esm/filters/components/filtersSearchList.js +375 -178
  258. package/esm/filters/components/filtersSelect.js +122 -60
  259. package/esm/filters/components/filtersSelectListItem.js +119 -12
  260. package/esm/filters/components/filtersSidePanel.js +504 -177
  261. package/esm/filters/filters.js +435 -265
  262. package/esm/filtersBar/components/filtersBarPeriodPicker/getRangeOption.js +722 -270
  263. package/esm/filtersBar/components/resetComponentButton.js +39 -4
  264. package/esm/filtersBar/filtersBarActions/filtersBarActions.js +120 -14
  265. package/esm/filtersBar/filtersBarSidePanel/components/filtersBarSidePanelRange/filtersBarSidePanelRange.js +149 -48
  266. package/esm/filtersBar/filtersBarSidePanel/filtersBarSidePanel.js +354 -103
  267. package/esm/filtersBar/filtersContainer/filtersContainer.js +198 -133
  268. package/esm/formField/components/formFieldWithLabel.d.ts +2 -1
  269. package/esm/formField/components/formFieldWithLabel.js +3 -2
  270. package/esm/formField/components/formFieldWithoutLabel.d.ts +2 -1
  271. package/esm/formField/components/formFieldWithoutLabel.js +3 -3
  272. package/esm/formField/components/trailingComponent.d.ts +8 -0
  273. package/esm/formField/components/trailingComponent.js +7 -0
  274. package/esm/formField/formField.js +12 -11
  275. package/esm/formField/hooks/useError.js +94 -35
  276. package/esm/formGroup/components/reviewListToggle/reviewListToggle.js +66 -6
  277. package/esm/formGroup/hooks/useToggle.js +31 -10
  278. package/esm/formGroup/utils/getControls.js +8 -7
  279. package/esm/formLayout/hooks/useError.js +49 -14
  280. package/esm/formLayout/hooks/useFormButtons.js +122 -26
  281. package/esm/formSection/components/formSectionModal.js +1 -1
  282. package/esm/formSection/formSection.js +1 -1
  283. package/esm/formSection/hooks/useError.js +64 -21
  284. package/esm/formStepper/components/formStep.js +59 -9
  285. package/esm/formStepper/formStepper.js +123 -32
  286. package/esm/formStepperButtons/formStepperButtons.js +178 -37
  287. package/esm/groupsFilter/groupsHelper.d.ts +1 -1
  288. package/esm/groupsFilterRaw/groupsFilterAdjustmentState.js +152 -14
  289. package/esm/groupsFilterRaw/groupsFilterBox.js +131 -31
  290. package/esm/groupsFilterRaw/groupsFilterCommon.js +69 -7
  291. package/esm/groupsFilterRaw/groupsFilterCurrentlySelectedState.js +178 -24
  292. package/esm/groupsFilterRaw/groupsFilterHelper.d.ts +2 -1
  293. package/esm/groupsFilterRaw/groupsFilterHelper.js +279 -168
  294. package/esm/groupsFilterRaw/groupsFilterInitialState.js +260 -17
  295. package/esm/groupsFilterRaw/groupsFilterMenu.js +118 -8
  296. package/esm/groupsFilterRaw/groupsFilterRaw.d.ts +1 -0
  297. package/esm/groupsFilterRaw/groupsFilterRaw.js +811 -308
  298. package/esm/groupsFilterRaw/groupsFilterTestData.d.ts +155 -2
  299. package/esm/groupsFilterRaw/groupsFilterTestData.js +152 -57
  300. package/esm/groupsFilterRaw/groupsFilterTrigger.js +133 -34
  301. package/esm/groupsFilterRaw/groupsHelper.js +733 -207
  302. package/esm/groupsFilterRaw/stateReducer/stateReducerHelper.js +3 -1
  303. package/esm/groupsFilterRaw/types.d.ts +1 -0
  304. package/esm/header/components/collapsedItemsControl/collapsedItemsControl.js +101 -51
  305. package/esm/header/components/mobileFilterControl/mobileFilterControl.js +56 -8
  306. package/esm/header/components/mobileSearchControl/mobileSearchControl.js +113 -13
  307. package/esm/header/headerBack.js +58 -19
  308. package/esm/index.d.ts +1 -0
  309. package/esm/index.js +1 -0
  310. package/esm/list/itemData/itemDataInternal.js +210 -50
  311. package/esm/list/listItem/listItem.js +162 -54
  312. package/esm/menu/components/menuErrorItem.js +27 -4
  313. package/esm/mobileSheet/mobileSheet.js +189 -68
  314. package/esm/modal/modal.js +265 -120
  315. package/esm/nav/nav.js +1 -1
  316. package/esm/nav/navFooter/navFooter.js +76 -38
  317. package/esm/nav/navFooter/navFooterAction/navFooterAction.js +46 -12
  318. package/esm/nav/navHeader/navHeader.js +80 -35
  319. package/esm/nav/navHeader/navHeaderSearch/navHeaderSearch.js +82 -28
  320. package/esm/nav/navItem/navItem.d.ts +3 -3
  321. package/esm/nav/navItem/navItem.js +35 -33
  322. package/esm/nav/navMobileBar/navMobileBar.js +61 -20
  323. package/esm/notification/notification.js +114 -18
  324. package/esm/pagination/paginationArrow.js +75 -10
  325. package/esm/pagination/paginationText/paginationText.js +39 -10
  326. package/esm/pill/components/pillNonActionable/pillNonActionable.js +87 -23
  327. package/esm/pillBox/components/pillBoxItem.js +46 -8
  328. package/esm/pillBox/pillBox.js +115 -19
  329. package/esm/pillExpandable/pillExpandable.js +327 -138
  330. package/esm/rangeRaw/rangeRaw.js +480 -140
  331. package/esm/rangeRaw/utils/rangeHelper.js +203 -38
  332. package/esm/searchInputRaw/searchInputRaw.js +145 -43
  333. package/esm/skeleton/skeleton.js +45 -5
  334. package/esm/sortControl/sortControl.js +146 -41
  335. package/esm/stepperRaw/stepperRaw.js +112 -41
  336. package/esm/storybookHelpers/dataGridWithDifferentCellOptions/components/EntitiesListAction.js +178 -19
  337. package/esm/summary/summary.js +88 -7
  338. package/esm/table/actions/actionsMenu.js +165 -77
  339. package/esm/table/flexible/columnSettings.js +74 -9
  340. package/esm/table/flexible/columnsList.js +104 -42
  341. package/esm/table/flexible/columnsPopup.js +71 -19
  342. package/esm/table/nested/useNestedRows.js +161 -76
  343. package/esm/table/selectable/selectableHeader.js +174 -40
  344. package/esm/table/selectable/useSelectableRows.js +264 -190
  345. package/esm/table/sortable/sortableHeader.js +147 -74
  346. package/esm/tabs/tabs.js +221 -117
  347. package/esm/timePickerRaw/timePickerRaw.js +272 -57
  348. package/esm/toastRaw/toastRaw.js +132 -31
  349. package/esm/toggleButton/toggleButton.d.ts +0 -1
  350. package/esm/toggleButtonRaw/toggleButtonRaw.d.ts +1 -0
  351. package/esm/toggleButtonRaw/toggleButtonRaw.js +111 -18
  352. package/esm/utils/formatDate.js +995 -116
  353. package/{dist/utils/localization/translations/cs-json.js → esm/utils/localization/translations/cs.json} +11 -15
  354. package/{dist/utils/localization/translations/da-DK-json.js → esm/utils/localization/translations/da-DK.json} +31 -26
  355. package/{dist/utils/localization/translations/de-json.js → esm/utils/localization/translations/de.json} +12 -16
  356. package/esm/utils/localization/translations/en.json +308 -0
  357. package/{dist/utils/localization/translations/es-json.js → esm/utils/localization/translations/es.json} +11 -15
  358. package/{dist/utils/localization/translations/fi-FI-json.js → esm/utils/localization/translations/fi-FI.json} +31 -26
  359. package/{dist/utils/localization/translations/fr-FR-json.js → esm/utils/localization/translations/fr-FR.json} +12 -15
  360. package/{dist/utils/localization/translations/fr-json.js → esm/utils/localization/translations/fr.json} +11 -15
  361. package/{dist/utils/localization/translations/hu-HU-json.js → esm/utils/localization/translations/hu-HU.json} +31 -26
  362. package/{dist/utils/localization/translations/id-json.js → esm/utils/localization/translations/id.json} +11 -16
  363. package/{dist/utils/localization/translations/it-json.js → esm/utils/localization/translations/it.json} +11 -15
  364. package/{dist/utils/localization/translations/ja-json.js → esm/utils/localization/translations/ja.json} +11 -15
  365. package/{dist/utils/localization/translations/ko-KR-json.js → esm/utils/localization/translations/ko-KR.json} +24 -26
  366. package/{dist/utils/localization/translations/ms-json.js → esm/utils/localization/translations/ms.json} +11 -15
  367. package/{dist/utils/localization/translations/nb-NO-json.js → esm/utils/localization/translations/nb-NO.json} +31 -26
  368. package/{dist/utils/localization/translations/nl-json.js → esm/utils/localization/translations/nl.json} +11 -15
  369. package/{dist/utils/localization/translations/pl-json.js → esm/utils/localization/translations/pl.json} +11 -15
  370. package/{dist/utils/localization/translations/pt-BR-json.js → esm/utils/localization/translations/pt-BR.json} +11 -15
  371. package/{dist/utils/localization/translations/sk-SK-json.js → esm/utils/localization/translations/sk-SK.json} +31 -26
  372. package/{dist/utils/localization/translations/sv-json.js → esm/utils/localization/translations/sv.json} +11 -15
  373. package/{dist/utils/localization/translations/th-json.js → esm/utils/localization/translations/th.json} +11 -15
  374. package/{dist/utils/localization/translations/tr-json.js → esm/utils/localization/translations/tr.json} +11 -15
  375. package/{dist/utils/localization/translations/zh-Hans-json.js → esm/utils/localization/translations/zh-Hans.json} +11 -15
  376. package/{dist/utils/localization/translations/zh-TW-json.js → esm/utils/localization/translations/zh-TW.json} +11 -26
  377. package/esm/utils/localization/translationsDictionary.d.ts +2 -0
  378. package/esm/utils/localization/translationsDictionary.js +59 -0
  379. package/esm/utils/localization/useLanguage.js +1 -50
  380. package/package.json +17 -10
  381. package/dist/utils/localization/translations/cs-json.d.ts +0 -251
  382. package/dist/utils/localization/translations/da-DK-json.d.ts +0 -252
  383. package/dist/utils/localization/translations/de-json.d.ts +0 -251
  384. package/dist/utils/localization/translations/en-json.d.ts +0 -314
  385. package/dist/utils/localization/translations/en-json.js +0 -317
  386. package/dist/utils/localization/translations/es-json.d.ts +0 -251
  387. package/dist/utils/localization/translations/fi-FI-json.d.ts +0 -252
  388. package/dist/utils/localization/translations/fr-FR-json.d.ts +0 -250
  389. package/dist/utils/localization/translations/fr-json.d.ts +0 -251
  390. package/dist/utils/localization/translations/hu-HU-json.d.ts +0 -252
  391. package/dist/utils/localization/translations/id-json.d.ts +0 -252
  392. package/dist/utils/localization/translations/it-json.d.ts +0 -251
  393. package/dist/utils/localization/translations/ja-json.d.ts +0 -251
  394. package/dist/utils/localization/translations/ko-KR-json.d.ts +0 -258
  395. package/dist/utils/localization/translations/ms-json.d.ts +0 -251
  396. package/dist/utils/localization/translations/nb-NO-json.d.ts +0 -252
  397. package/dist/utils/localization/translations/nl-json.d.ts +0 -251
  398. package/dist/utils/localization/translations/pl-json.d.ts +0 -251
  399. package/dist/utils/localization/translations/pt-BR-json.d.ts +0 -251
  400. package/dist/utils/localization/translations/sk-SK-json.d.ts +0 -251
  401. package/dist/utils/localization/translations/sv-json.d.ts +0 -251
  402. package/dist/utils/localization/translations/th-json.d.ts +0 -251
  403. package/dist/utils/localization/translations/tr-json.d.ts +0 -251
  404. package/dist/utils/localization/translations/zh-Hans-json.d.ts +0 -251
  405. package/dist/utils/localization/translations/zh-TW-json.d.ts +0 -271
  406. package/esm/utils/localization/translations/cs-json.d.ts +0 -251
  407. package/esm/utils/localization/translations/da-DK-json.d.ts +0 -252
  408. package/esm/utils/localization/translations/de-json.d.ts +0 -251
  409. package/esm/utils/localization/translations/en-json.d.ts +0 -314
  410. package/esm/utils/localization/translations/en-json.js +0 -314
  411. package/esm/utils/localization/translations/es-json.d.ts +0 -251
  412. package/esm/utils/localization/translations/fi-FI-json.d.ts +0 -252
  413. package/esm/utils/localization/translations/fr-FR-json.d.ts +0 -250
  414. package/esm/utils/localization/translations/fr-json.d.ts +0 -251
  415. package/esm/utils/localization/translations/hu-HU-json.d.ts +0 -252
  416. package/esm/utils/localization/translations/id-json.d.ts +0 -252
  417. package/esm/utils/localization/translations/it-json.d.ts +0 -251
  418. package/esm/utils/localization/translations/ja-json.d.ts +0 -251
  419. package/esm/utils/localization/translations/ko-KR-json.d.ts +0 -258
  420. package/esm/utils/localization/translations/ms-json.d.ts +0 -251
  421. package/esm/utils/localization/translations/nb-NO-json.d.ts +0 -252
  422. package/esm/utils/localization/translations/nl-json.d.ts +0 -251
  423. package/esm/utils/localization/translations/pl-json.d.ts +0 -251
  424. package/esm/utils/localization/translations/pt-BR-json.d.ts +0 -251
  425. package/esm/utils/localization/translations/sk-SK-json.d.ts +0 -251
  426. package/esm/utils/localization/translations/sv-json.d.ts +0 -251
  427. package/esm/utils/localization/translations/th-json.d.ts +0 -251
  428. package/esm/utils/localization/translations/tr-json.d.ts +0 -251
  429. package/esm/utils/localization/translations/zh-Hans-json.d.ts +0 -251
  430. package/esm/utils/localization/translations/zh-TW-json.d.ts +0 -271
@@ -1,5 +1,11 @@
1
1
  "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
2
+
3
+ const {
4
+ injectString
5
+ } = require("../../utils/localization/translationsDictionary");
6
+ Object.defineProperty(exports, "__esModule", {
7
+ value: true
8
+ });
3
9
  exports.AccessibleChartNarrative = exports.simplifyData = exports.collectAllPoints = void 0;
4
10
  const jsx_runtime_1 = require("react/jsx-runtime");
5
11
  const useLanguage_1 = require("../../utils/localization/useLanguage");
@@ -11,595 +17,682 @@ const getFormattedLabel_1 = require("../utils/getFormattedLabel");
11
17
  const truncateDecimals_1 = require("../../utils/truncateDecimals");
12
18
  const calculateMinTruncationPrecision_1 = require("../utils/calculateMinTruncationPrecision");
13
19
  const removeTrendDataFromDatasets_1 = require("../utils/removeTrendDataFromDatasets");
20
+ injectString("cs", "Data", "Data");
21
+ injectString("da-DK", "Data", "Data");
22
+ injectString("de", "Data", "Daten");
23
+ injectString("en", "Data", "Data");
24
+ injectString("es", "Data", "Datos");
25
+ injectString("fi-FI", "Data", "Data");
26
+ injectString("fr", "Data", "Donn\xE9es");
27
+ injectString("fr-FR", "Data", "Donn\xE9es");
28
+ injectString("hu-HU", "Data", "Adatok");
29
+ injectString("id", "Data", "Data");
30
+ injectString("it", "Data", "Dati");
31
+ injectString("ja", "Data", "\u30C7\u30FC\u30BF");
32
+ injectString("ko-KR", "Data", "\uB370\uC774\uD130");
33
+ injectString("ms", "Data", "Data");
34
+ injectString("nb-NO", "Data", "Data");
35
+ injectString("nl", "Data", "Gegevens");
36
+ injectString("pl", "Data", "Dane");
37
+ injectString("pt-BR", "Data", "Dados");
38
+ injectString("sk-SK", "Data", "D\xE1ta");
39
+ injectString("sv", "Data", "Data");
40
+ injectString("th", "Data", "\u0E02\u0E49\u0E2D\u0E21\u0E39\u0E25");
41
+ injectString("tr", "Data", "Veri");
42
+ injectString("zh-Hans", "Data", "\u6570\u636E");
43
+ injectString("zh-TW", "Data", "\u8CC7\u6599");
44
+ injectString("en", "switched {TRANSITIONS} times between two states: {STATE1} and {STATE2}.", "switched {TRANSITIONS} times between two states: {STATE1} and {STATE2}.");
45
+ injectString("en", "Highest point(s):", "Highest point(s):");
46
+ injectString("en", "Lowest point(s):", "Lowest point(s):");
47
+ injectString("en", "Segment {INDEX} {DIRECTION} from {FROM} at {X0} to {TO} at {X}.", "Segment {INDEX} {DIRECTION} from {FROM} at {X0} to {TO} at {X}.");
48
+ injectString("en", "shows a complex trend with multiple segments:", "shows a complex trend with multiple segments:");
49
+ injectString("cs", "No data available", "Nejsou k\xA0dispozici \u017E\xE1dn\xE1 data");
50
+ injectString("da-DK", "No data available", "Ingen data tilg\xE6ngelige");
51
+ injectString("de", "No data available", "Keine Daten verf\xFCgbar");
52
+ injectString("en", "No data available", "No data available");
53
+ injectString("es", "No data available", "No hay datos disponibles");
54
+ injectString("fi-FI", "No data available", "Tietoja ei saatavilla");
55
+ injectString("fr", "No data available", "Aucune donn\xE9e disponible");
56
+ injectString("fr-FR", "No data available", "Aucune donn\xE9e disponible");
57
+ injectString("hu-HU", "No data available", "Nincsenek rendelkez\xE9sre \xE1ll\xF3 adatok");
58
+ injectString("id", "No data available", "Tidak ada data tersedia");
59
+ injectString("it", "No data available", "Nessun dato disponibile");
60
+ injectString("ja", "No data available", "\u30C7\u30FC\u30BF\u304C\u3042\u308A\u307E\u305B\u3093");
61
+ injectString("ko-KR", "No data available", "\uC0AC\uC6A9 \uAC00\uB2A5\uD55C \uB370\uC774\uD130\uAC00 \uC5C6\uC2B5\uB2C8\uB2E4");
62
+ injectString("ms", "No data available", "Tiada data tersedia");
63
+ injectString("nb-NO", "No data available", "Ingen data tilgjengelig");
64
+ injectString("nl", "No data available", "Geen gegevens beschikbaar");
65
+ injectString("pl", "No data available", "Brak dost\u0119pnych danych");
66
+ injectString("pt-BR", "No data available", "Nenhum dado dispon\xEDvel");
67
+ injectString("sk-SK", "No data available", "Nie s\xFA k dispoz\xEDcii \u017Eiadne \xFAdaje");
68
+ injectString("sv", "No data available", "Det finns inga tillg\xE4ngliga data");
69
+ injectString("th", "No data available", "\u0E44\u0E21\u0E48\u0E21\u0E35\u0E02\u0E49\u0E2D\u0E21\u0E39\u0E25");
70
+ injectString("tr", "No data available", "Mevcut veri yok");
71
+ injectString("zh-Hans", "No data available", "\u65E0\u53EF\u7528\u6570\u636E");
72
+ injectString("zh-TW", "No data available", "\u6C92\u6709\u53EF\u7528\u8CC7\u6599");
73
+ injectString("en", "Only one data point: value is {VALUE}.", "Only one data point: value is {VALUE}.");
74
+ injectString("en", "Average value is:", "Average value is:");
75
+ injectString("en", "shows a relatively flat or stable trend.", "shows a relatively flat or stable trend.");
76
+ injectString("en", "value changes in the range from {MIN} to {MAX}.", "value changes in the range from {MIN} to {MAX}.");
77
+ injectString("en", "from {FROM} at {X0} to {TO} at {X}.", "from {FROM} at {X0} to {TO} at {X}.");
78
+ injectString("en", "Error generating chart narrative for dataset", "Error generating chart narrative for dataset");
14
79
  function collectAllPoints(dataset, dateFormatter, miniChartLabels, options) {
15
- if (dataset.data.length === 0) {
16
- return [];
17
- }
18
- // Minichart data processing
19
- if (miniChartLabels) {
20
- return dataset.data.map((value, index) => ({
21
- x: index,
22
- y: typeof value === "number" ? value : 0,
23
- originX: index === 0 ? miniChartLabels[0] : (index === dataset.data.length - 1 ? miniChartLabels[miniChartLabels.length - 1] : index)
24
- }));
25
- }
26
- // Standard chart data processing
27
- const allPoints = [];
28
- for (const [index, point] of dataset.data.entries()) {
29
- if (typeof point !== "object" || point === null || !("y" in point)) {
30
- continue;
31
- }
32
- let xNumeric;
33
- let originX;
34
- const rawXValue = point.x;
35
- if (rawXValue instanceof Date || (typeof rawXValue === "string" && (0, isDateString_1.isDateString)(rawXValue))) {
36
- xNumeric = new Date(rawXValue).getTime();
37
- originX = (0, getFormattedLabel_1.getFormattedLabel)(rawXValue, dateFormatter, options);
38
- }
39
- else if (typeof rawXValue === "number") {
40
- xNumeric = rawXValue;
41
- originX = rawXValue;
42
- }
43
- else {
44
- xNumeric = index;
45
- originX = rawXValue;
46
- }
47
- allPoints.push({ x: xNumeric, y: point.y || 0, originX });
48
- }
49
- return allPoints;
80
+ if (dataset.data.length === 0) {
81
+ return [];
82
+ }
83
+ // Minichart data processing
84
+ if (miniChartLabels) {
85
+ return dataset.data.map((value, index) => ({
86
+ x: index,
87
+ y: typeof value === "number" ? value : 0,
88
+ originX: index === 0 ? miniChartLabels[0] : index === dataset.data.length - 1 ? miniChartLabels[miniChartLabels.length - 1] : index
89
+ }));
90
+ }
91
+ // Standard chart data processing
92
+ const allPoints = [];
93
+ for (const [index, point] of dataset.data.entries()) {
94
+ if (typeof point !== "object" || point === null || !("y" in point)) {
95
+ continue;
96
+ }
97
+ let xNumeric;
98
+ let originX;
99
+ const rawXValue = point.x;
100
+ if (rawXValue instanceof Date || typeof rawXValue === "string" && (0, isDateString_1.isDateString)(rawXValue)) {
101
+ xNumeric = new Date(rawXValue).getTime();
102
+ originX = (0, getFormattedLabel_1.getFormattedLabel)(rawXValue, dateFormatter, options);
103
+ } else if (typeof rawXValue === "number") {
104
+ xNumeric = rawXValue;
105
+ originX = rawXValue;
106
+ } else {
107
+ xNumeric = index;
108
+ originX = rawXValue;
109
+ }
110
+ allPoints.push({
111
+ x: xNumeric,
112
+ y: point.y || 0,
113
+ originX
114
+ });
115
+ }
116
+ return allPoints;
50
117
  }
51
118
  exports.collectAllPoints = collectAllPoints;
52
119
  function simplifyData(data) {
53
- // Need at least 3 points to find a peak or valley
54
- if (data.length < 3) {
55
- return data;
56
- }
57
- // Calculate Potential Peak/Valley Height and Dominance for Every Point
58
- const scoredData = data.map((currentPoint, i) => {
59
- if (currentPoint.y === null) {
60
- return {
61
- point: currentPoint,
62
- peakHeight: 0,
63
- valleyHeight: 0,
64
- peakDominance: 0,
65
- valleyDominance: 0
66
- };
67
- }
68
- let peakHeight = 0;
69
- let valleyHeight = 0;
70
- let peakDominance = 0;
71
- let valleyDominance = 0;
72
- let localMinForPeak = currentPoint.y;
73
- // Scan left
74
- for (let j = i - 1; j >= 0; j--) {
75
- const point = data[j];
76
- if (point.y !== null && point.y < currentPoint.y) {
77
- localMinForPeak = Math.min(localMinForPeak, point.y);
78
- peakDominance++;
79
- }
80
- else {
81
- break;
82
- }
83
- }
84
- // Scan right
85
- for (let j = i + 1; j < data.length; j++) {
86
- const point = data[j];
87
- if (point.y !== null && point.y < currentPoint.y) {
88
- localMinForPeak = Math.min(localMinForPeak, point.y);
89
- peakDominance++;
90
- }
91
- else {
92
- break;
93
- }
94
- }
95
- if (peakDominance > 0) {
96
- peakHeight = currentPoint.y - localMinForPeak;
97
- }
98
- // Calculate Valley Height & Dominance
99
- let localMaxForValley = currentPoint.y;
100
- // Scan left
101
- for (let j = i - 1; j >= 0; j--) {
102
- const point = data[j];
103
- if (point.y !== null && point.y > currentPoint.y) {
104
- localMaxForValley = Math.max(localMaxForValley, point.y);
105
- valleyDominance++;
106
- }
107
- else {
108
- break;
109
- }
110
- }
111
- // Scan right
112
- for (let j = i + 1; j < data.length; j++) {
113
- const point = data[j];
114
- if (point.y !== null && point.y > currentPoint.y) {
115
- localMaxForValley = Math.max(localMaxForValley, point.y);
116
- valleyDominance++;
117
- }
118
- else {
119
- break;
120
- }
121
- }
122
- if (valleyDominance > 0) {
123
- valleyHeight = localMaxForValley - currentPoint.y;
124
- }
125
- return { point: currentPoint, peakHeight, valleyHeight, peakDominance, valleyDominance };
126
- });
127
- // Filter points by trend change and relative height
128
- const significantExtremums = [];
129
- const strengthThreshold = 0.50;
130
- const yValues = data.filter(p => p.y !== null).map(p => p.y);
131
- const minY = yValues.reduce((min, current) => Math.min(min, current));
132
- const maxY = yValues.reduce((max, current) => Math.max(max, current));
133
- const datasetRange = maxY - minY;
134
- // Proceed only if there is a range to avoid division by zero
135
- if (datasetRange > 0) {
136
- for (let i = 1; i < scoredData.length - 1; i++) {
137
- const prev = scoredData[i - 1];
138
- const current = scoredData[i];
139
- const next = scoredData[i + 1];
140
- // Check for a peak in the 'peakHeight' values
141
- const isPeak = current.peakHeight > prev.peakHeight && current.peakHeight > next.peakHeight;
142
- // Check for a peak in the 'valleyHeight' values
143
- const isValley = current.valleyHeight > prev.valleyHeight && current.valleyHeight > next.valleyHeight;
144
- if (isPeak) {
145
- const relHeight = current.peakHeight / datasetRange;
146
- if (relHeight >= strengthThreshold && current.peakDominance > 2) {
147
- significantExtremums.push(current.point);
148
- }
149
- }
150
- else if (isValley) {
151
- const relHeight = current.valleyHeight / datasetRange;
152
- if (relHeight >= strengthThreshold && current.valleyDominance > 2) {
153
- significantExtremums.push(current.point);
154
- }
155
- }
156
- }
157
- }
158
- const uniquePointsSet = new Set();
159
- const finalResult = [];
160
- const addPointIfUnique = (point) => {
161
- // using a composite key for uniqueness
162
- const key = `${point.x.toString()}-${point.y || ""}`;
163
- if (!uniquePointsSet.has(key)) {
164
- uniquePointsSet.add(key);
165
- finalResult.push(point);
166
- }
120
+ // Need at least 3 points to find a peak or valley
121
+ if (data.length < 3) {
122
+ return data;
123
+ }
124
+ // Calculate Potential Peak/Valley Height and Dominance for Every Point
125
+ const scoredData = data.map((currentPoint, i) => {
126
+ if (currentPoint.y === null) {
127
+ return {
128
+ point: currentPoint,
129
+ peakHeight: 0,
130
+ valleyHeight: 0,
131
+ peakDominance: 0,
132
+ valleyDominance: 0
133
+ };
134
+ }
135
+ let peakHeight = 0;
136
+ let valleyHeight = 0;
137
+ let peakDominance = 0;
138
+ let valleyDominance = 0;
139
+ let localMinForPeak = currentPoint.y;
140
+ // Scan left
141
+ for (let j = i - 1; j >= 0; j--) {
142
+ const point = data[j];
143
+ if (point.y !== null && point.y < currentPoint.y) {
144
+ localMinForPeak = Math.min(localMinForPeak, point.y);
145
+ peakDominance++;
146
+ } else {
147
+ break;
148
+ }
149
+ }
150
+ // Scan right
151
+ for (let j = i + 1; j < data.length; j++) {
152
+ const point = data[j];
153
+ if (point.y !== null && point.y < currentPoint.y) {
154
+ localMinForPeak = Math.min(localMinForPeak, point.y);
155
+ peakDominance++;
156
+ } else {
157
+ break;
158
+ }
159
+ }
160
+ if (peakDominance > 0) {
161
+ peakHeight = currentPoint.y - localMinForPeak;
162
+ }
163
+ // Calculate Valley Height & Dominance
164
+ let localMaxForValley = currentPoint.y;
165
+ // Scan left
166
+ for (let j = i - 1; j >= 0; j--) {
167
+ const point = data[j];
168
+ if (point.y !== null && point.y > currentPoint.y) {
169
+ localMaxForValley = Math.max(localMaxForValley, point.y);
170
+ valleyDominance++;
171
+ } else {
172
+ break;
173
+ }
174
+ }
175
+ // Scan right
176
+ for (let j = i + 1; j < data.length; j++) {
177
+ const point = data[j];
178
+ if (point.y !== null && point.y > currentPoint.y) {
179
+ localMaxForValley = Math.max(localMaxForValley, point.y);
180
+ valleyDominance++;
181
+ } else {
182
+ break;
183
+ }
184
+ }
185
+ if (valleyDominance > 0) {
186
+ valleyHeight = localMaxForValley - currentPoint.y;
187
+ }
188
+ return {
189
+ point: currentPoint,
190
+ peakHeight,
191
+ valleyHeight,
192
+ peakDominance,
193
+ valleyDominance
167
194
  };
168
- // Add key points to the array
169
- addPointIfUnique(data[0]);
170
- addPointIfUnique(data[data.length - 1]);
171
- const globalMinPoint = data.find(p => p.y === minY);
172
- if (globalMinPoint) {
173
- addPointIfUnique(globalMinPoint);
174
- }
175
- const globalMaxPoint = data.find(p => p.y === maxY);
176
- if (globalMaxPoint) {
177
- addPointIfUnique(globalMaxPoint);
178
- }
179
- // Add other significant extremums
180
- significantExtremums.forEach(addPointIfUnique);
181
- // Sort the final result array chronologically
182
- finalResult.sort((a, b) => new Date(a.x).getTime() - new Date(b.x).getTime());
183
- // Filter out non-significant points based on area under the curve
184
- const getSquare = (p1, p2) => {
185
- const x1 = new Date(p1.x).getTime();
186
- const x2 = new Date(p2.x).getTime();
187
- const y1 = p1.y;
188
- const y2 = p2.y;
189
- return (x2 - x1) * (y1 + (y2 - y1) / 2);
190
- };
191
- const immutablePoints = [data[0], data[data.length - 1], globalMinPoint, globalMaxPoint].filter(Boolean);
192
- for (let i = 1; i < finalResult.length - 1; i++) {
193
- const current = finalResult[i];
194
- // Skip removal if the current point is one of the designated immutable points
195
- if (immutablePoints.some(p => p && p.x === current.x && p.y === current.y)) {
196
- continue;
195
+ });
196
+ // Filter points by trend change and relative height
197
+ const significantExtremums = [];
198
+ const strengthThreshold = 0.50;
199
+ const yValues = data.filter(p => p.y !== null).map(p => p.y);
200
+ const minY = yValues.reduce((min, current) => Math.min(min, current));
201
+ const maxY = yValues.reduce((max, current) => Math.max(max, current));
202
+ const datasetRange = maxY - minY;
203
+ // Proceed only if there is a range to avoid division by zero
204
+ if (datasetRange > 0) {
205
+ for (let i = 1; i < scoredData.length - 1; i++) {
206
+ const prev = scoredData[i - 1];
207
+ const current = scoredData[i];
208
+ const next = scoredData[i + 1];
209
+ // Check for a peak in the 'peakHeight' values
210
+ const isPeak = current.peakHeight > prev.peakHeight && current.peakHeight > next.peakHeight;
211
+ // Check for a peak in the 'valleyHeight' values
212
+ const isValley = current.valleyHeight > prev.valleyHeight && current.valleyHeight > next.valleyHeight;
213
+ if (isPeak) {
214
+ const relHeight = current.peakHeight / datasetRange;
215
+ if (relHeight >= strengthThreshold && current.peakDominance > 2) {
216
+ significantExtremums.push(current.point);
197
217
  }
198
- const prev = finalResult[i - 1];
199
- const next = finalResult[i + 1];
200
- const squareWithPoint = getSquare(prev, current) + getSquare(current, next);
201
- const squareWithoutPoint = getSquare(prev, next);
202
- const squares = [squareWithPoint, squareWithoutPoint].sort((a, b) => a - b);
203
- const squareRatio = squares[0] / squares[1];
204
- if (squareRatio > 0.9) {
205
- // remove insignificant point
206
- finalResult.splice(i, 1);
207
- i--;
218
+ } else if (isValley) {
219
+ const relHeight = current.valleyHeight / datasetRange;
220
+ if (relHeight >= strengthThreshold && current.valleyDominance > 2) {
221
+ significantExtremums.push(current.point);
208
222
  }
209
- }
210
- return finalResult;
223
+ }
224
+ }
225
+ }
226
+ const uniquePointsSet = new Set();
227
+ const finalResult = [];
228
+ const addPointIfUnique = point => {
229
+ // using a composite key for uniqueness
230
+ const key = `${point.x.toString()}-${point.y || ""}`;
231
+ if (!uniquePointsSet.has(key)) {
232
+ uniquePointsSet.add(key);
233
+ finalResult.push(point);
234
+ }
235
+ };
236
+ // Add key points to the array
237
+ addPointIfUnique(data[0]);
238
+ addPointIfUnique(data[data.length - 1]);
239
+ const globalMinPoint = data.find(p => p.y === minY);
240
+ if (globalMinPoint) {
241
+ addPointIfUnique(globalMinPoint);
242
+ }
243
+ const globalMaxPoint = data.find(p => p.y === maxY);
244
+ if (globalMaxPoint) {
245
+ addPointIfUnique(globalMaxPoint);
246
+ }
247
+ // Add other significant extremums
248
+ significantExtremums.forEach(addPointIfUnique);
249
+ // Sort the final result array chronologically
250
+ finalResult.sort((a, b) => new Date(a.x).getTime() - new Date(b.x).getTime());
251
+ // Filter out non-significant points based on area under the curve
252
+ const getSquare = (p1, p2) => {
253
+ const x1 = new Date(p1.x).getTime();
254
+ const x2 = new Date(p2.x).getTime();
255
+ const y1 = p1.y;
256
+ const y2 = p2.y;
257
+ return (x2 - x1) * (y1 + (y2 - y1) / 2);
258
+ };
259
+ const immutablePoints = [data[0], data[data.length - 1], globalMinPoint, globalMaxPoint].filter(Boolean);
260
+ for (let i = 1; i < finalResult.length - 1; i++) {
261
+ const current = finalResult[i];
262
+ // Skip removal if the current point is one of the designated immutable points
263
+ if (immutablePoints.some(p => p && p.x === current.x && p.y === current.y)) {
264
+ continue;
265
+ }
266
+ const prev = finalResult[i - 1];
267
+ const next = finalResult[i + 1];
268
+ const squareWithPoint = getSquare(prev, current) + getSquare(current, next);
269
+ const squareWithoutPoint = getSquare(prev, next);
270
+ const squares = [squareWithPoint, squareWithoutPoint].sort((a, b) => a - b);
271
+ const squareRatio = squares[0] / squares[1];
272
+ if (squareRatio > 0.9) {
273
+ // remove insignificant point
274
+ finalResult.splice(i, 1);
275
+ i--;
276
+ }
277
+ }
278
+ return finalResult;
211
279
  }
212
280
  exports.simplifyData = simplifyData;
213
281
  function getTrendDirectionBySlope(slope) {
214
- const slopeThreshold = 1e-10;
215
- if (slope > slopeThreshold) {
216
- return "increases";
217
- }
218
- if (slope < -slopeThreshold) {
219
- return "decreases";
220
- }
221
- return "flat";
282
+ const slopeThreshold = 1e-10;
283
+ if (slope > slopeThreshold) {
284
+ return "increases";
285
+ }
286
+ if (slope < -slopeThreshold) {
287
+ return "decreases";
288
+ }
289
+ return "flat";
222
290
  }
223
291
  function calculateLinearRegression(points) {
224
- if (points.length < 2) {
225
- return { slope: NaN, yIntercept: NaN };
226
- }
227
- const sumX = points.reduce((sum, p) => sum + p.x, 0);
228
- const sumY = points.reduce((sum, p) => sum + p.y, 0);
229
- const meanX = sumX / points.length;
230
- const meanY = sumY / points.length;
231
- let numerator = 0;
232
- let denominator = 0;
233
- for (const p of points) {
234
- numerator += (p.x - meanX) * (p.y - meanY);
235
- denominator += (p.x - meanX) * (p.x - meanX);
236
- }
237
- const slope = denominator === 0 ? 0 : numerator / denominator;
238
- const yIntercept = meanY - slope * meanX;
239
- return { slope, yIntercept };
292
+ if (points.length < 2) {
293
+ return {
294
+ slope: NaN,
295
+ yIntercept: NaN
296
+ };
297
+ }
298
+ const sumX = points.reduce((sum, p) => sum + p.x, 0);
299
+ const sumY = points.reduce((sum, p) => sum + p.y, 0);
300
+ const meanX = sumX / points.length;
301
+ const meanY = sumY / points.length;
302
+ let numerator = 0;
303
+ let denominator = 0;
304
+ for (const p of points) {
305
+ numerator += (p.x - meanX) * (p.y - meanY);
306
+ denominator += (p.x - meanX) * (p.x - meanX);
307
+ }
308
+ const slope = denominator === 0 ? 0 : numerator / denominator;
309
+ const yIntercept = meanY - slope * meanX;
310
+ return {
311
+ slope,
312
+ yIntercept
313
+ };
240
314
  }
241
315
  function detectTwoStateChart(dataset, translate, dateFormatter, miniChartLabels, options) {
242
- const allPoints = collectAllPoints(dataset, dateFormatter, miniChartLabels, options);
243
- if (allPoints.length <= 2) {
244
- return false;
245
- }
246
- const datasetName = dataset.label || translate("Data");
247
- const uniqueYValues = new Set();
248
- const tolerance = 1e-6;
249
- for (const point of allPoints) {
250
- uniqueYValues.add(point.y);
251
- if (uniqueYValues.size > 2) {
252
- return false;
253
- }
254
- }
255
- const isTwoState = uniqueYValues.size === 2;
256
- if (!isTwoState) {
257
- return false;
258
- }
259
- // Count state transitions
260
- let transitions = 0;
261
- for (let i = 1; i < allPoints.length; i++) {
262
- const prevValue = allPoints[i - 1].y;
263
- const currentValue = allPoints[i].y;
264
- if (Math.abs(prevValue - currentValue) > tolerance) {
265
- transitions++;
266
- }
267
- }
268
- const [val1, val2] = uniqueYValues;
269
- const decimalLength = (0, calculateMinTruncationPrecision_1.calculateMinTruncationPrecision)([val1, val2]);
270
- const summary = `${datasetName} ${translate("switched {TRANSITIONS} times between two states: {STATE1} and {STATE2}.")
271
- .replace("{STATE1}", (0, truncateDecimals_1.truncateDecimals)(val1, decimalLength).toString())
272
- .replace("{STATE2}", (0, truncateDecimals_1.truncateDecimals)(val2, decimalLength).toString())
273
- .replace("{TRANSITIONS}", transitions.toString())}`;
274
- return summary;
316
+ const allPoints = collectAllPoints(dataset, dateFormatter, miniChartLabels, options);
317
+ if (allPoints.length <= 2) {
318
+ return false;
319
+ }
320
+ const datasetName = dataset.label || translate("Data");
321
+ const uniqueYValues = new Set();
322
+ const tolerance = 1e-6;
323
+ for (const point of allPoints) {
324
+ uniqueYValues.add(point.y);
325
+ if (uniqueYValues.size > 2) {
326
+ return false;
327
+ }
328
+ }
329
+ const isTwoState = uniqueYValues.size === 2;
330
+ if (!isTwoState) {
331
+ return false;
332
+ }
333
+ // Count state transitions
334
+ let transitions = 0;
335
+ for (let i = 1; i < allPoints.length; i++) {
336
+ const prevValue = allPoints[i - 1].y;
337
+ const currentValue = allPoints[i].y;
338
+ if (Math.abs(prevValue - currentValue) > tolerance) {
339
+ transitions++;
340
+ }
341
+ }
342
+ const [val1, val2] = uniqueYValues;
343
+ const decimalLength = (0, calculateMinTruncationPrecision_1.calculateMinTruncationPrecision)([val1, val2]);
344
+ const summary = `${datasetName} ${translate("switched {TRANSITIONS} times between two states: {STATE1} and {STATE2}.").replace("{STATE1}", (0, truncateDecimals_1.truncateDecimals)(val1, decimalLength).toString()).replace("{STATE2}", (0, truncateDecimals_1.truncateDecimals)(val2, decimalLength).toString()).replace("{TRANSITIONS}", transitions.toString())}`;
345
+ return summary;
275
346
  }
276
347
  // Calculates the Median Absolute Deviation (MAD) for a given array of numbers.
277
348
  function calculateMAD(data, scaleFactor = 1.4826) {
278
- if (data.length === 0) {
279
- return 0;
280
- }
281
- // Sort the data to find the median
282
- const sortedData = [...data].sort((a, b) => a - b);
283
- const mid = Math.floor(sortedData.length / 2);
284
- let median;
285
- if (sortedData.length % 2 === 0) {
286
- median = (sortedData[mid - 1] + sortedData[mid]) / 2;
287
- }
288
- else {
289
- median = sortedData[mid];
290
- }
291
- // Calculate absolute deviations from the median
292
- const deviations = sortedData.map(d => Math.abs(d - median));
293
- let mad;
294
- const madMid = Math.floor(deviations.length / 2);
295
- if (deviations.length % 2 === 0) {
296
- mad = (deviations[madMid - 1] + deviations[madMid]) / 2;
297
- }
298
- else {
299
- mad = deviations[madMid];
300
- }
301
- return mad * scaleFactor;
349
+ if (data.length === 0) {
350
+ return 0;
351
+ }
352
+ // Sort the data to find the median
353
+ const sortedData = [...data].sort((a, b) => a - b);
354
+ const mid = Math.floor(sortedData.length / 2);
355
+ let median;
356
+ if (sortedData.length % 2 === 0) {
357
+ median = (sortedData[mid - 1] + sortedData[mid]) / 2;
358
+ } else {
359
+ median = sortedData[mid];
360
+ }
361
+ // Calculate absolute deviations from the median
362
+ const deviations = sortedData.map(d => Math.abs(d - median));
363
+ let mad;
364
+ const madMid = Math.floor(deviations.length / 2);
365
+ if (deviations.length % 2 === 0) {
366
+ mad = (deviations[madMid - 1] + deviations[madMid]) / 2;
367
+ } else {
368
+ mad = deviations[madMid];
369
+ }
370
+ return mad * scaleFactor;
302
371
  }
303
372
  function getInliersForSmallSet(allPoints) {
304
- // Only proceed if there are enough points to perform exclusion
305
- if (allPoints.length < 3) {
306
- return allPoints;
307
- }
308
- const initialLr = calculateLinearRegression(allPoints);
309
- const initialResiduals = allPoints.map((point) => ({
310
- point,
311
- residual: Math.abs(point.y - (initialLr.slope * point.x + initialLr.yIntercept))
312
- }));
313
- // Sort to put the worst-fitting point (largest residual) first
314
- initialResiduals.sort((a, b) => b.residual - a.residual);
315
- // Exclude the top residual (the potential outlier) and return the rest as inliers.
316
- return initialResiduals.slice(1).map(r => r.point);
373
+ // Only proceed if there are enough points to perform exclusion
374
+ if (allPoints.length < 3) {
375
+ return allPoints;
376
+ }
377
+ const initialLr = calculateLinearRegression(allPoints);
378
+ const initialResiduals = allPoints.map(point => ({
379
+ point,
380
+ residual: Math.abs(point.y - (initialLr.slope * point.x + initialLr.yIntercept))
381
+ }));
382
+ // Sort to put the worst-fitting point (largest residual) first
383
+ initialResiduals.sort((a, b) => b.residual - a.residual);
384
+ // Exclude the top residual (the potential outlier) and return the rest as inliers.
385
+ return initialResiduals.slice(1).map(r => r.point);
317
386
  }
318
387
  function getInliersForLargeSet(allPoints, initialLr) {
319
- const initialResiduals = allPoints.map(point => {
320
- const predictedY = initialLr.slope * point.x + initialLr.yIntercept;
321
- return point.y - predictedY;
322
- });
323
- const madOfInitialResiduals = calculateMAD(initialResiduals);
324
- const strictInlierFilter = 1.5;
325
- const pointsForRobustLr = [];
326
- if (madOfInitialResiduals > 1e-9) {
327
- for (let i = 0; i < allPoints.length; i++) {
328
- if (Math.abs(initialResiduals[i]) <= strictInlierFilter * madOfInitialResiduals) {
329
- pointsForRobustLr.push(allPoints[i]);
330
- }
331
- }
332
- }
333
- else {
334
- // If no spread, use all points.
335
- pointsForRobustLr.push(...allPoints);
336
- }
337
- return pointsForRobustLr;
388
+ const initialResiduals = allPoints.map(point => {
389
+ const predictedY = initialLr.slope * point.x + initialLr.yIntercept;
390
+ return point.y - predictedY;
391
+ });
392
+ const madOfInitialResiduals = calculateMAD(initialResiduals);
393
+ const strictInlierFilter = 1.5;
394
+ const pointsForRobustLr = [];
395
+ if (madOfInitialResiduals > 1e-9) {
396
+ for (let i = 0; i < allPoints.length; i++) {
397
+ if (Math.abs(initialResiduals[i]) <= strictInlierFilter * madOfInitialResiduals) {
398
+ pointsForRobustLr.push(allPoints[i]);
399
+ }
400
+ }
401
+ } else {
402
+ // If no spread, use all points.
403
+ pointsForRobustLr.push(...allPoints);
404
+ }
405
+ return pointsForRobustLr;
338
406
  }
339
407
  function detectSignificantDeviations(allPoints, translate, decimalLength, deviationThreshold = 2) {
340
- if (allPoints.length < 3) {
341
- return null;
342
- }
343
- let pointsForRobustLr = [];
344
- let initialLr = null;
345
- // If the dataset is tiny (where MAD-based filtering is most fragile)
346
- if (allPoints.length <= 5) {
347
- pointsForRobustLr = getInliersForSmallSet(allPoints);
348
- }
349
- else {
350
- initialLr = calculateLinearRegression(allPoints);
351
- pointsForRobustLr = getInliersForLargeSet(allPoints, initialLr);
352
- }
353
- let finalSlope;
354
- let finalYIntercept;
355
- // Use the determined pointsForRobustLr for the final regression
356
- if (pointsForRobustLr.length < 2) {
357
- console.warn("Not enough points for robust regression, falling back to all points.");
358
- if (!initialLr) {
359
- initialLr = calculateLinearRegression(allPoints);
360
- }
361
- finalSlope = initialLr.slope;
362
- finalYIntercept = initialLr.yIntercept;
363
- }
364
- else {
365
- const robustLr = calculateLinearRegression(pointsForRobustLr);
366
- finalSlope = robustLr.slope;
367
- finalYIntercept = robustLr.yIntercept;
368
- }
369
- // Calculate Final Residuals for ALL Original Points against the Robust Line
370
- const pointsWithFinalResiduals = allPoints.map(point => {
371
- const predictedYRobust = finalSlope * point.x + finalYIntercept;
372
- const residual = point.y - predictedYRobust;
373
- return Object.assign(Object.assign({}, point), { residual: residual, isSignificantlyHigh: false, isSignificantlyLow: false });
408
+ if (allPoints.length < 3) {
409
+ return null;
410
+ }
411
+ let pointsForRobustLr = [];
412
+ let initialLr = null;
413
+ // If the dataset is tiny (where MAD-based filtering is most fragile)
414
+ if (allPoints.length <= 5) {
415
+ pointsForRobustLr = getInliersForSmallSet(allPoints);
416
+ } else {
417
+ initialLr = calculateLinearRegression(allPoints);
418
+ pointsForRobustLr = getInliersForLargeSet(allPoints, initialLr);
419
+ }
420
+ let finalSlope;
421
+ let finalYIntercept;
422
+ // Use the determined pointsForRobustLr for the final regression
423
+ if (pointsForRobustLr.length < 2) {
424
+ console.warn("Not enough points for robust regression, falling back to all points.");
425
+ if (!initialLr) {
426
+ initialLr = calculateLinearRegression(allPoints);
427
+ }
428
+ finalSlope = initialLr.slope;
429
+ finalYIntercept = initialLr.yIntercept;
430
+ } else {
431
+ const robustLr = calculateLinearRegression(pointsForRobustLr);
432
+ finalSlope = robustLr.slope;
433
+ finalYIntercept = robustLr.yIntercept;
434
+ }
435
+ // Calculate Final Residuals for ALL Original Points against the Robust Line
436
+ const pointsWithFinalResiduals = allPoints.map(point => {
437
+ const predictedYRobust = finalSlope * point.x + finalYIntercept;
438
+ const residual = point.y - predictedYRobust;
439
+ return Object.assign(Object.assign({}, point), {
440
+ residual: residual,
441
+ isSignificantlyHigh: false,
442
+ isSignificantlyLow: false
374
443
  });
375
- const finalResidualsForDetection = pointsWithFinalResiduals.map(p => p.residual);
376
- const robustResidualSpread = calculateMAD(finalResidualsForDetection);
377
- const SMALL_TOLERANCE = 1e-9;
378
- let effectiveDeviationMeasure = robustResidualSpread;
379
- const isSmallSet = allPoints.length <= 5;
380
- // Calculate the Y-range of the final data set for absolute thresholding
381
- const yValues = allPoints.map(p => p.y);
382
- const yMin = yValues.reduce((min, current) => Math.min(min, current), Infinity);
383
- const yMax = yValues.reduce((max, current) => Math.max(max, current), -Infinity);
384
- const yRange = yMax - yMin;
385
- // Set a very low absolute residual floor (e.g., 5% of the total range)
386
- const ABS_RESIDUAL_FLOOR = yRange * 0.05; // 5% of range
387
- if (effectiveDeviationMeasure < SMALL_TOLERANCE) {
388
- const maxResidual = finalResidualsForDetection.reduce((max, current) => Math.max(max, Math.abs(current)), 0);
389
- effectiveDeviationMeasure = maxResidual > SMALL_TOLERANCE ? maxResidual / (deviationThreshold + SMALL_TOLERANCE) : 0;
390
- }
391
- else if (isSmallSet) {
392
- // Aggressively reduce the spread measure for small sets with non-zero MAD
393
- effectiveDeviationMeasure = effectiveDeviationMeasure / 1.5;
394
- }
395
- const significantDeviations = [];
396
- // Detect Significant Deviations using the robust spread
397
- if (effectiveDeviationMeasure > SMALL_TOLERANCE) {
398
- for (const pointWithRes of pointsWithFinalResiduals) {
399
- const isSignificantByMAD = Math.abs(pointWithRes.residual) > deviationThreshold * effectiveDeviationMeasure;
400
- const isSignificantByFloor = Math.abs(pointWithRes.residual) > ABS_RESIDUAL_FLOOR;
401
- if (isSignificantByMAD || isSignificantByFloor) {
402
- significantDeviations.push(Object.assign(Object.assign({}, pointWithRes), { isSignificantlyHigh: pointWithRes.residual > 0, isSignificantlyLow: pointWithRes.residual < 0 }));
403
- }
404
- }
405
- }
406
- // Check for Absolute Maximum Inclusion
407
- const maxIsIncluded = significantDeviations.some(sd => sd.y === yMax);
408
- if (!maxIsIncluded) {
409
- const maxPoint = allPoints.find(p => p.y === yMax);
410
- if (maxPoint) {
411
- // Flag the absolute max as a significant deviation if it was missed
412
- significantDeviations.push(Object.assign(Object.assign({}, maxPoint), { residual: maxPoint.y - (finalSlope * maxPoint.x + finalYIntercept), isSignificantlyHigh: true, isSignificantlyLow: false }));
413
- }
414
- }
415
- // Check for Absolute Minimum Inclusion
416
- const minIsIncluded = significantDeviations.some(sd => sd.y === yMin);
417
- if (!minIsIncluded) {
418
- const minPoint = allPoints.find(p => p.y === yMin);
419
- if (minPoint) {
420
- // Flag the absolute min as a significant deviation if it was missed
421
- significantDeviations.push(Object.assign(Object.assign({}, minPoint), { residual: minPoint.y - (finalSlope * minPoint.x + finalYIntercept), isSignificantlyHigh: false, isSignificantlyLow: true // It's the lowest point
422
- }));
423
- }
424
- }
425
- if (significantDeviations.length === 0) {
426
- return null;
427
- }
428
- let summary = "";
429
- const highestPoints = significantDeviations.filter(sd => sd.isSignificantlyHigh);
430
- const lowestPoints = significantDeviations.filter(sd => sd.isSignificantlyLow);
431
- const MAX_POINTS_TO_REPORT = 5;
432
- if (highestPoints.length > 0) {
433
- const uniqueHighestY = [...new Set(highestPoints.map(hp => hp.y))];
434
- uniqueHighestY.sort((a, b) => b - a);
435
- const limitedHighestY = uniqueHighestY.slice(0, MAX_POINTS_TO_REPORT);
436
- const formattedHighestY = limitedHighestY.map(y => (0, truncateDecimals_1.truncateDecimals)(y, decimalLength)).join(", ");
437
- summary += `${translate("Highest point(s):")} ${formattedHighestY}. `;
438
- }
439
- if (lowestPoints.length > 0) {
440
- const uniqueLowestY = [...new Set(lowestPoints.map(lp => lp.y))];
441
- uniqueLowestY.sort((a, b) => a - b);
442
- const limitedLowestY = uniqueLowestY.slice(0, MAX_POINTS_TO_REPORT);
443
- const formattedLowestY = limitedLowestY.map(y => (0, truncateDecimals_1.truncateDecimals)(y, decimalLength)).join(", ");
444
- summary += `${translate("Lowest point(s):")} ${formattedLowestY}. `;
445
- }
446
- return summary.trim();
444
+ });
445
+ const finalResidualsForDetection = pointsWithFinalResiduals.map(p => p.residual);
446
+ const robustResidualSpread = calculateMAD(finalResidualsForDetection);
447
+ const SMALL_TOLERANCE = 1e-9;
448
+ let effectiveDeviationMeasure = robustResidualSpread;
449
+ const isSmallSet = allPoints.length <= 5;
450
+ // Calculate the Y-range of the final data set for absolute thresholding
451
+ const yValues = allPoints.map(p => p.y);
452
+ const yMin = yValues.reduce((min, current) => Math.min(min, current), Infinity);
453
+ const yMax = yValues.reduce((max, current) => Math.max(max, current), -Infinity);
454
+ const yRange = yMax - yMin;
455
+ // Set a very low absolute residual floor (e.g., 5% of the total range)
456
+ const ABS_RESIDUAL_FLOOR = yRange * 0.05; // 5% of range
457
+ if (effectiveDeviationMeasure < SMALL_TOLERANCE) {
458
+ const maxResidual = finalResidualsForDetection.reduce((max, current) => Math.max(max, Math.abs(current)), 0);
459
+ effectiveDeviationMeasure = maxResidual > SMALL_TOLERANCE ? maxResidual / (deviationThreshold + SMALL_TOLERANCE) : 0;
460
+ } else if (isSmallSet) {
461
+ // Aggressively reduce the spread measure for small sets with non-zero MAD
462
+ effectiveDeviationMeasure = effectiveDeviationMeasure / 1.5;
463
+ }
464
+ const significantDeviations = [];
465
+ // Detect Significant Deviations using the robust spread
466
+ if (effectiveDeviationMeasure > SMALL_TOLERANCE) {
467
+ for (const pointWithRes of pointsWithFinalResiduals) {
468
+ const isSignificantByMAD = Math.abs(pointWithRes.residual) > deviationThreshold * effectiveDeviationMeasure;
469
+ const isSignificantByFloor = Math.abs(pointWithRes.residual) > ABS_RESIDUAL_FLOOR;
470
+ if (isSignificantByMAD || isSignificantByFloor) {
471
+ significantDeviations.push(Object.assign(Object.assign({}, pointWithRes), {
472
+ isSignificantlyHigh: pointWithRes.residual > 0,
473
+ isSignificantlyLow: pointWithRes.residual < 0
474
+ }));
475
+ }
476
+ }
477
+ }
478
+ // Check for Absolute Maximum Inclusion
479
+ const maxIsIncluded = significantDeviations.some(sd => sd.y === yMax);
480
+ if (!maxIsIncluded) {
481
+ const maxPoint = allPoints.find(p => p.y === yMax);
482
+ if (maxPoint) {
483
+ // Flag the absolute max as a significant deviation if it was missed
484
+ significantDeviations.push(Object.assign(Object.assign({}, maxPoint), {
485
+ residual: maxPoint.y - (finalSlope * maxPoint.x + finalYIntercept),
486
+ isSignificantlyHigh: true,
487
+ isSignificantlyLow: false
488
+ }));
489
+ }
490
+ }
491
+ // Check for Absolute Minimum Inclusion
492
+ const minIsIncluded = significantDeviations.some(sd => sd.y === yMin);
493
+ if (!minIsIncluded) {
494
+ const minPoint = allPoints.find(p => p.y === yMin);
495
+ if (minPoint) {
496
+ // Flag the absolute min as a significant deviation if it was missed
497
+ significantDeviations.push(Object.assign(Object.assign({}, minPoint), {
498
+ residual: minPoint.y - (finalSlope * minPoint.x + finalYIntercept),
499
+ isSignificantlyHigh: false,
500
+ isSignificantlyLow: true // It's the lowest point
501
+ }));
502
+ }
503
+ }
504
+ if (significantDeviations.length === 0) {
505
+ return null;
506
+ }
507
+ let summary = "";
508
+ const highestPoints = significantDeviations.filter(sd => sd.isSignificantlyHigh);
509
+ const lowestPoints = significantDeviations.filter(sd => sd.isSignificantlyLow);
510
+ const MAX_POINTS_TO_REPORT = 5;
511
+ if (highestPoints.length > 0) {
512
+ const uniqueHighestY = [...new Set(highestPoints.map(hp => hp.y))];
513
+ uniqueHighestY.sort((a, b) => b - a);
514
+ const limitedHighestY = uniqueHighestY.slice(0, MAX_POINTS_TO_REPORT);
515
+ const formattedHighestY = limitedHighestY.map(y => (0, truncateDecimals_1.truncateDecimals)(y, decimalLength)).join(", ");
516
+ summary += `${translate("Highest point(s):")} ${formattedHighestY}. `;
517
+ }
518
+ if (lowestPoints.length > 0) {
519
+ const uniqueLowestY = [...new Set(lowestPoints.map(lp => lp.y))];
520
+ uniqueLowestY.sort((a, b) => a - b);
521
+ const limitedLowestY = uniqueLowestY.slice(0, MAX_POINTS_TO_REPORT);
522
+ const formattedLowestY = limitedLowestY.map(y => (0, truncateDecimals_1.truncateDecimals)(y, decimalLength)).join(", ");
523
+ summary += `${translate("Lowest point(s):")} ${formattedLowestY}. `;
524
+ }
525
+ return summary.trim();
447
526
  }
448
527
  function calculateNumberOfSegments(points) {
449
- const minPointsForSegmentation = 50;
450
- const maxSegments = 8;
451
- const base = 5;
452
- if (points.length <= minPointsForSegmentation) {
453
- return 1;
454
- }
455
- const calculatedSegments = Math.floor(base * Math.log(points.length));
456
- return Math.min(calculatedSegments, maxSegments);
528
+ const minPointsForSegmentation = 50;
529
+ const maxSegments = 8;
530
+ const base = 5;
531
+ if (points.length <= minPointsForSegmentation) {
532
+ return 1;
533
+ }
534
+ const calculatedSegments = Math.floor(base * Math.log(points.length));
535
+ return Math.min(calculatedSegments, maxSegments);
457
536
  }
458
537
  function splitIntoSegments(points) {
459
- const numSegments = calculateNumberOfSegments(points);
460
- if (numSegments === 1) {
461
- return [points];
462
- }
463
- const segments = [];
464
- const segmentSize = Math.floor(points.length / numSegments);
465
- const remainder = points.length % numSegments;
466
- let startIndex = 0;
467
- for (let i = 0; i < numSegments; i++) {
468
- const currentSegmentSize = segmentSize + (i < remainder ? 1 : 0);
469
- const endIndex = startIndex + currentSegmentSize;
470
- segments.push(points.slice(startIndex, endIndex));
471
- startIndex = endIndex;
472
- }
473
- return segments;
538
+ const numSegments = calculateNumberOfSegments(points);
539
+ if (numSegments === 1) {
540
+ return [points];
541
+ }
542
+ const segments = [];
543
+ const segmentSize = Math.floor(points.length / numSegments);
544
+ const remainder = points.length % numSegments;
545
+ let startIndex = 0;
546
+ for (let i = 0; i < numSegments; i++) {
547
+ const currentSegmentSize = segmentSize + (i < remainder ? 1 : 0);
548
+ const endIndex = startIndex + currentSegmentSize;
549
+ segments.push(points.slice(startIndex, endIndex));
550
+ startIndex = endIndex;
551
+ }
552
+ return segments;
474
553
  }
475
554
  function detectComplexTrend(allPoints, datasetName, decimalLength, translate) {
476
- const segments = splitIntoSegments(allPoints);
477
- const segmentTrends = segments.map(segment => calculateLinearRegression(segment));
478
- const trendDirections = segmentTrends.map(trend => getTrendDirectionBySlope(trend.slope));
479
- const isComplex = new Set(trendDirections).size > 1;
480
- if (isComplex) {
481
- const summaryParts = trendDirections.map((direction, index) => {
482
- const startPoint = segments[index][0];
483
- const endPoint = segments[index][segments[index].length - 1];
484
- return translate(`Segment {INDEX} {DIRECTION} from {FROM} at {X0} to {TO} at {X}.`)
485
- .replace("{INDEX}", (index + 1).toString())
486
- .replace("{DIRECTION}", direction)
487
- .replace("{FROM}", (0, truncateDecimals_1.truncateDecimals)(startPoint.y, decimalLength).toString())
488
- .replace("{TO}", (0, truncateDecimals_1.truncateDecimals)(endPoint.y, decimalLength).toString())
489
- .replace("{X0}", startPoint.originX.toString())
490
- .replace("{X}", endPoint.originX.toString());
491
- });
492
- const complexSummary = `${datasetName} ${translate("shows a complex trend with multiple segments:")} ${summaryParts.join(" ")}`;
493
- return complexSummary;
494
- }
495
- return false;
555
+ const segments = splitIntoSegments(allPoints);
556
+ const segmentTrends = segments.map(segment => calculateLinearRegression(segment));
557
+ const trendDirections = segmentTrends.map(trend => getTrendDirectionBySlope(trend.slope));
558
+ const isComplex = new Set(trendDirections).size > 1;
559
+ if (isComplex) {
560
+ const summaryParts = trendDirections.map((direction, index) => {
561
+ const startPoint = segments[index][0];
562
+ const endPoint = segments[index][segments[index].length - 1];
563
+ return translate("Segment {INDEX} {DIRECTION} from {FROM} at {X0} to {TO} at {X}.").replace("{INDEX}", (index + 1).toString()).replace("{DIRECTION}", direction).replace("{FROM}", (0, truncateDecimals_1.truncateDecimals)(startPoint.y, decimalLength).toString()).replace("{TO}", (0, truncateDecimals_1.truncateDecimals)(endPoint.y, decimalLength).toString()).replace("{X0}", startPoint.originX.toString()).replace("{X}", endPoint.originX.toString());
564
+ });
565
+ const complexSummary = `${datasetName} ${translate("shows a complex trend with multiple segments:")} ${summaryParts.join(" ")}`;
566
+ return complexSummary;
567
+ }
568
+ return false;
496
569
  }
497
570
  function calculateAverageValue(points) {
498
- const yValues = points.map(point => point.y);
499
- const validNumbers = yValues.filter(n => typeof n === "number");
500
- if (validNumbers.length === 0) {
501
- return null;
502
- }
503
- const sum = validNumbers.reduce((total, current) => total + current, 0);
504
- return sum / validNumbers.length;
571
+ const yValues = points.map(point => point.y);
572
+ const validNumbers = yValues.filter(n => typeof n === "number");
573
+ if (validNumbers.length === 0) {
574
+ return null;
575
+ }
576
+ const sum = validNumbers.reduce((total, current) => total + current, 0);
577
+ return sum / validNumbers.length;
505
578
  }
506
579
  function detectDatasetTrend(dataset, translate, dateFormatter, miniChartLabels, options) {
507
- const datasetName = dataset.label || translate("Data");
508
- const twoState = detectTwoStateChart(dataset, translate, dateFormatter, miniChartLabels, options);
509
- if (twoState) {
510
- return { trendDirection: "flat", summary: twoState };
511
- }
512
- const datasetObj = Object.assign({}, dataset);
513
- if (!miniChartLabels) {
514
- // simplify the data before trend detection
515
- datasetObj.data = simplifyData(datasetObj.data);
516
- }
517
- const allPoints = collectAllPoints(datasetObj, dateFormatter, miniChartLabels, options);
518
- if (allPoints.length === 0) {
519
- return { trendDirection: "undefined", summary: translate("No data available") };
520
- }
521
- const allUniqueYValues = [...new Set(allPoints.map(p => p.y))];
522
- const decimalLength = (0, calculateMinTruncationPrecision_1.calculateMinTruncationPrecision)(allUniqueYValues);
523
- if (allPoints.length === 1) {
524
- return { trendDirection: "flat", summary: translate("Only one data point: value is {VALUE}.").replace("{VALUE}", (0, truncateDecimals_1.truncateDecimals)(allPoints[0].y, decimalLength).toString()) };
525
- }
526
- const complexTrend = detectComplexTrend(allPoints, datasetName, decimalLength, translate);
527
- if (complexTrend) {
528
- return { trendDirection: "complex", summary: complexTrend };
529
- }
530
- const { slope } = calculateLinearRegression(allPoints);
531
- let trendDirection = getTrendDirectionBySlope(slope);
532
- const firstPoint = allPoints[0];
533
- const lastPoint = allPoints[allPoints.length - 1];
534
- const yValues = allPoints.map(p => p.y);
535
- const yMin = yValues.reduce((min, current) => Math.min(min, current));
536
- const yMax = yValues.reduce((max, current) => Math.max(max, current));
537
- const yRange = yMax - yMin;
538
- const netChange = lastPoint.y - firstPoint.y;
539
- // A tolerance to decide if the net change is significant enough
540
- // to overrule a weak linear regression. (e.g., a 5% change of the total range).
541
- const NARRATIVE_TREND_THRESHOLD = 0.05;
542
- // If the linear regression detected a non-flat trend, check if it's strong enough.
543
- if (trendDirection !== "flat" && yRange > 1e-9) {
544
- const netChangeRatio = Math.abs(netChange / yRange);
545
- if (netChangeRatio < NARRATIVE_TREND_THRESHOLD) {
546
- trendDirection = "flat";
547
- }
548
- else {
549
- const netDirection = netChange > 1e-9 ? "increases" : "decreases";
550
- if (trendDirection !== netDirection) {
551
- trendDirection = netDirection;
552
- }
553
- }
554
- }
555
- let summary;
556
- if (trendDirection === "flat") {
557
- const averageValue = calculateAverageValue(allPoints);
558
- const averageString = averageValue ? ` ${translate("Average value is:")} ${(0, truncateDecimals_1.truncateDecimals)(averageValue, decimalLength)}` : "";
559
- const FLAT_TREND_TOLERANCE = 0.25;
560
- if (yMax - yMin < FLAT_TREND_TOLERANCE) {
561
- summary = `${datasetName} ${translate("shows a relatively flat or stable trend.")} ${averageString}`;
562
- }
563
- else {
564
- const formattedYMin = (0, truncateDecimals_1.truncateDecimals)(yMin, decimalLength);
565
- const formattedYMax = (0, truncateDecimals_1.truncateDecimals)(yMax, decimalLength);
566
- summary = `${datasetName} ${translate("value changes in the range from {MIN} to {MAX}.")
567
- .replace("{MIN}", formattedYMin.toString())
568
- .replace("{MAX}", formattedYMax.toString())}
580
+ const datasetName = dataset.label || translate("Data");
581
+ const twoState = detectTwoStateChart(dataset, translate, dateFormatter, miniChartLabels, options);
582
+ if (twoState) {
583
+ return {
584
+ trendDirection: "flat",
585
+ summary: twoState
586
+ };
587
+ }
588
+ const datasetObj = Object.assign({}, dataset);
589
+ if (!miniChartLabels) {
590
+ // simplify the data before trend detection
591
+ datasetObj.data = simplifyData(datasetObj.data);
592
+ }
593
+ const allPoints = collectAllPoints(datasetObj, dateFormatter, miniChartLabels, options);
594
+ if (allPoints.length === 0) {
595
+ return {
596
+ trendDirection: "undefined",
597
+ summary: translate("No data available")
598
+ };
599
+ }
600
+ const allUniqueYValues = [...new Set(allPoints.map(p => p.y))];
601
+ const decimalLength = (0, calculateMinTruncationPrecision_1.calculateMinTruncationPrecision)(allUniqueYValues);
602
+ if (allPoints.length === 1) {
603
+ return {
604
+ trendDirection: "flat",
605
+ summary: translate("Only one data point: value is {VALUE}.").replace("{VALUE}", (0, truncateDecimals_1.truncateDecimals)(allPoints[0].y, decimalLength).toString())
606
+ };
607
+ }
608
+ const complexTrend = detectComplexTrend(allPoints, datasetName, decimalLength, translate);
609
+ if (complexTrend) {
610
+ return {
611
+ trendDirection: "complex",
612
+ summary: complexTrend
613
+ };
614
+ }
615
+ const {
616
+ slope
617
+ } = calculateLinearRegression(allPoints);
618
+ let trendDirection = getTrendDirectionBySlope(slope);
619
+ const firstPoint = allPoints[0];
620
+ const lastPoint = allPoints[allPoints.length - 1];
621
+ const yValues = allPoints.map(p => p.y);
622
+ const yMin = yValues.reduce((min, current) => Math.min(min, current));
623
+ const yMax = yValues.reduce((max, current) => Math.max(max, current));
624
+ const yRange = yMax - yMin;
625
+ const netChange = lastPoint.y - firstPoint.y;
626
+ // A tolerance to decide if the net change is significant enough
627
+ // to overrule a weak linear regression. (e.g., a 5% change of the total range).
628
+ const NARRATIVE_TREND_THRESHOLD = 0.05;
629
+ // If the linear regression detected a non-flat trend, check if it's strong enough.
630
+ if (trendDirection !== "flat" && yRange > 1e-9) {
631
+ const netChangeRatio = Math.abs(netChange / yRange);
632
+ if (netChangeRatio < NARRATIVE_TREND_THRESHOLD) {
633
+ trendDirection = "flat";
634
+ } else {
635
+ const netDirection = netChange > 1e-9 ? "increases" : "decreases";
636
+ if (trendDirection !== netDirection) {
637
+ trendDirection = netDirection;
638
+ }
639
+ }
640
+ }
641
+ let summary;
642
+ if (trendDirection === "flat") {
643
+ const averageValue = calculateAverageValue(allPoints);
644
+ const averageString = averageValue ? ` ${translate("Average value is:")} ${(0, truncateDecimals_1.truncateDecimals)(averageValue, decimalLength)}` : "";
645
+ const FLAT_TREND_TOLERANCE = 0.25;
646
+ if (yMax - yMin < FLAT_TREND_TOLERANCE) {
647
+ summary = `${datasetName} ${translate("shows a relatively flat or stable trend.")} ${averageString}`;
648
+ } else {
649
+ const formattedYMin = (0, truncateDecimals_1.truncateDecimals)(yMin, decimalLength);
650
+ const formattedYMax = (0, truncateDecimals_1.truncateDecimals)(yMax, decimalLength);
651
+ summary = `${datasetName} ${translate("value changes in the range from {MIN} to {MAX}.").replace("{MIN}", formattedYMin.toString()).replace("{MAX}", formattedYMax.toString())}
569
652
  ${averageString}`;
570
- }
571
- }
572
- else {
573
- summary = `${datasetName} ${trendDirection} ${translate("from {FROM} at {X0} to {TO} at {X}.")
574
- .replace("{FROM}", (0, truncateDecimals_1.truncateDecimals)(firstPoint.y, decimalLength).toString())
575
- .replace("{TO}", (0, truncateDecimals_1.truncateDecimals)(lastPoint.y, decimalLength).toString())
576
- .replace("{X0}", firstPoint.originX.toString())
577
- .replace("{X}", lastPoint.originX.toString())}`;
578
- const significantDeviations = detectSignificantDeviations(allPoints, translate, decimalLength);
579
- if (significantDeviations && typeof significantDeviations === "string") {
580
- summary += ` ${significantDeviations}`;
581
- }
582
653
  }
583
- return { trendDirection, summary };
654
+ } else {
655
+ summary = `${datasetName} ${trendDirection} ${translate("from {FROM} at {X0} to {TO} at {X}.").replace("{FROM}", (0, truncateDecimals_1.truncateDecimals)(firstPoint.y, decimalLength).toString()).replace("{TO}", (0, truncateDecimals_1.truncateDecimals)(lastPoint.y, decimalLength).toString()).replace("{X0}", firstPoint.originX.toString()).replace("{X}", lastPoint.originX.toString())}`;
656
+ const significantDeviations = detectSignificantDeviations(allPoints, translate, decimalLength);
657
+ if (significantDeviations && typeof significantDeviations === "string") {
658
+ summary += ` ${significantDeviations}`;
659
+ }
660
+ }
661
+ return {
662
+ trendDirection,
663
+ summary
664
+ };
584
665
  }
585
- const AccessibleChartNarrative = ({ data, options }) => {
586
- const { translate } = (0, useLanguage_1.useLanguage)();
587
- const miniChartLabels = (0, react_1.useMemo)(() => data.labels, [data]);
588
- const { dateFormat, toLocalDateTime } = (0, react_1.useContext)(userFormatContext_1.userFormatContext);
589
- const dateFormatter = (0, react_1.useCallback)((d, format = dateFormat) => (0, formatDate_1.formatDate)(toLocalDateTime(d), format, translate), [toLocalDateTime, dateFormat, translate]);
590
- const filteredDatasets = (0, removeTrendDataFromDatasets_1.removeTrendDataFromDatasets)(data.datasets);
591
- const datasetsWithAnalysis = (0, react_1.useMemo)(() => filteredDatasets.map(dataset => {
592
- const datasetObj = Object.assign({}, dataset);
593
- try {
594
- const trend = detectDatasetTrend(datasetObj, translate, dateFormatter, miniChartLabels, options);
595
- return trend.summary;
596
- }
597
- catch (error) {
598
- const errMsg = `${translate("Error generating chart narrative for dataset")} ${dataset.label || ""}`;
599
- console.error(errMsg, error);
600
- return errMsg;
601
- }
602
- }), [filteredDatasets, translate, dateFormatter, miniChartLabels, options]);
603
- return (0, jsx_runtime_1.jsx)("div", { className: "screen-reader-only", children: datasetsWithAnalysis.map((analysis, index) => (0, jsx_runtime_1.jsx)("div", { children: analysis }, index)) });
666
+ const AccessibleChartNarrative = ({
667
+ data,
668
+ options
669
+ }) => {
670
+ const {
671
+ translate
672
+ } = (0, useLanguage_1.useLanguage)();
673
+ const miniChartLabels = (0, react_1.useMemo)(() => data.labels, [data]);
674
+ const {
675
+ dateFormat,
676
+ toLocalDateTime
677
+ } = (0, react_1.useContext)(userFormatContext_1.userFormatContext);
678
+ const dateFormatter = (0, react_1.useCallback)((d, format = dateFormat) => (0, formatDate_1.formatDate)(toLocalDateTime(d), format, translate), [toLocalDateTime, dateFormat, translate]);
679
+ const filteredDatasets = (0, removeTrendDataFromDatasets_1.removeTrendDataFromDatasets)(data.datasets);
680
+ const datasetsWithAnalysis = (0, react_1.useMemo)(() => filteredDatasets.map(dataset => {
681
+ const datasetObj = Object.assign({}, dataset);
682
+ try {
683
+ const trend = detectDatasetTrend(datasetObj, translate, dateFormatter, miniChartLabels, options);
684
+ return trend.summary;
685
+ } catch (error) {
686
+ const errMsg = `${translate("Error generating chart narrative for dataset")} ${dataset.label || ""}`;
687
+ console.error(errMsg, error);
688
+ return errMsg;
689
+ }
690
+ }), [filteredDatasets, translate, dateFormatter, miniChartLabels, options]);
691
+ return (0, jsx_runtime_1.jsx)("div", {
692
+ className: "screen-reader-only",
693
+ children: datasetsWithAnalysis.map((analysis, index) => (0, jsx_runtime_1.jsx)("div", {
694
+ children: analysis
695
+ }, index))
696
+ });
604
697
  };
605
- exports.AccessibleChartNarrative = AccessibleChartNarrative;
698
+ exports.AccessibleChartNarrative = AccessibleChartNarrative;