@buildcanada/charts 0.1.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 (404) hide show
  1. package/LICENSE.md +8 -0
  2. package/README.md +113 -0
  3. package/package.json +137 -0
  4. package/src/components/BodyPortal/BodyPortal.tsx +40 -0
  5. package/src/components/Button/Button.scss +110 -0
  6. package/src/components/Button/Button.tsx +101 -0
  7. package/src/components/Checkbox.scss +93 -0
  8. package/src/components/Checkbox.tsx +47 -0
  9. package/src/components/ExpandableToggle/ExpandableToggle.scss +123 -0
  10. package/src/components/ExpandableToggle/ExpandableToggle.tsx +60 -0
  11. package/src/components/GrapherTabIcon.tsx +156 -0
  12. package/src/components/GrapherTrendArrow.scss +16 -0
  13. package/src/components/GrapherTrendArrow.tsx +30 -0
  14. package/src/components/Halo/Halo.tsx +44 -0
  15. package/src/components/LabeledSwitch/LabeledSwitch.scss +109 -0
  16. package/src/components/LabeledSwitch/LabeledSwitch.tsx +62 -0
  17. package/src/components/MarkdownTextWrap/MarkdownTextWrap.tsx +1173 -0
  18. package/src/components/OverlayHeader.scss +18 -0
  19. package/src/components/OverlayHeader.tsx +29 -0
  20. package/src/components/RadioButton.scss +69 -0
  21. package/src/components/RadioButton.tsx +42 -0
  22. package/src/components/SimpleMarkdownText.tsx +89 -0
  23. package/src/components/TextInput.scss +17 -0
  24. package/src/components/TextInput.tsx +19 -0
  25. package/src/components/TextWrap/TextWrap.tsx +361 -0
  26. package/src/components/TextWrap/TextWrapUtils.ts +32 -0
  27. package/src/components/closeButton/CloseButton.scss +40 -0
  28. package/src/components/closeButton/CloseButton.tsx +27 -0
  29. package/src/components/index.ts +70 -0
  30. package/src/components/loadingIndicator/LoadingIndicator.scss +40 -0
  31. package/src/components/loadingIndicator/LoadingIndicator.tsx +28 -0
  32. package/src/components/markdown/remarkPlainLinks.ts +36 -0
  33. package/src/components/reactUtil.ts +20 -0
  34. package/src/components/stubs/CodeSnippet.tsx +19 -0
  35. package/src/components/stubs/DataCitation.tsx +16 -0
  36. package/src/components/stubs/IndicatorKeyData.tsx +45 -0
  37. package/src/components/stubs/IndicatorProcessing.tsx +15 -0
  38. package/src/components/stubs/IndicatorSources.tsx +15 -0
  39. package/src/components/styles/colors.scss +113 -0
  40. package/src/components/styles/mixins.scss +630 -0
  41. package/src/components/styles/typography.scss +579 -0
  42. package/src/components/styles/util.scss +89 -0
  43. package/src/components/styles/variables.scss +208 -0
  44. package/src/config/ChartsConfig.ts +163 -0
  45. package/src/config/ChartsProvider.tsx +157 -0
  46. package/src/config/index.ts +20 -0
  47. package/src/core-table/CoreTable.ts +1355 -0
  48. package/src/core-table/CoreTableColumns.ts +973 -0
  49. package/src/core-table/CoreTableUtils.ts +793 -0
  50. package/src/core-table/ErrorValues.ts +73 -0
  51. package/src/core-table/OwidTable.ts +1175 -0
  52. package/src/core-table/OwidTableSynthesizers.ts +272 -0
  53. package/src/core-table/OwidTableUtil.ts +76 -0
  54. package/src/core-table/Transforms.ts +484 -0
  55. package/src/core-table/index.ts +82 -0
  56. package/src/explorer/ColumnGrammar.ts +217 -0
  57. package/src/explorer/Explorer.sample.ts +212 -0
  58. package/src/explorer/Explorer.scss +148 -0
  59. package/src/explorer/Explorer.tsx +1283 -0
  60. package/src/explorer/ExplorerConstants.ts +85 -0
  61. package/src/explorer/ExplorerControls.scss +156 -0
  62. package/src/explorer/ExplorerControls.tsx +210 -0
  63. package/src/explorer/ExplorerDecisionMatrix.ts +471 -0
  64. package/src/explorer/ExplorerGrammar.ts +161 -0
  65. package/src/explorer/ExplorerProgram.ts +568 -0
  66. package/src/explorer/ExplorerUtils.ts +59 -0
  67. package/src/explorer/GrapherGrammar.ts +387 -0
  68. package/src/explorer/gridLang/GrammarUtils.ts +121 -0
  69. package/src/explorer/gridLang/GridCell.ts +298 -0
  70. package/src/explorer/gridLang/GridLangConstants.ts +255 -0
  71. package/src/explorer/gridLang/GridProgram.ts +311 -0
  72. package/src/explorer/gridLang/readme.md +17 -0
  73. package/src/explorer/index.ts +69 -0
  74. package/src/explorer/readme.md +19 -0
  75. package/src/explorer/urlMigrations/CO2UrlMigration.ts +46 -0
  76. package/src/explorer/urlMigrations/CovidUrlMigration.ts +37 -0
  77. package/src/explorer/urlMigrations/EnergyUrlMigration.ts +41 -0
  78. package/src/explorer/urlMigrations/ExplorerPageUrlMigrationSpec.ts +12 -0
  79. package/src/explorer/urlMigrations/ExplorerUrlMigrationUtils.ts +45 -0
  80. package/src/explorer/urlMigrations/ExplorerUrlMigrations.ts +33 -0
  81. package/src/explorer/urlMigrations/LegacyCovidUrlMigration.ts +144 -0
  82. package/src/explorer/urlMigrations/readme.md +39 -0
  83. package/src/grapher/axis/Axis.ts +973 -0
  84. package/src/grapher/axis/AxisConfig.ts +179 -0
  85. package/src/grapher/axis/AxisViews.tsx +597 -0
  86. package/src/grapher/barCharts/DiscreteBarChart.tsx +728 -0
  87. package/src/grapher/barCharts/DiscreteBarChartConstants.ts +60 -0
  88. package/src/grapher/barCharts/DiscreteBarChartHelpers.ts +338 -0
  89. package/src/grapher/barCharts/DiscreteBarChartState.ts +354 -0
  90. package/src/grapher/barCharts/DiscreteBarChartThumbnail.tsx +34 -0
  91. package/src/grapher/captionedChart/CaptionedChart.scss +61 -0
  92. package/src/grapher/captionedChart/CaptionedChart.tsx +523 -0
  93. package/src/grapher/captionedChart/Logos.tsx +141 -0
  94. package/src/grapher/captionedChart/LogosSVG.tsx +16 -0
  95. package/src/grapher/captionedChart/StaticChartRasterizer.tsx +178 -0
  96. package/src/grapher/captionedChart/assets/buildcanada-logo-square.svg +15 -0
  97. package/src/grapher/captionedChart/assets/buildcanada-logo.svg +15 -0
  98. package/src/grapher/captionedChart/assets/canadaspends.svg +7 -0
  99. package/src/grapher/captionedChart/readme.md +14 -0
  100. package/src/grapher/chart/Chart.tsx +62 -0
  101. package/src/grapher/chart/ChartAreaContent.tsx +172 -0
  102. package/src/grapher/chart/ChartDimension.ts +121 -0
  103. package/src/grapher/chart/ChartInterface.ts +83 -0
  104. package/src/grapher/chart/ChartManager.ts +113 -0
  105. package/src/grapher/chart/ChartTabs.ts +178 -0
  106. package/src/grapher/chart/ChartTypeMap.tsx +158 -0
  107. package/src/grapher/chart/ChartTypeSwitcher.tsx +26 -0
  108. package/src/grapher/chart/ChartUtils.tsx +364 -0
  109. package/src/grapher/chart/DimensionSlot.ts +45 -0
  110. package/src/grapher/chart/StaticChartWrapper.tsx +94 -0
  111. package/src/grapher/chart/guidedChartUtils.ts +82 -0
  112. package/src/grapher/color/BinningStrategies.ts +484 -0
  113. package/src/grapher/color/BinningStrategyEqualSizeBins.ts +132 -0
  114. package/src/grapher/color/BinningStrategyLogarithmic.ts +121 -0
  115. package/src/grapher/color/CategoricalColorAssigner.ts +97 -0
  116. package/src/grapher/color/ColorBrewerSchemes.ts +80 -0
  117. package/src/grapher/color/ColorConstants.ts +20 -0
  118. package/src/grapher/color/ColorScale.ts +339 -0
  119. package/src/grapher/color/ColorScaleBin.ts +147 -0
  120. package/src/grapher/color/ColorScaleConfig.ts +204 -0
  121. package/src/grapher/color/ColorScheme.ts +137 -0
  122. package/src/grapher/color/ColorSchemes.ts +149 -0
  123. package/src/grapher/color/ColorUtils.ts +86 -0
  124. package/src/grapher/color/CustomSchemes.ts +1772 -0
  125. package/src/grapher/color/readme.md +84 -0
  126. package/src/grapher/comparisonLine/ComparisonLine.tsx +31 -0
  127. package/src/grapher/comparisonLine/ComparisonLineConstants.ts +11 -0
  128. package/src/grapher/comparisonLine/ComparisonLineGenerator.ts +60 -0
  129. package/src/grapher/comparisonLine/ComparisonLineHelpers.ts +10 -0
  130. package/src/grapher/comparisonLine/CustomComparisonLine.tsx +159 -0
  131. package/src/grapher/comparisonLine/VerticalComparisonLine.tsx +208 -0
  132. package/src/grapher/controls/ActionButtons.scss +97 -0
  133. package/src/grapher/controls/ActionButtons.tsx +453 -0
  134. package/src/grapher/controls/CommandPalette.scss +50 -0
  135. package/src/grapher/controls/CommandPalette.tsx +74 -0
  136. package/src/grapher/controls/ContentSwitchers.scss +93 -0
  137. package/src/grapher/controls/ContentSwitchers.tsx +238 -0
  138. package/src/grapher/controls/Controls.scss +158 -0
  139. package/src/grapher/controls/DataTableFilterDropdown.scss +7 -0
  140. package/src/grapher/controls/DataTableFilterDropdown.tsx +168 -0
  141. package/src/grapher/controls/DataTableSearchField.scss +3 -0
  142. package/src/grapher/controls/DataTableSearchField.tsx +76 -0
  143. package/src/grapher/controls/Dropdown.scss +252 -0
  144. package/src/grapher/controls/Dropdown.tsx +235 -0
  145. package/src/grapher/controls/EntitySelectionToggle.tsx +135 -0
  146. package/src/grapher/controls/MapRegionDropdown.scss +3 -0
  147. package/src/grapher/controls/MapRegionDropdown.tsx +104 -0
  148. package/src/grapher/controls/MapResetButton.tsx +115 -0
  149. package/src/grapher/controls/MapZoomDropdown.scss +9 -0
  150. package/src/grapher/controls/MapZoomDropdown.tsx +270 -0
  151. package/src/grapher/controls/MapZoomToSelectionButton.tsx +87 -0
  152. package/src/grapher/controls/SearchField.scss +78 -0
  153. package/src/grapher/controls/SearchField.tsx +63 -0
  154. package/src/grapher/controls/SettingsMenu.scss +191 -0
  155. package/src/grapher/controls/SettingsMenu.tsx +399 -0
  156. package/src/grapher/controls/ShareMenu.scss +58 -0
  157. package/src/grapher/controls/ShareMenu.tsx +304 -0
  158. package/src/grapher/controls/SortIcon.tsx +39 -0
  159. package/src/grapher/controls/VerticalScrollContainer.tsx +263 -0
  160. package/src/grapher/controls/controlsRow/ControlsRow.tsx +168 -0
  161. package/src/grapher/controls/dropdown-icons.scss +4 -0
  162. package/src/grapher/controls/entityPicker/EntityPicker.scss +255 -0
  163. package/src/grapher/controls/entityPicker/EntityPicker.tsx +816 -0
  164. package/src/grapher/controls/entityPicker/EntityPickerConstants.ts +23 -0
  165. package/src/grapher/controls/globalEntitySelector/GlobalEntitySelector.scss +129 -0
  166. package/src/grapher/controls/globalEntitySelector/GlobalEntitySelector.tsx +463 -0
  167. package/src/grapher/controls/globalEntitySelector/GlobalEntitySelectorConstants.ts +3 -0
  168. package/src/grapher/controls/globalEntitySelector/readme.md +17 -0
  169. package/src/grapher/controls/settings/AbsRelToggle.tsx +64 -0
  170. package/src/grapher/controls/settings/AxisScaleToggle.tsx +53 -0
  171. package/src/grapher/controls/settings/FacetStrategySelector.tsx +110 -0
  172. package/src/grapher/controls/settings/FacetYDomainToggle.tsx +51 -0
  173. package/src/grapher/controls/settings/NoDataAreaToggle.tsx +38 -0
  174. package/src/grapher/controls/settings/ZoomToggle.tsx +36 -0
  175. package/src/grapher/core/EntitiesByRegionType.ts +174 -0
  176. package/src/grapher/core/EntityCodes.ts +19 -0
  177. package/src/grapher/core/EntityUrlBuilder.ts +200 -0
  178. package/src/grapher/core/FetchingGrapher.tsx +156 -0
  179. package/src/grapher/core/Grapher.tsx +760 -0
  180. package/src/grapher/core/GrapherAnalytics.ts +229 -0
  181. package/src/grapher/core/GrapherConstants.ts +173 -0
  182. package/src/grapher/core/GrapherState.tsx +3659 -0
  183. package/src/grapher/core/GrapherUrl.ts +184 -0
  184. package/src/grapher/core/GrapherUrlMigrations.ts +29 -0
  185. package/src/grapher/core/GrapherUseHelpers.tsx +147 -0
  186. package/src/grapher/core/LegacyToOwidTable.ts +841 -0
  187. package/src/grapher/core/grapher.entry.ts +5 -0
  188. package/src/grapher/core/grapher.scss +257 -0
  189. package/src/grapher/core/loadGrapherTableHelpers.ts +116 -0
  190. package/src/grapher/core/loadVariable.ts +104 -0
  191. package/src/grapher/core/relatedQuestion.ts +12 -0
  192. package/src/grapher/core/typography.scss +206 -0
  193. package/src/grapher/dataTable/DataTable.sample.ts +206 -0
  194. package/src/grapher/dataTable/DataTable.scss +249 -0
  195. package/src/grapher/dataTable/DataTable.tsx +1332 -0
  196. package/src/grapher/dataTable/DataTableConstants.ts +186 -0
  197. package/src/grapher/entitySelector/EntitySelector.scss +255 -0
  198. package/src/grapher/entitySelector/EntitySelector.tsx +1838 -0
  199. package/src/grapher/facet/FacetChart.tsx +943 -0
  200. package/src/grapher/facet/FacetChartConstants.ts +24 -0
  201. package/src/grapher/facet/FacetChartUtils.ts +51 -0
  202. package/src/grapher/facet/FacetMap.tsx +604 -0
  203. package/src/grapher/facet/FacetMapConstants.ts +23 -0
  204. package/src/grapher/facet/readme.md +13 -0
  205. package/src/grapher/focus/FocusArray.ts +79 -0
  206. package/src/grapher/footer/Footer.scss +63 -0
  207. package/src/grapher/footer/Footer.tsx +809 -0
  208. package/src/grapher/footer/FooterManager.ts +44 -0
  209. package/src/grapher/fullScreen/FullScreen.scss +11 -0
  210. package/src/grapher/fullScreen/FullScreen.tsx +61 -0
  211. package/src/grapher/header/Header.scss +35 -0
  212. package/src/grapher/header/Header.tsx +372 -0
  213. package/src/grapher/header/HeaderManager.ts +28 -0
  214. package/src/grapher/index.ts +157 -0
  215. package/src/grapher/interaction/InteractionState.ts +60 -0
  216. package/src/grapher/legend/HorizontalColorLegends.tsx +923 -0
  217. package/src/grapher/legend/LegendInteractionState.ts +40 -0
  218. package/src/grapher/legend/VerticalColorLegend.tsx +295 -0
  219. package/src/grapher/lineCharts/LineChart.tsx +968 -0
  220. package/src/grapher/lineCharts/LineChartConstants.ts +89 -0
  221. package/src/grapher/lineCharts/LineChartHelpers.ts +184 -0
  222. package/src/grapher/lineCharts/LineChartState.ts +394 -0
  223. package/src/grapher/lineCharts/LineChartThumbnail.tsx +437 -0
  224. package/src/grapher/lineCharts/Lines.tsx +258 -0
  225. package/src/grapher/lineLegend/LineLegend.tsx +723 -0
  226. package/src/grapher/lineLegend/LineLegendConstants.ts +9 -0
  227. package/src/grapher/lineLegend/LineLegendFilterAlgorithms.ts +143 -0
  228. package/src/grapher/lineLegend/LineLegendHelpers.ts +253 -0
  229. package/src/grapher/lineLegend/LineLegendTypes.ts +32 -0
  230. package/src/grapher/mapCharts/CanadaTopology.ts +17922 -0
  231. package/src/grapher/mapCharts/ChoroplethGlobe.tsx +949 -0
  232. package/src/grapher/mapCharts/ChoroplethMap.tsx +662 -0
  233. package/src/grapher/mapCharts/GeoFeatures.ts +184 -0
  234. package/src/grapher/mapCharts/GlobeController.ts +496 -0
  235. package/src/grapher/mapCharts/MapAnnotationPlacements.json +1040 -0
  236. package/src/grapher/mapCharts/MapAnnotationPlacements.ts +31 -0
  237. package/src/grapher/mapCharts/MapAnnotations.ts +723 -0
  238. package/src/grapher/mapCharts/MapChart.sample.ts +59 -0
  239. package/src/grapher/mapCharts/MapChart.scss +5 -0
  240. package/src/grapher/mapCharts/MapChart.tsx +720 -0
  241. package/src/grapher/mapCharts/MapChartConstants.ts +260 -0
  242. package/src/grapher/mapCharts/MapChartState.ts +416 -0
  243. package/src/grapher/mapCharts/MapChartThumbnail.tsx +25 -0
  244. package/src/grapher/mapCharts/MapComponents.tsx +338 -0
  245. package/src/grapher/mapCharts/MapConfig.ts +156 -0
  246. package/src/grapher/mapCharts/MapHelpers.ts +181 -0
  247. package/src/grapher/mapCharts/MapProjections.ts +49 -0
  248. package/src/grapher/mapCharts/MapSparkline.tsx +257 -0
  249. package/src/grapher/mapCharts/MapTooltip.scss +49 -0
  250. package/src/grapher/mapCharts/MapTooltip.tsx +409 -0
  251. package/src/grapher/mapCharts/MapTopology.ts +1766 -0
  252. package/src/grapher/mapCharts/d3-bboxCollide.js +204 -0
  253. package/src/grapher/mapCharts/d3-geo-projection.ts +198 -0
  254. package/src/grapher/modal/DownloadIcons.tsx +39 -0
  255. package/src/grapher/modal/DownloadModal.scss +300 -0
  256. package/src/grapher/modal/DownloadModal.tsx +1226 -0
  257. package/src/grapher/modal/EmbedModal.scss +40 -0
  258. package/src/grapher/modal/EmbedModal.tsx +160 -0
  259. package/src/grapher/modal/EntitySelectorModal.tsx +59 -0
  260. package/src/grapher/modal/Modal.scss +31 -0
  261. package/src/grapher/modal/Modal.tsx +90 -0
  262. package/src/grapher/modal/ModalHeader.scss +12 -0
  263. package/src/grapher/modal/ModalHeader.tsx +16 -0
  264. package/src/grapher/modal/SourcesDescriptions.scss +87 -0
  265. package/src/grapher/modal/SourcesDescriptions.tsx +89 -0
  266. package/src/grapher/modal/SourcesKeyDataTable.scss +49 -0
  267. package/src/grapher/modal/SourcesKeyDataTable.tsx +87 -0
  268. package/src/grapher/modal/SourcesModal.scss +301 -0
  269. package/src/grapher/modal/SourcesModal.tsx +568 -0
  270. package/src/grapher/noDataModal/NoDataModal.tsx +125 -0
  271. package/src/grapher/scatterCharts/ConnectedScatterLegend.tsx +143 -0
  272. package/src/grapher/scatterCharts/MultiColorPolyline.tsx +129 -0
  273. package/src/grapher/scatterCharts/NoDataSection.scss +14 -0
  274. package/src/grapher/scatterCharts/NoDataSection.tsx +56 -0
  275. package/src/grapher/scatterCharts/ScatterPlotChart.tsx +792 -0
  276. package/src/grapher/scatterCharts/ScatterPlotChartConstants.ts +157 -0
  277. package/src/grapher/scatterCharts/ScatterPlotChartState.ts +678 -0
  278. package/src/grapher/scatterCharts/ScatterPlotChartThumbnail.tsx +155 -0
  279. package/src/grapher/scatterCharts/ScatterPlotTooltip.tsx +560 -0
  280. package/src/grapher/scatterCharts/ScatterPoints.tsx +153 -0
  281. package/src/grapher/scatterCharts/ScatterPointsWithLabels.tsx +708 -0
  282. package/src/grapher/scatterCharts/ScatterSizeLegend.tsx +327 -0
  283. package/src/grapher/scatterCharts/ScatterUtils.ts +265 -0
  284. package/src/grapher/scatterCharts/Triangle.tsx +41 -0
  285. package/src/grapher/schema/README.md +33 -0
  286. package/src/grapher/schema/defaultGrapherConfig.ts +100 -0
  287. package/src/grapher/schema/grapher-schema.009.yaml +781 -0
  288. package/src/grapher/schema/migrations/helpers.ts +58 -0
  289. package/src/grapher/schema/migrations/migrate.ts +75 -0
  290. package/src/grapher/schema/migrations/migrations.ts +158 -0
  291. package/src/grapher/selection/MapSelectionArray.ts +99 -0
  292. package/src/grapher/selection/SelectionArray.ts +71 -0
  293. package/src/grapher/selection/readme.md +16 -0
  294. package/src/grapher/sidePanel/SidePanel.scss +10 -0
  295. package/src/grapher/sidePanel/SidePanel.tsx +23 -0
  296. package/src/grapher/slideInDrawer/SlideInDrawer.scss +57 -0
  297. package/src/grapher/slideInDrawer/SlideInDrawer.tsx +125 -0
  298. package/src/grapher/slideshowController/SlideShowController.tsx +43 -0
  299. package/src/grapher/slideshowController/readme.md +7 -0
  300. package/src/grapher/slopeCharts/MarkX.tsx +45 -0
  301. package/src/grapher/slopeCharts/Slope.tsx +102 -0
  302. package/src/grapher/slopeCharts/SlopeChart.tsx +1152 -0
  303. package/src/grapher/slopeCharts/SlopeChartConstants.ts +33 -0
  304. package/src/grapher/slopeCharts/SlopeChartHelpers.ts +73 -0
  305. package/src/grapher/slopeCharts/SlopeChartState.ts +392 -0
  306. package/src/grapher/slopeCharts/SlopeChartThumbnail.tsx +368 -0
  307. package/src/grapher/stackedCharts/AbstractStackedChartState.ts +370 -0
  308. package/src/grapher/stackedCharts/MarimekkoBars.tsx +190 -0
  309. package/src/grapher/stackedCharts/MarimekkoBarsForOneEntity.tsx +168 -0
  310. package/src/grapher/stackedCharts/MarimekkoChart.tsx +1144 -0
  311. package/src/grapher/stackedCharts/MarimekkoChartConstants.ts +112 -0
  312. package/src/grapher/stackedCharts/MarimekkoChartHelpers.ts +21 -0
  313. package/src/grapher/stackedCharts/MarimekkoChartState.ts +465 -0
  314. package/src/grapher/stackedCharts/MarimekkoChartThumbnail.tsx +168 -0
  315. package/src/grapher/stackedCharts/MarimekkoInternalLabels.tsx +124 -0
  316. package/src/grapher/stackedCharts/StackedAreaChart.tsx +678 -0
  317. package/src/grapher/stackedCharts/StackedAreaChartState.ts +34 -0
  318. package/src/grapher/stackedCharts/StackedAreaChartThumbnail.tsx +215 -0
  319. package/src/grapher/stackedCharts/StackedAreas.tsx +223 -0
  320. package/src/grapher/stackedCharts/StackedBarChart.tsx +619 -0
  321. package/src/grapher/stackedCharts/StackedBarChartState.ts +80 -0
  322. package/src/grapher/stackedCharts/StackedBarChartThumbnail.tsx +220 -0
  323. package/src/grapher/stackedCharts/StackedBarSegment.tsx +87 -0
  324. package/src/grapher/stackedCharts/StackedBars.tsx +102 -0
  325. package/src/grapher/stackedCharts/StackedConstants.ts +109 -0
  326. package/src/grapher/stackedCharts/StackedDiscreteBarChart.tsx +270 -0
  327. package/src/grapher/stackedCharts/StackedDiscreteBarChartState.ts +296 -0
  328. package/src/grapher/stackedCharts/StackedDiscreteBarChartThumbnail.tsx +27 -0
  329. package/src/grapher/stackedCharts/StackedDiscreteBars.tsx +648 -0
  330. package/src/grapher/stackedCharts/StackedUtils.ts +142 -0
  331. package/src/grapher/tabs/Tabs.scss +169 -0
  332. package/src/grapher/tabs/Tabs.tsx +54 -0
  333. package/src/grapher/tabs/TabsWithDropdown.scss +62 -0
  334. package/src/grapher/tabs/TabsWithDropdown.tsx +114 -0
  335. package/src/grapher/testData/OwidTestData.sample.ts +273 -0
  336. package/src/grapher/testData/OwidTestData.ts +64 -0
  337. package/src/grapher/timeline/TimelineComponent.scss +139 -0
  338. package/src/grapher/timeline/TimelineComponent.tsx +658 -0
  339. package/src/grapher/timeline/TimelineController.ts +368 -0
  340. package/src/grapher/timeline/readme.md +7 -0
  341. package/src/grapher/tooltip/Tooltip.scss +510 -0
  342. package/src/grapher/tooltip/Tooltip.tsx +294 -0
  343. package/src/grapher/tooltip/TooltipContents.tsx +383 -0
  344. package/src/grapher/tooltip/TooltipProps.ts +123 -0
  345. package/src/grapher/tooltip/TooltipState.ts +81 -0
  346. package/src/grapher/verticalLabels/VerticalLabels.tsx +31 -0
  347. package/src/grapher/verticalLabels/VerticalLabelsState.ts +154 -0
  348. package/src/index.ts +226 -0
  349. package/src/styles/charts.scss +15 -0
  350. package/src/types/NominalType.ts +30 -0
  351. package/src/types/OwidOrigin.ts +18 -0
  352. package/src/types/OwidSource.ts +9 -0
  353. package/src/types/OwidVariable.ts +133 -0
  354. package/src/types/OwidVariableDisplayConfigInterface.ts +49 -0
  355. package/src/types/analyticsTypes.ts +54 -0
  356. package/src/types/dbTypes/Tags.ts +11 -0
  357. package/src/types/domainTypes/Archive.ts +139 -0
  358. package/src/types/domainTypes/Author.ts +28 -0
  359. package/src/types/domainTypes/ContentGraph.ts +76 -0
  360. package/src/types/domainTypes/CoreTableTypes.ts +305 -0
  361. package/src/types/domainTypes/DeployStatus.ts +23 -0
  362. package/src/types/domainTypes/Layout.ts +34 -0
  363. package/src/types/domainTypes/Posts.ts +34 -0
  364. package/src/types/domainTypes/Search.ts +299 -0
  365. package/src/types/domainTypes/Site.ts +8 -0
  366. package/src/types/domainTypes/StaticViz.ts +64 -0
  367. package/src/types/domainTypes/Toc.ts +11 -0
  368. package/src/types/domainTypes/Tombstone.ts +19 -0
  369. package/src/types/domainTypes/Various.ts +79 -0
  370. package/src/types/gdocTypes/Gdoc.ts +280 -0
  371. package/src/types/grapherTypes/BinningStrategyTypes.ts +46 -0
  372. package/src/types/grapherTypes/GrapherConstants.ts +53 -0
  373. package/src/types/grapherTypes/GrapherTypes.ts +743 -0
  374. package/src/types/index.ts +316 -0
  375. package/src/types/wordpressTypes/WordpressTypes.ts +9 -0
  376. package/src/utils/Bounds.ts +439 -0
  377. package/src/utils/BrowserUtils.ts +12 -0
  378. package/src/utils/FuzzySearch.ts +74 -0
  379. package/src/utils/MultiDimDataPageConfig.ts +31 -0
  380. package/src/utils/OwidVariable.ts +82 -0
  381. package/src/utils/PointVector.ts +97 -0
  382. package/src/utils/PromiseCache.ts +36 -0
  383. package/src/utils/PromiseSwitcher.ts +52 -0
  384. package/src/utils/TimeBounds.ts +130 -0
  385. package/src/utils/Tippy.tsx +57 -0
  386. package/src/utils/Util.ts +2369 -0
  387. package/src/utils/archival/archivalDate.ts +48 -0
  388. package/src/utils/dayjs.ts +32 -0
  389. package/src/utils/formatValue.ts +242 -0
  390. package/src/utils/grapherConfigUtils.ts +81 -0
  391. package/src/utils/image.ts +225 -0
  392. package/src/utils/index.ts +318 -0
  393. package/src/utils/isPresent.ts +5 -0
  394. package/src/utils/metadataHelpers.ts +329 -0
  395. package/src/utils/persistable/Persistable.ts +82 -0
  396. package/src/utils/persistable/readme.md +50 -0
  397. package/src/utils/regions.json +5635 -0
  398. package/src/utils/regions.ts +463 -0
  399. package/src/utils/serializers.ts +16 -0
  400. package/src/utils/string.ts +42 -0
  401. package/src/utils/urls/Url.ts +195 -0
  402. package/src/utils/urls/UrlMigration.ts +10 -0
  403. package/src/utils/urls/UrlUtils.ts +54 -0
  404. package/src/utils/urls/readme.md +90 -0
@@ -0,0 +1,172 @@
1
+ import React from "react"
2
+ import { observer } from "mobx-react"
3
+ import { computed, makeObservable } from "mobx"
4
+ import {
5
+ Bounds,
6
+ GRAPHER_MAP_TYPE,
7
+ GrapherChartOrMapType,
8
+ makeIdForHumanConsumption,
9
+ } from "../../utils/index.js"
10
+ import { DataTable } from "../dataTable/DataTable"
11
+ import { CaptionedChartManager } from "../captionedChart/CaptionedChart"
12
+ import { LoadingIndicator } from "../../components/index.js"
13
+ import { FacetChart } from "../facet/FacetChart"
14
+ import { getChartSvgProps, NoDataPattern } from "./ChartUtils"
15
+ import { ChartComponent, makeChartState } from "./ChartTypeMap"
16
+ import { GRAPHER_CHART_AREA_CLASS } from "../core/GrapherConstants"
17
+ import { ChartState } from "./ChartInterface"
18
+ import { FacetMap } from "../facet/FacetMap.js"
19
+
20
+ interface ChartAreaContentProps {
21
+ manager: CaptionedChartManager
22
+ bounds: Bounds
23
+ padWidth?: number
24
+ }
25
+
26
+ @observer
27
+ export class ChartAreaContent extends React.Component<ChartAreaContentProps> {
28
+ constructor(props: ChartAreaContentProps) {
29
+ super(props)
30
+ makeObservable(this)
31
+ }
32
+
33
+ @computed private get manager(): CaptionedChartManager {
34
+ return this.props.manager
35
+ }
36
+
37
+ @computed private get bounds(): Bounds {
38
+ return this.props.bounds.padWidth(this.props.padWidth ?? 0)
39
+ }
40
+
41
+ @computed private get activeChartOrMapType():
42
+ | GrapherChartOrMapType
43
+ | undefined {
44
+ const { manager } = this
45
+ if (manager.isOnTableTab) return undefined
46
+ if (manager.isOnMapTab) return GRAPHER_MAP_TYPE
47
+ if (manager.isOnChartTab) return manager.activeChartType
48
+ return undefined
49
+ }
50
+
51
+ private renderNoDataPattern(): React.ReactElement {
52
+ return (
53
+ <defs>
54
+ <NoDataPattern />
55
+ </defs>
56
+ )
57
+ }
58
+
59
+ @computed private get chartState(): ChartState | undefined {
60
+ if (!this.activeChartOrMapType) return undefined
61
+ return makeChartState(this.activeChartOrMapType, this.manager)
62
+ }
63
+
64
+ private renderLoadingIndicatorIntoSvg(): React.ReactElement {
65
+ return (
66
+ <foreignObject {...this.bounds.toProps()}>
67
+ <LoadingIndicator title={this.manager.whatAreWeWaitingFor} />
68
+ </foreignObject>
69
+ )
70
+ }
71
+
72
+ private renderReadyChartOrMap(): React.ReactElement | null {
73
+ const { bounds, manager, activeChartOrMapType, chartState } = this
74
+
75
+ if (!activeChartOrMapType) return null
76
+
77
+ if (manager.isFaceted)
78
+ return activeChartOrMapType === GRAPHER_MAP_TYPE ? (
79
+ <FacetMap bounds={bounds} manager={manager} />
80
+ ) : (
81
+ <FacetChart
82
+ bounds={bounds}
83
+ manager={manager}
84
+ chartTypeName={activeChartOrMapType}
85
+ />
86
+ )
87
+
88
+ if (!chartState) return null
89
+
90
+ return (
91
+ <ChartComponent
92
+ manager={manager}
93
+ chartType={activeChartOrMapType}
94
+ chartState={chartState}
95
+ variant={manager.variant}
96
+ bounds={bounds}
97
+ />
98
+ )
99
+ }
100
+
101
+ private renderChartOrMap(): React.ReactElement {
102
+ const { width, height } = this.props.bounds
103
+
104
+ const containerStyle: React.CSSProperties = {
105
+ position: "relative",
106
+ clear: "both",
107
+ height,
108
+ }
109
+
110
+ return (
111
+ <div style={containerStyle}>
112
+ <svg
113
+ {...getChartSvgProps(this.manager)}
114
+ width={width}
115
+ height={height}
116
+ viewBox={`0 0 ${width} ${height}`}
117
+ >
118
+ {this.renderNoDataPattern()}
119
+ {this.manager.isReady
120
+ ? this.renderReadyChartOrMap()
121
+ : this.renderLoadingIndicatorIntoSvg()}
122
+ </svg>
123
+ </div>
124
+ )
125
+ }
126
+
127
+ private renderDataTable(): React.ReactElement {
128
+ const { bounds } = this
129
+ const containerStyle: React.CSSProperties = {
130
+ position: "relative",
131
+ ...bounds.toCSS(),
132
+ }
133
+ return (
134
+ <div className="DataTableContainer" style={containerStyle}>
135
+ {this.manager.isReady ? (
136
+ <DataTable bounds={bounds} manager={this.manager} />
137
+ ) : (
138
+ <LoadingIndicator
139
+ title={this.manager.whatAreWeWaitingFor}
140
+ />
141
+ )}
142
+ </div>
143
+ )
144
+ }
145
+
146
+ renderStatic(): React.ReactElement | null {
147
+ // We cannot render a table to svg, but would rather display nothing at all to avoid issues.
148
+ // See https://github.com/owid/owid-grapher/issues/3283
149
+ if (this.manager.isOnTableTab) return null
150
+
151
+ return (
152
+ <g
153
+ id={makeIdForHumanConsumption(GRAPHER_CHART_AREA_CLASS)}
154
+ style={{ pointerEvents: "none" }}
155
+ >
156
+ {this.renderReadyChartOrMap()}
157
+ </g>
158
+ )
159
+ }
160
+
161
+ renderInteractive(): React.ReactElement | null {
162
+ return this.manager.isOnTableTab
163
+ ? this.renderDataTable()
164
+ : this.renderChartOrMap()
165
+ }
166
+
167
+ override render(): React.ReactElement | null {
168
+ return this.manager.isStatic
169
+ ? this.renderStatic()
170
+ : this.renderInteractive()
171
+ }
172
+ }
@@ -0,0 +1,121 @@
1
+ // Todo: remove this.
2
+ // Any display changes really can be computed columns. And then charts just need xColumnSlug, sizeColumnSlug, yColumnSlug (or yColumnSlugs) et cetera
3
+
4
+ import { observable, computed, makeObservable } from "mobx"
5
+ import {
6
+ trimObject,
7
+ ColumnSlug,
8
+ DimensionProperty,
9
+ OwidVariableId,
10
+ Persistable,
11
+ deleteRuntimeAndUnchangedProps,
12
+ updatePersistables,
13
+ OwidVariableDisplayConfig,
14
+ OwidChartDimensionInterface,
15
+ Time,
16
+ OwidChartDimensionInterfaceWithMandatorySlug,
17
+ } from "../../utils/index.js"
18
+ import { OwidTable, CoreColumn } from "../../core-table/index.js"
19
+
20
+ // A chart "dimension" represents a binding between a chart
21
+ // and a particular variable that it requests as data
22
+ class ChartDimensionDefaults implements OwidChartDimensionInterface {
23
+ property!: DimensionProperty
24
+ variableId!: OwidVariableId
25
+
26
+ // check on: malaria-deaths-comparisons and computing-efficiency
27
+
28
+ display = new OwidVariableDisplayConfig() // todo: make persistable
29
+
30
+ // XXX move this somewhere else, it's only used for scatter x override and Marimekko override
31
+ targetYear: Time | undefined = undefined
32
+
33
+ constructor() {
34
+ makeObservable(this, {
35
+ property: observable,
36
+ variableId: observable,
37
+ display: observable,
38
+ targetYear: observable,
39
+ })
40
+ }
41
+ }
42
+
43
+ // todo: remove when we remove dimensions
44
+ export interface LegacyDimensionsManager {
45
+ table: OwidTable
46
+ }
47
+
48
+ export function getDimensionColumnSlug(
49
+ variableId: OwidVariableId,
50
+ targetYear: Time | undefined
51
+ ): ColumnSlug {
52
+ if (targetYear) return `${variableId}-${targetYear}`
53
+ return variableId.toString()
54
+ }
55
+
56
+ export class ChartDimension
57
+ extends ChartDimensionDefaults
58
+ implements Persistable, OwidChartDimensionInterfaceWithMandatorySlug
59
+ {
60
+ private manager: LegacyDimensionsManager
61
+
62
+ constructor(
63
+ obj: OwidChartDimensionInterface,
64
+ manager: LegacyDimensionsManager
65
+ ) {
66
+ super()
67
+
68
+ makeObservable(this, {
69
+ _slug: observable,
70
+ })
71
+ this.manager = manager
72
+ if (obj) this.updateFromObject(obj)
73
+ }
74
+
75
+ @computed private get table(): OwidTable {
76
+ return this.manager.table
77
+ }
78
+
79
+ updateFromObject(obj: OwidChartDimensionInterface): void {
80
+ if (obj.display) updatePersistables(this, { display: obj.display })
81
+
82
+ this.targetYear = obj.targetYear
83
+ this.variableId = obj.variableId
84
+ this.property = obj.property
85
+ this.slug = obj.slug
86
+ }
87
+
88
+ toObject(): OwidChartDimensionInterface {
89
+ return trimObject(
90
+ deleteRuntimeAndUnchangedProps(
91
+ {
92
+ property: this.property,
93
+ variableId: this.variableId,
94
+ display: this.display,
95
+ targetYear: this.targetYear,
96
+ },
97
+ new ChartDimensionDefaults()
98
+ )
99
+ )
100
+ }
101
+
102
+ // Do not persist yet, until we migrate off VariableIds
103
+ _slug: ColumnSlug | undefined = undefined
104
+
105
+ @computed get slug(): ColumnSlug {
106
+ if (this._slug) return this._slug
107
+ return getDimensionColumnSlug(this.variableId, this.targetYear)
108
+ }
109
+
110
+ set slug(value: ColumnSlug | undefined) {
111
+ this._slug = value
112
+ }
113
+
114
+ @computed get column(): CoreColumn {
115
+ return this.table.get(this.columnSlug)
116
+ }
117
+
118
+ @computed get columnSlug(): string {
119
+ return this.slug ?? this.variableId.toString()
120
+ }
121
+ }
@@ -0,0 +1,83 @@
1
+ import { OwidTable } from "../../core-table/index.js"
2
+ import {
3
+ FacetStrategy,
4
+ SeriesName,
5
+ SeriesStrategy,
6
+ Color,
7
+ ChartErrorInfo,
8
+ } from "../../types/index.js"
9
+ import { ColorScale } from "../color/ColorScale"
10
+ import { HorizontalAxis, VerticalAxis } from "../axis/Axis"
11
+ import { HorizontalColorLegendManager } from "../legend/HorizontalColorLegends"
12
+ import { SelectionArray } from "../selection/SelectionArray"
13
+ import { FocusArray } from "../focus/FocusArray"
14
+
15
+ // The idea of this interface is to try and start reusing more code across our Chart classes and make it easier
16
+ // for a dev to work on a chart type they haven't touched before if they've worked with another that implements
17
+ // this interface.
18
+
19
+ export interface ChartSeries {
20
+ seriesName: SeriesName
21
+ color: Color
22
+ }
23
+
24
+ export type ChartTableTransformer = (inputTable: OwidTable) => OwidTable
25
+
26
+ /** Interface implemented by all chart state classes */
27
+ export interface ChartState {
28
+ /** Fail message(s) to show to the user if something went wrong */
29
+ errorInfo: ChartErrorInfo
30
+
31
+ /** OwidTable coming into the chart */
32
+ inputTable: OwidTable
33
+ /** OwidTable after the chart has transformed the input table */
34
+ transformedTable: OwidTable
35
+
36
+ /** Array of selected entities for the chart */
37
+ selectionArray?: SelectionArray
38
+ /** Array of series that should be highlighted or focused */
39
+ focusArray?: FocusArray
40
+
41
+ /** Marks that the chart will render. Not placed yet */
42
+ series: readonly ChartSeries[]
43
+ /** Strategy for handling multiple data series in the chart */
44
+ seriesStrategy?: SeriesStrategy
45
+
46
+ /** Function to transform the input table into the format needed by the chart */
47
+ transformTable: ChartTableTransformer
48
+ /** Optional function to transform the table specifically for the rendered data table */
49
+ transformTableForDisplay?: ChartTableTransformer
50
+ /** Optional function to transform the table specifically for the entity selector */
51
+ transformTableForSelection?: ChartTableTransformer
52
+
53
+ /** Color scale used to assign colors to chart elements */
54
+ colorScale?: ColorScale
55
+
56
+ /**
57
+ * Available facet strategies that are supported by this chart type in its
58
+ * current configuration, if any. Does not necessarily contain
59
+ * FacetStrategy.None - there are situations where an unfaceted chart
60
+ * doesn't make sense.
61
+ */
62
+ availableFacetStrategies?: FacetStrategy[]
63
+ }
64
+
65
+ /** Interface implemented by all chart component classes */
66
+ export interface ChartInterface {
67
+ chartState: ChartState
68
+
69
+ yAxis?: HorizontalAxis | VerticalAxis
70
+ xAxis?: HorizontalAxis | VerticalAxis
71
+
72
+ /**
73
+ * The legend that has been hidden from the chart plot (using `manager.hideLegend`).
74
+ * Used to create a global legend for faceted charts.
75
+ */
76
+ externalLegend?: HorizontalColorLegendManager
77
+
78
+ /**
79
+ * Opt-out of assigned colors and use a value-based color scheme instead.
80
+ * Only relevant for StackedBar charts.
81
+ */
82
+ shouldUseValueBasedColorScheme?: boolean
83
+ }
@@ -0,0 +1,113 @@
1
+ import * as React from "react"
2
+ import {
3
+ EntitySelectionMode,
4
+ FacetStrategy,
5
+ SeriesColorMap,
6
+ SeriesStrategy,
7
+ MissingDataStrategy,
8
+ ColorScaleConfigInterface,
9
+ ComparisonLineConfig,
10
+ AxisConfigInterface,
11
+ ColorSchemeName,
12
+ EntityName,
13
+ DetailsMarker,
14
+ Color,
15
+ GrapherVariant,
16
+ } from "../../types/index.js"
17
+ import { TooltipManager } from "../tooltip/TooltipProps"
18
+ import { OwidTable, CoreColumn } from "../../core-table/index.js"
19
+
20
+ import { SelectionArray } from "../selection/SelectionArray"
21
+ import { ColumnSlug, SortConfig, TimeBound } from "../../utils/index.js"
22
+ import { ColorScaleBin } from "../color/ColorScaleBin"
23
+ import { ColorScale } from "../color/ColorScale"
24
+ import { FocusArray } from "../focus/FocusArray"
25
+
26
+ // The possible options common across our chart types. Not all of these apply to every chart type, so there is room to create a better type hierarchy.
27
+
28
+ export interface ChartManager {
29
+ base?: React.RefObject<SVGGElement | HTMLDivElement | null>
30
+ fontSize?: number
31
+
32
+ table: OwidTable
33
+ transformedTable?: OwidTable
34
+
35
+ variant?: GrapherVariant
36
+ isDisplayedAlongsideComplementaryTable?: boolean
37
+ chartAreaPadding?: number
38
+
39
+ isExportingToSvgOrPng?: boolean
40
+ isRelativeMode?: boolean
41
+ comparisonLines?: ComparisonLineConfig[]
42
+ showLegend?: boolean
43
+ tooltip?: TooltipManager["tooltip"]
44
+ baseColorScheme?: ColorSchemeName
45
+ invertColorScheme?: boolean
46
+ compareEndPointsOnly?: boolean
47
+ zoomToSelection?: boolean
48
+ matchingEntitiesOnly?: boolean
49
+
50
+ colorScale?: Readonly<ColorScaleConfigInterface>
51
+ // for consistent automatic color scales across facets
52
+ colorScaleColumnOverride?: CoreColumn
53
+ // for passing colorScale to sparkline in map charts
54
+ colorScaleOverride?: ColorScale
55
+ // If you want to use auto-assigned colors, but then have them preserved across selection and chart changes
56
+ seriesColorMap?: SeriesColorMap
57
+ // If you want to opt out of assigned colors and use a value-based color scheme instead
58
+ // (e.g. stacked bar charts coloring positive/negative values differently)
59
+ useValueBasedColorScheme?: boolean
60
+
61
+ yAxisConfig?: Readonly<AxisConfigInterface>
62
+ xAxisConfig?: Readonly<AxisConfigInterface>
63
+
64
+ addCountryMode?: EntitySelectionMode
65
+
66
+ yColumnSlug?: ColumnSlug
67
+ yColumnSlugs?: ColumnSlug[]
68
+ xColumnSlug?: ColumnSlug
69
+ sizeColumnSlug?: ColumnSlug
70
+ colorColumnSlug?: ColumnSlug
71
+
72
+ // if colorColumnSlug is given, either one of these is set
73
+ categoricalColorColumnSlug?: ColumnSlug
74
+ numericColorColumnSlug?: ColumnSlug
75
+
76
+ selection?: SelectionArray | EntityName[]
77
+ entityType?: string
78
+ entityTypePlural?: string
79
+
80
+ focusArray?: FocusArray
81
+
82
+ hidePoints?: boolean // for line options
83
+ startHandleTimeBound?: TimeBound // for relative-to-first-year line chart
84
+ hideNoDataSection?: boolean // for slope charts
85
+
86
+ // we need endTime so DiscreteBarCharts and StackedDiscreteBarCharts can
87
+ // know what date the timeline is set to. and let's pass startTime in, too.
88
+ startTime?: number
89
+ endTime?: number
90
+
91
+ facetStrategy?: FacetStrategy // todo: make a strategy? a column prop? etc
92
+ seriesStrategy?: SeriesStrategy
93
+
94
+ sortConfig?: SortConfig
95
+ showNoDataArea?: boolean // No data area in Marimekko charts
96
+
97
+ externalLegendHoverBin?: ColorScaleBin | undefined
98
+ disableIntroAnimation?: boolean
99
+
100
+ missingDataStrategy?: MissingDataStrategy
101
+
102
+ isNarrow?: boolean
103
+ isStatic?: boolean
104
+ isSemiNarrow?: boolean
105
+ isStaticAndSmall?: boolean
106
+ isExportingForSocialMedia?: boolean
107
+ isExportingForWikimedia?: boolean
108
+ backgroundColor?: Color
109
+ shouldPinTooltipToBottom?: boolean
110
+
111
+ detailsOrderedByReference?: string[]
112
+ detailsMarkerInSvg?: DetailsMarker
113
+ }
@@ -0,0 +1,178 @@
1
+ import {
2
+ ALL_GRAPHER_CHART_TYPES,
3
+ GRAPHER_CHART_TYPES,
4
+ GRAPHER_TAB_NAMES,
5
+ GRAPHER_TAB_CONFIG_OPTIONS,
6
+ GRAPHER_TAB_QUERY_PARAMS,
7
+ GrapherChartType,
8
+ GrapherTabName,
9
+ GrapherTabConfigOption,
10
+ GrapherTabQueryParam,
11
+ } from "../../types/index.js"
12
+ import * as R from "remeda"
13
+ import { match } from "ts-pattern"
14
+
15
+ /**
16
+ * Chart type combinations that are currently supported. Every subset of these
17
+ * combinations is valid. For example, [LineChart, SlopeChart, DiscreteBar]
18
+ * makes all these combinations valid: [LineChart, SlopeChart, DiscreteBar],
19
+ * [LineChart, SlopeChart], [LineChart, DiscreteBar], [SlopeChart, DiscreteBar]
20
+ *
21
+ * This also determines the order of chart types in the UI.
22
+ */
23
+ const VALID_CHART_TYPE_COMBINATIONS = [
24
+ [
25
+ GRAPHER_CHART_TYPES.LineChart,
26
+ GRAPHER_CHART_TYPES.SlopeChart,
27
+ GRAPHER_CHART_TYPES.DiscreteBar,
28
+ GRAPHER_CHART_TYPES.Marimekko,
29
+ ],
30
+ ]
31
+
32
+ type ChartTabConfigOption = Exclude<
33
+ GrapherTabConfigOption,
34
+ "table" | "map" | "chart"
35
+ >
36
+
37
+ export const CHART_TYPE_LABEL: Record<GrapherChartType, string> = {
38
+ [GRAPHER_CHART_TYPES.LineChart]: "Line",
39
+ [GRAPHER_CHART_TYPES.SlopeChart]: "Slope",
40
+ [GRAPHER_CHART_TYPES.ScatterPlot]: "Scatter",
41
+ [GRAPHER_CHART_TYPES.StackedArea]: "Stacked area",
42
+ [GRAPHER_CHART_TYPES.StackedBar]: "Stacked bar",
43
+ [GRAPHER_CHART_TYPES.DiscreteBar]: "Bar",
44
+ [GRAPHER_CHART_TYPES.StackedDiscreteBar]: "Stacked bar",
45
+ [GRAPHER_CHART_TYPES.Marimekko]: "Marimekko",
46
+ }
47
+
48
+ export const LONG_CHART_TYPE_LABEL: Record<GrapherChartType, string> = {
49
+ [GRAPHER_CHART_TYPES.LineChart]: "Line chart",
50
+ [GRAPHER_CHART_TYPES.SlopeChart]: "Slope chart",
51
+ [GRAPHER_CHART_TYPES.ScatterPlot]: "Scatter plot",
52
+ [GRAPHER_CHART_TYPES.StackedArea]: "Stacked area chart",
53
+ [GRAPHER_CHART_TYPES.StackedBar]: "Bar chart",
54
+ [GRAPHER_CHART_TYPES.DiscreteBar]: "Bar chart",
55
+ [GRAPHER_CHART_TYPES.StackedDiscreteBar]: "Bar chart",
56
+ [GRAPHER_CHART_TYPES.Marimekko]: "Marimekko chart",
57
+ }
58
+
59
+ const MAP_CHART_TAB_CONFIG_OPTION_TO_CHART_TYPE_NAME: Record<
60
+ ChartTabConfigOption,
61
+ GrapherChartType
62
+ > = {
63
+ [GRAPHER_TAB_CONFIG_OPTIONS.line]: GRAPHER_CHART_TYPES.LineChart,
64
+ [GRAPHER_TAB_CONFIG_OPTIONS.slope]: GRAPHER_CHART_TYPES.SlopeChart,
65
+ [GRAPHER_TAB_CONFIG_OPTIONS.scatter]: GRAPHER_CHART_TYPES.ScatterPlot,
66
+ [GRAPHER_TAB_CONFIG_OPTIONS["stacked-area"]]:
67
+ GRAPHER_CHART_TYPES.StackedArea,
68
+ [GRAPHER_TAB_CONFIG_OPTIONS["stacked-bar"]]: GRAPHER_CHART_TYPES.StackedBar,
69
+ [GRAPHER_TAB_CONFIG_OPTIONS["discrete-bar"]]:
70
+ GRAPHER_CHART_TYPES.DiscreteBar,
71
+ [GRAPHER_TAB_CONFIG_OPTIONS["stacked-discrete-bar"]]:
72
+ GRAPHER_CHART_TYPES.StackedDiscreteBar,
73
+ [GRAPHER_TAB_CONFIG_OPTIONS.marimekko]: GRAPHER_CHART_TYPES.Marimekko,
74
+ }
75
+
76
+ const MAP_CHART_TYPE_NAME_TO_CHART_TAB_CONFIG_OPTION = R.invert(
77
+ MAP_CHART_TAB_CONFIG_OPTION_TO_CHART_TYPE_NAME
78
+ )
79
+
80
+ export function mapTabConfigOptionToChartTypeName(
81
+ tabOption: ChartTabConfigOption
82
+ ): GrapherChartType {
83
+ return MAP_CHART_TAB_CONFIG_OPTION_TO_CHART_TYPE_NAME[tabOption]
84
+ }
85
+
86
+ export function mapChartTypeNameToTabConfigOption(
87
+ chartType: GrapherChartType
88
+ ): ChartTabConfigOption {
89
+ return MAP_CHART_TYPE_NAME_TO_CHART_TAB_CONFIG_OPTION[chartType]
90
+ }
91
+
92
+ export function mapTabQueryParamToChartTypeName(
93
+ tab: ChartTabConfigOption
94
+ ): GrapherChartType {
95
+ return MAP_CHART_TAB_CONFIG_OPTION_TO_CHART_TYPE_NAME[tab]
96
+ }
97
+
98
+ export function mapChartTypeNameToQueryParam(
99
+ chartType: GrapherChartType
100
+ ): ChartTabConfigOption {
101
+ return MAP_CHART_TYPE_NAME_TO_CHART_TAB_CONFIG_OPTION[chartType]
102
+ }
103
+
104
+ export function mapGrapherTabNameToConfigOption(
105
+ tabName: GrapherTabName
106
+ ): GrapherTabConfigOption {
107
+ return match(tabName)
108
+ .with(GRAPHER_TAB_NAMES.Table, () => GRAPHER_TAB_CONFIG_OPTIONS.table)
109
+ .with(GRAPHER_TAB_NAMES.WorldMap, () => GRAPHER_TAB_CONFIG_OPTIONS.map)
110
+ .otherwise((tabName) => mapChartTypeNameToTabConfigOption(tabName))
111
+ }
112
+
113
+ export const mapGrapherTabNameToQueryParam = mapGrapherTabNameToConfigOption
114
+
115
+ export function makeLabelForGrapherTab(
116
+ tab: GrapherTabName,
117
+ options?: { useGenericChartLabel?: boolean; format?: "short" | "long" }
118
+ ): string {
119
+ const { useGenericChartLabel = false, format = "short" } = options ?? {}
120
+
121
+ if (tab === GRAPHER_TAB_NAMES.Table) return "Table"
122
+ if (tab === GRAPHER_TAB_NAMES.WorldMap)
123
+ return format === "short" ? "Map" : "World map"
124
+
125
+ if (useGenericChartLabel) return "Chart"
126
+
127
+ return format === "short"
128
+ ? CHART_TYPE_LABEL[tab]
129
+ : LONG_CHART_TYPE_LABEL[tab]
130
+ }
131
+
132
+ export function findPotentialChartTypeSiblings(
133
+ chartTypes: GrapherChartType[]
134
+ ): GrapherChartType[] | undefined {
135
+ for (const validCombination of VALID_CHART_TYPE_COMBINATIONS) {
136
+ const validSet: Set<GrapherChartType> = new Set(validCombination)
137
+ const hasIntersection = chartTypes.some((chartType) =>
138
+ validSet.has(chartType)
139
+ )
140
+ if (hasIntersection) return validCombination
141
+ }
142
+ return undefined
143
+ }
144
+
145
+ export function findValidChartTypeCombination(
146
+ chartTypes: GrapherChartType[]
147
+ ): GrapherChartType[] | undefined {
148
+ const validCombination = findPotentialChartTypeSiblings(chartTypes)
149
+ return validCombination?.filter((chartType) =>
150
+ chartTypes.includes(chartType)
151
+ )
152
+ }
153
+
154
+ export function isChartTypeName(
155
+ candidate: string
156
+ ): candidate is GrapherChartType {
157
+ return ALL_GRAPHER_CHART_TYPES.includes(candidate as any)
158
+ }
159
+
160
+ export function isValidTabQueryParam(
161
+ candidate: string
162
+ ): candidate is GrapherTabQueryParam {
163
+ return Object.values(GRAPHER_TAB_QUERY_PARAMS).includes(candidate as any)
164
+ }
165
+
166
+ export function isValidTabConfigOption(
167
+ candidate: string
168
+ ): candidate is GrapherTabConfigOption {
169
+ return Object.values(GRAPHER_TAB_CONFIG_OPTIONS).includes(candidate as any)
170
+ }
171
+
172
+ export const isChartTab = (tab: GrapherTabName): tab is GrapherChartType =>
173
+ tab !== GRAPHER_TAB_NAMES.Table && tab !== GRAPHER_TAB_NAMES.WorldMap
174
+
175
+ export const isMapTab = (
176
+ tab: GrapherTabName
177
+ ): tab is typeof GRAPHER_TAB_NAMES.WorldMap =>
178
+ tab === GRAPHER_TAB_NAMES.WorldMap