@robr0/design-system 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 (223) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +127 -0
  3. package/charts.d.ts +14 -0
  4. package/charts.js +20 -0
  5. package/components/Accordion/Accordion.css +119 -0
  6. package/components/Accordion/Accordion.d.ts +24 -0
  7. package/components/Accordion/Accordion.js +76 -0
  8. package/components/Alert/Alert.css +252 -0
  9. package/components/Alert/Alert.d.ts +24 -0
  10. package/components/Alert/Alert.js +53 -0
  11. package/components/AlertDialog/AlertDialog.css +131 -0
  12. package/components/AlertDialog/AlertDialog.d.ts +29 -0
  13. package/components/AlertDialog/AlertDialog.js +143 -0
  14. package/components/AppLayout/AppLayout.css +52 -0
  15. package/components/AppLayout/AppLayout.d.ts +27 -0
  16. package/components/AppLayout/AppLayout.js +45 -0
  17. package/components/AppSidebar/AppSidebar.css +434 -0
  18. package/components/AppSidebar/AppSidebar.d.ts +67 -0
  19. package/components/AppSidebar/AppSidebar.js +272 -0
  20. package/components/Avatar/Avatar.css +133 -0
  21. package/components/Avatar/Avatar.d.ts +20 -0
  22. package/components/Avatar/Avatar.js +56 -0
  23. package/components/Avatar/demoAvatars.d.ts +14 -0
  24. package/components/Avatar/demoAvatars.js +16 -0
  25. package/components/Badge/Badge.css +68 -0
  26. package/components/Badge/Badge.d.ts +13 -0
  27. package/components/Badge/Badge.js +15 -0
  28. package/components/Breadcrumb/Breadcrumb.css +92 -0
  29. package/components/Breadcrumb/Breadcrumb.d.ts +19 -0
  30. package/components/Breadcrumb/Breadcrumb.js +39 -0
  31. package/components/Button/Button.css +381 -0
  32. package/components/Button/Button.d.ts +39 -0
  33. package/components/Button/Button.js +71 -0
  34. package/components/ButtonGroup/ButtonGroup.css +39 -0
  35. package/components/ButtonGroup/ButtonGroup.d.ts +13 -0
  36. package/components/ButtonGroup/ButtonGroup.js +37 -0
  37. package/components/Card/Card.css +169 -0
  38. package/components/Card/Card.d.ts +30 -0
  39. package/components/Card/Card.js +90 -0
  40. package/components/Carousel/Carousel.css +112 -0
  41. package/components/Carousel/Carousel.d.ts +25 -0
  42. package/components/Carousel/Carousel.js +126 -0
  43. package/components/Chart/AreaChart.d.ts +36 -0
  44. package/components/Chart/AreaChart.js +99 -0
  45. package/components/Chart/BarChart.d.ts +34 -0
  46. package/components/Chart/BarChart.js +107 -0
  47. package/components/Chart/Chart.css +176 -0
  48. package/components/Chart/LineChart.d.ts +34 -0
  49. package/components/Chart/LineChart.js +90 -0
  50. package/components/Chart/PieChart.d.ts +34 -0
  51. package/components/Chart/PieChart.js +106 -0
  52. package/components/Chart/RadarChart.d.ts +34 -0
  53. package/components/Chart/RadarChart.js +91 -0
  54. package/components/Chart/RadialChart.d.ts +37 -0
  55. package/components/Chart/RadialChart.js +119 -0
  56. package/components/Chart/ScatterChart.d.ts +36 -0
  57. package/components/Chart/ScatterChart.js +109 -0
  58. package/components/Chart/StackedBarChart.d.ts +34 -0
  59. package/components/Chart/StackedBarChart.js +111 -0
  60. package/components/Chart/Treemap.d.ts +33 -0
  61. package/components/Chart/Treemap.js +109 -0
  62. package/components/Checkbox/Checkbox.css +164 -0
  63. package/components/Checkbox/Checkbox.d.ts +45 -0
  64. package/components/Checkbox/Checkbox.js +125 -0
  65. package/components/Chip/Chip.css +195 -0
  66. package/components/Chip/Chip.d.ts +27 -0
  67. package/components/Chip/Chip.js +80 -0
  68. package/components/CircularButton/CircularButton.css +206 -0
  69. package/components/CircularButton/CircularButton.d.ts +30 -0
  70. package/components/CircularButton/CircularButton.js +54 -0
  71. package/components/CodeBlock/CodeBlock.css +180 -0
  72. package/components/CodeBlock/CodeBlock.d.ts +23 -0
  73. package/components/CodeBlock/CodeBlock.js +85 -0
  74. package/components/ColourSwatch/ColourSwatch.css +88 -0
  75. package/components/ColourSwatch/ColourSwatch.d.ts +34 -0
  76. package/components/ColourSwatch/ColourSwatch.js +42 -0
  77. package/components/Combobox/Combobox.css +411 -0
  78. package/components/Combobox/Combobox.d.ts +73 -0
  79. package/components/Combobox/Combobox.js +312 -0
  80. package/components/CommandPalette/CommandPalette.css +310 -0
  81. package/components/CommandPalette/CommandPalette.d.ts +60 -0
  82. package/components/CommandPalette/CommandPalette.js +263 -0
  83. package/components/ContactCard/ContactCard.css +123 -0
  84. package/components/ContactCard/ContactCard.d.ts +23 -0
  85. package/components/ContactCard/ContactCard.js +78 -0
  86. package/components/ContributionGraph/ContributionGraph.css +142 -0
  87. package/components/ContributionGraph/ContributionGraph.d.ts +26 -0
  88. package/components/ContributionGraph/ContributionGraph.js +125 -0
  89. package/components/DateInput/DateInput.css +163 -0
  90. package/components/DateInput/DateInput.d.ts +43 -0
  91. package/components/DateInput/DateInput.js +69 -0
  92. package/components/DatePicker/DatePicker.css +198 -0
  93. package/components/DatePicker/DatePicker.d.ts +22 -0
  94. package/components/DatePicker/DatePicker.js +170 -0
  95. package/components/Dialog/Dialog.css +176 -0
  96. package/components/Dialog/Dialog.d.ts +28 -0
  97. package/components/Dialog/Dialog.js +132 -0
  98. package/components/Divider/Divider.css +100 -0
  99. package/components/Divider/Divider.d.ts +18 -0
  100. package/components/Divider/Divider.js +31 -0
  101. package/components/Drawer/Drawer.css +262 -0
  102. package/components/Drawer/Drawer.d.ts +30 -0
  103. package/components/Drawer/Drawer.js +134 -0
  104. package/components/Dropdown/Dropdown.css +300 -0
  105. package/components/Dropdown/Dropdown.d.ts +48 -0
  106. package/components/Dropdown/Dropdown.js +196 -0
  107. package/components/DropdownMenu/DropdownMenu.css +303 -0
  108. package/components/DropdownMenu/DropdownMenu.d.ts +42 -0
  109. package/components/DropdownMenu/DropdownMenu.js +322 -0
  110. package/components/EmptyState/EmptyState.css +115 -0
  111. package/components/EmptyState/EmptyState.d.ts +27 -0
  112. package/components/EmptyState/EmptyState.js +32 -0
  113. package/components/EntityCard/EntityCard.css +69 -0
  114. package/components/EntityCard/EntityCard.d.ts +18 -0
  115. package/components/EntityCard/EntityCard.js +26 -0
  116. package/components/Figure/Figure.css +61 -0
  117. package/components/Figure/Figure.d.ts +17 -0
  118. package/components/Figure/Figure.js +35 -0
  119. package/components/FileInput/FileInput.css +308 -0
  120. package/components/FileInput/FileInput.d.ts +54 -0
  121. package/components/FileInput/FileInput.js +177 -0
  122. package/components/Input/Input.css +193 -0
  123. package/components/Input/Input.d.ts +40 -0
  124. package/components/Input/Input.js +71 -0
  125. package/components/Instructions/Instructions.css +216 -0
  126. package/components/Instructions/Instructions.d.ts +28 -0
  127. package/components/Instructions/Instructions.js +32 -0
  128. package/components/LinkList/LinkList.css +71 -0
  129. package/components/LinkList/LinkList.d.ts +20 -0
  130. package/components/LinkList/LinkList.js +41 -0
  131. package/components/MotionSwatch/MotionSwatch.css +176 -0
  132. package/components/MotionSwatch/MotionSwatch.d.ts +25 -0
  133. package/components/MotionSwatch/MotionSwatch.js +74 -0
  134. package/components/Nav/Nav.css +51 -0
  135. package/components/Nav/Nav.d.ts +19 -0
  136. package/components/Nav/Nav.js +26 -0
  137. package/components/Pagination/Pagination.css +126 -0
  138. package/components/Pagination/Pagination.d.ts +22 -0
  139. package/components/Pagination/Pagination.js +83 -0
  140. package/components/Popover/Popover.css +99 -0
  141. package/components/Popover/Popover.d.ts +28 -0
  142. package/components/Popover/Popover.js +102 -0
  143. package/components/ProgressBar/ProgressBar.css +60 -0
  144. package/components/ProgressBar/ProgressBar.d.ts +16 -0
  145. package/components/ProgressBar/ProgressBar.js +27 -0
  146. package/components/Quote/Quote.css +79 -0
  147. package/components/Quote/Quote.d.ts +18 -0
  148. package/components/Quote/Quote.js +26 -0
  149. package/components/RadioButton/RadioButton.css +132 -0
  150. package/components/RadioButton/RadioButton.d.ts +43 -0
  151. package/components/RadioButton/RadioButton.js +77 -0
  152. package/components/SectionTitle/SectionTitle.css +37 -0
  153. package/components/SectionTitle/SectionTitle.d.ts +10 -0
  154. package/components/SectionTitle/SectionTitle.js +17 -0
  155. package/components/SegmentedControl/SegmentedControl.css +129 -0
  156. package/components/SegmentedControl/SegmentedControl.d.ts +33 -0
  157. package/components/SegmentedControl/SegmentedControl.js +91 -0
  158. package/components/SelectionCard/SelectionCard.css +251 -0
  159. package/components/SelectionCard/SelectionCard.d.ts +26 -0
  160. package/components/SelectionCard/SelectionCard.js +85 -0
  161. package/components/Skeleton/Skeleton.css +79 -0
  162. package/components/Skeleton/Skeleton.d.ts +16 -0
  163. package/components/Skeleton/Skeleton.js +30 -0
  164. package/components/Slider/Slider.css +86 -0
  165. package/components/Slider/Slider.d.ts +25 -0
  166. package/components/Slider/Slider.js +46 -0
  167. package/components/SpacingSwatch/SpacingSwatch.css +108 -0
  168. package/components/SpacingSwatch/SpacingSwatch.d.ts +20 -0
  169. package/components/SpacingSwatch/SpacingSwatch.js +50 -0
  170. package/components/Spinner/Spinner.css +73 -0
  171. package/components/Spinner/Spinner.d.ts +14 -0
  172. package/components/Spinner/Spinner.js +42 -0
  173. package/components/Stat/Stat.css +78 -0
  174. package/components/Stat/Stat.d.ts +19 -0
  175. package/components/Stat/Stat.js +30 -0
  176. package/components/Table/Table.css +186 -0
  177. package/components/Table/Table.d.ts +45 -0
  178. package/components/Table/Table.js +65 -0
  179. package/components/Tabs/Tabs.css +140 -0
  180. package/components/Tabs/Tabs.d.ts +28 -0
  181. package/components/Tabs/Tabs.js +77 -0
  182. package/components/Textarea/Textarea.css +152 -0
  183. package/components/Textarea/Textarea.d.ts +40 -0
  184. package/components/Textarea/Textarea.js +74 -0
  185. package/components/Timeline/Timeline.css +339 -0
  186. package/components/Timeline/Timeline.d.ts +63 -0
  187. package/components/Timeline/Timeline.js +69 -0
  188. package/components/Toast/Toast.css +342 -0
  189. package/components/Toast/Toast.d.ts +63 -0
  190. package/components/Toast/Toast.js +213 -0
  191. package/components/ToggleGroup/ToggleGroup.css +84 -0
  192. package/components/ToggleGroup/ToggleGroup.d.ts +30 -0
  193. package/components/ToggleGroup/ToggleGroup.js +53 -0
  194. package/components/ToggleSwitch/ToggleSwitch.css +139 -0
  195. package/components/ToggleSwitch/ToggleSwitch.d.ts +23 -0
  196. package/components/ToggleSwitch/ToggleSwitch.js +50 -0
  197. package/components/Tooltip/Tooltip.css +122 -0
  198. package/components/Tooltip/Tooltip.d.ts +21 -0
  199. package/components/Tooltip/Tooltip.js +63 -0
  200. package/components/TypographySwatch/TypographySwatch.css +81 -0
  201. package/components/TypographySwatch/TypographySwatch.d.ts +24 -0
  202. package/components/TypographySwatch/TypographySwatch.js +40 -0
  203. package/components/registry.d.ts +20 -0
  204. package/components/registry.js +7 -0
  205. package/components/registry.json +67 -0
  206. package/components/registry.json.d.ts +70 -0
  207. package/components/registry.json.js +8 -0
  208. package/fonts/MaterialSymbolsRounded-VariableFont_FILL,GRAD,opsz,wght.woff2 +0 -0
  209. package/fonts/material-symbols.css +94 -0
  210. package/index.d.ts +62 -0
  211. package/index.js +123 -0
  212. package/package.json +63 -0
  213. package/tokens/registry.d.ts +22 -0
  214. package/tokens/registry.js +14 -0
  215. package/tokens/registry.json +203 -0
  216. package/tokens/registry.json.d.ts +206 -0
  217. package/tokens/registry.json.js +8 -0
  218. package/tokens/tokens-dark.css +119 -0
  219. package/tokens/tokens-light.css +159 -0
  220. package/tokens/tokens-motion.css +68 -0
  221. package/tokens/tokens-primitives.css +176 -0
  222. package/tokens/tokens-typography.css +116 -0
  223. package/tokens/tokens.css +11 -0
@@ -0,0 +1,34 @@
1
+ import { ChartSummaryItem } from './BarChart';
2
+ export interface RadarSeriesConfig {
3
+ /** Key in data for this series */
4
+ dataKey: string;
5
+ /** Display name (shown in tooltip and legend) */
6
+ label: string;
7
+ /** Fill / stroke colour — CSS value */
8
+ color?: string;
9
+ /** Fill opacity (0–1) */
10
+ fillOpacity?: number;
11
+ }
12
+ export interface RadarChartProps {
13
+ /** Array of data objects — each should have a category key and one or more value keys */
14
+ data: Record<string, unknown>[];
15
+ /** Key in data for the category labels on each axis */
16
+ categoryKey?: string;
17
+ /** One or more radar series to render */
18
+ series: RadarSeriesConfig[];
19
+ /** Chart title */
20
+ title?: string;
21
+ /** Description text below the title */
22
+ subtitle?: string;
23
+ /** Summary stats displayed in the header */
24
+ summaryItems?: ChartSummaryItem[];
25
+ /** Chart area height in pixels */
26
+ height?: number;
27
+ /** Additional CSS classes on the wrapper */
28
+ className?: string;
29
+ }
30
+ /**
31
+ * Radar chart built on Recharts with design-system tokens.
32
+ * Renders one or more data series as filled polygons on a polar grid.
33
+ */
34
+ export declare const RadarChart: ({ data, categoryKey, series, title, subtitle, summaryItems, height, className, }: RadarChartProps) => import("react").JSX.Element;
@@ -0,0 +1,91 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { useCallback } from "react";
3
+ import { ResponsiveContainer, RadarChart as RadarChart$1, PolarGrid, PolarAngleAxis, PolarRadiusAxis, Tooltip, Radar, Legend } from "recharts";
4
+ import "./Chart.css";
5
+ function getCSSVar(name, fallback) {
6
+ if (typeof window === "undefined") return fallback;
7
+ return getComputedStyle(document.documentElement).getPropertyValue(name).trim() || fallback;
8
+ }
9
+ function RadarTooltip({ active, payload, label }) {
10
+ if (!active || !payload?.length) return null;
11
+ return /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip", children: [
12
+ /* @__PURE__ */ jsx("div", { className: "ds-chart__tooltip-label", children: label }),
13
+ payload.map((entry, i) => /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip-row", children: [
14
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-dot", style: { backgroundColor: entry.color } }),
15
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-name", children: entry.name }),
16
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-value", children: entry.value?.toLocaleString() })
17
+ ] }, i))
18
+ ] });
19
+ }
20
+ const RadarChart = ({
21
+ data,
22
+ categoryKey = "subject",
23
+ series,
24
+ title,
25
+ subtitle,
26
+ summaryItems,
27
+ height = 350,
28
+ className = ""
29
+ }) => {
30
+ const baseClass = "ds-chart";
31
+ const classes = [baseClass, className].filter(Boolean).join(" ");
32
+ const textSecondary = getCSSVar("--color-text-secondary", "#A2A2A2");
33
+ const gridColor = getCSSVar("--color-divider", "#232323");
34
+ const defaultColor = getCSSVar("--color-action-primary-bg", "#118AB2");
35
+ const renderTooltip = useCallback(
36
+ /* eslint-disable-next-line @typescript-eslint/no-explicit-any */
37
+ (props) => /* @__PURE__ */ jsx(RadarTooltip, { ...props }),
38
+ []
39
+ );
40
+ return /* @__PURE__ */ jsxs("div", { className: classes, children: [
41
+ (title || subtitle || summaryItems) && /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header`, children: [
42
+ /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header-text`, children: [
43
+ title && /* @__PURE__ */ jsx("h3", { className: `${baseClass}__title`, children: title }),
44
+ subtitle && /* @__PURE__ */ jsx("p", { className: `${baseClass}__subtitle`, children: subtitle })
45
+ ] }),
46
+ summaryItems && summaryItems.length > 0 && /* @__PURE__ */ jsx("div", { className: `${baseClass}__summary`, children: summaryItems.map((item, i) => /* @__PURE__ */ jsxs("div", { className: `${baseClass}__summary-item`, children: [
47
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-label`, children: item.label }),
48
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-value`, children: typeof item.value === "number" ? item.value.toLocaleString() : item.value })
49
+ ] }, i)) })
50
+ ] }),
51
+ /* @__PURE__ */ jsx("div", { className: `${baseClass}__body`, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height, children: /* @__PURE__ */ jsxs(RadarChart$1, { data, cx: "50%", cy: "50%", outerRadius: "70%", children: [
52
+ /* @__PURE__ */ jsx(PolarGrid, { stroke: gridColor }),
53
+ /* @__PURE__ */ jsx(
54
+ PolarAngleAxis,
55
+ {
56
+ dataKey: categoryKey,
57
+ tick: { fill: textSecondary, fontSize: 12 }
58
+ }
59
+ ),
60
+ /* @__PURE__ */ jsx(
61
+ PolarRadiusAxis,
62
+ {
63
+ tick: { fill: textSecondary, fontSize: 10 },
64
+ axisLine: false,
65
+ tickCount: 5
66
+ }
67
+ ),
68
+ /* @__PURE__ */ jsx(Tooltip, { content: renderTooltip }),
69
+ series.map((s) => /* @__PURE__ */ jsx(
70
+ Radar,
71
+ {
72
+ name: s.label,
73
+ dataKey: s.dataKey,
74
+ stroke: s.color || defaultColor,
75
+ fill: s.color || defaultColor,
76
+ fillOpacity: s.fillOpacity ?? 0.3
77
+ },
78
+ s.dataKey
79
+ )),
80
+ series.length > 1 && /* @__PURE__ */ jsx(
81
+ Legend,
82
+ {
83
+ wrapperStyle: { color: textSecondary, fontSize: 12 }
84
+ }
85
+ )
86
+ ] }) }) })
87
+ ] });
88
+ };
89
+ export {
90
+ RadarChart
91
+ };
@@ -0,0 +1,37 @@
1
+ import { ChartSummaryItem } from './BarChart';
2
+ export interface RadialDataItem {
3
+ /** Display name */
4
+ name: string;
5
+ /** Numeric value */
6
+ value: number;
7
+ /** Ring fill colour */
8
+ color?: string;
9
+ }
10
+ export interface RadialChartProps {
11
+ /** Array of data items — each renders as a concentric ring */
12
+ data: RadialDataItem[];
13
+ /** Maximum value for the radial scale (100 = percentage) */
14
+ maxValue?: number;
15
+ /** Chart title */
16
+ title?: string;
17
+ /** Description text below the title */
18
+ subtitle?: string;
19
+ /** Summary stats displayed in the header */
20
+ summaryItems?: ChartSummaryItem[];
21
+ /** Chart area height in pixels */
22
+ height?: number;
23
+ /** Inner radius of the innermost ring */
24
+ innerRadius?: number;
25
+ /** Outer radius of the outermost ring */
26
+ outerRadius?: number;
27
+ /** Show legend */
28
+ showLegend?: boolean;
29
+ /** Additional CSS classes on the wrapper */
30
+ className?: string;
31
+ }
32
+ /**
33
+ * Radial bar chart built on Recharts with design-system tokens.
34
+ * Each data item renders as a concentric ring — great for
35
+ * progress indicators and comparative gauges.
36
+ */
37
+ export declare const RadialChart: ({ data, maxValue, title, subtitle, summaryItems, height, innerRadius, outerRadius, showLegend, className, }: RadialChartProps) => import("react").JSX.Element;
@@ -0,0 +1,119 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { useCallback } from "react";
3
+ import { ResponsiveContainer, RadialBarChart, PolarAngleAxis, RadialBar, Tooltip, Legend } from "recharts";
4
+ import "./Chart.css";
5
+ function getDefaultColors() {
6
+ if (typeof window === "undefined") {
7
+ return ["#118AB2", "#06D6A0", "#FFD166", "#EF476F", "#9E47EF", "#EF8247"];
8
+ }
9
+ const get = (v, fb) => getComputedStyle(document.documentElement).getPropertyValue(v).trim() || fb;
10
+ return [
11
+ get("--color-action-primary-bg", "#118AB2"),
12
+ get("--color-core-accent-mint", "#06D6A0"),
13
+ get("--color-core-accent-gold", "#FFD166"),
14
+ get("--color-core-accent-coral", "#EF476F"),
15
+ get("--color-core-accent-violet", "#9E47EF"),
16
+ get("--color-core-accent-amber", "#EF8247")
17
+ ];
18
+ }
19
+ function getCSSVar(name, fallback) {
20
+ if (typeof window === "undefined") return fallback;
21
+ return getComputedStyle(document.documentElement).getPropertyValue(name).trim() || fallback;
22
+ }
23
+ function RadialTooltip({ active, payload }) {
24
+ if (!active || !payload?.length) return null;
25
+ const entry = payload[0];
26
+ return /* @__PURE__ */ jsx("div", { className: "ds-chart__tooltip", children: /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip-row", children: [
27
+ /* @__PURE__ */ jsx(
28
+ "span",
29
+ {
30
+ className: "ds-chart__tooltip-dot",
31
+ style: { backgroundColor: entry.payload?.fill }
32
+ }
33
+ ),
34
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-name", children: entry.payload?.name }),
35
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-value", children: entry.value?.toLocaleString() })
36
+ ] }) });
37
+ }
38
+ const RadialChart = ({
39
+ data,
40
+ maxValue = 100,
41
+ title,
42
+ subtitle,
43
+ summaryItems,
44
+ height = 350,
45
+ innerRadius = 40,
46
+ outerRadius = 140,
47
+ showLegend = true,
48
+ className = ""
49
+ }) => {
50
+ const baseClass = "ds-chart";
51
+ const classes = [baseClass, className].filter(Boolean).join(" ");
52
+ const defaultColors = getDefaultColors();
53
+ const textSecondary = getCSSVar("--color-text-secondary", "#A2A2A2");
54
+ const bgColor = getCSSVar("--color-bg-container-primary", "#0E0E0E");
55
+ const chartData = data.map((item, i) => ({
56
+ ...item,
57
+ fill: item.color || defaultColors[i % defaultColors.length]
58
+ }));
59
+ const renderTooltip = useCallback(
60
+ /* eslint-disable-next-line @typescript-eslint/no-explicit-any */
61
+ (props) => /* @__PURE__ */ jsx(RadialTooltip, { ...props }),
62
+ []
63
+ );
64
+ return /* @__PURE__ */ jsxs("div", { className: classes, children: [
65
+ (title || subtitle || summaryItems) && /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header`, children: [
66
+ /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header-text`, children: [
67
+ title && /* @__PURE__ */ jsx("h3", { className: `${baseClass}__title`, children: title }),
68
+ subtitle && /* @__PURE__ */ jsx("p", { className: `${baseClass}__subtitle`, children: subtitle })
69
+ ] }),
70
+ summaryItems && summaryItems.length > 0 && /* @__PURE__ */ jsx("div", { className: `${baseClass}__summary`, children: summaryItems.map((item, i) => /* @__PURE__ */ jsxs("div", { className: `${baseClass}__summary-item`, children: [
71
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-label`, children: item.label }),
72
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-value`, children: typeof item.value === "number" ? item.value.toLocaleString() : item.value })
73
+ ] }, i)) })
74
+ ] }),
75
+ /* @__PURE__ */ jsx("div", { className: `${baseClass}__body`, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height, children: /* @__PURE__ */ jsxs(
76
+ RadialBarChart,
77
+ {
78
+ cx: "50%",
79
+ cy: "50%",
80
+ innerRadius,
81
+ outerRadius,
82
+ data: chartData,
83
+ startAngle: 90,
84
+ endAngle: -270,
85
+ barSize: 16,
86
+ children: [
87
+ /* @__PURE__ */ jsx(PolarAngleAxis, { type: "number", domain: [0, maxValue], tick: false }),
88
+ /* @__PURE__ */ jsx(
89
+ RadialBar,
90
+ {
91
+ background: { fill: bgColor },
92
+ dataKey: "value",
93
+ cornerRadius: 8
94
+ }
95
+ ),
96
+ /* @__PURE__ */ jsx(Tooltip, { content: renderTooltip }),
97
+ showLegend && /* @__PURE__ */ jsx(
98
+ Legend,
99
+ {
100
+ verticalAlign: "bottom",
101
+ iconType: "circle",
102
+ iconSize: 8,
103
+ ...{ payload: chartData.map((d) => ({
104
+ value: d.name,
105
+ type: "circle",
106
+ color: d.fill
107
+ /* eslint-disable-next-line @typescript-eslint/no-explicit-any */
108
+ })) },
109
+ formatter: (value) => /* @__PURE__ */ jsx("span", { style: { color: textSecondary, fontSize: 12 }, children: value })
110
+ }
111
+ )
112
+ ]
113
+ }
114
+ ) }) })
115
+ ] });
116
+ };
117
+ export {
118
+ RadialChart
119
+ };
@@ -0,0 +1,36 @@
1
+ import { ChartSummaryItem } from './BarChart';
2
+ export interface ScatterDatasetConfig {
3
+ /** Display name for this dataset (shown in tooltip and legend) */
4
+ name: string;
5
+ /** Array of data points */
6
+ data: Record<string, unknown>[];
7
+ /** Fill colour */
8
+ color?: string;
9
+ }
10
+ export interface ScatterChartProps {
11
+ /** One or more scatter datasets to plot */
12
+ datasets: ScatterDatasetConfig[];
13
+ /** Key in data for x-axis values */
14
+ xKey?: string;
15
+ /** Key in data for y-axis values */
16
+ yKey?: string;
17
+ /** Display label for x-axis */
18
+ xLabel?: string;
19
+ /** Display label for y-axis */
20
+ yLabel?: string;
21
+ /** Chart title */
22
+ title?: string;
23
+ /** Description text below the title */
24
+ subtitle?: string;
25
+ /** Summary stats displayed in the header */
26
+ summaryItems?: ChartSummaryItem[];
27
+ /** Chart area height in pixels */
28
+ height?: number;
29
+ /** Additional CSS classes on the wrapper */
30
+ className?: string;
31
+ }
32
+ /**
33
+ * Scatter chart built on Recharts with design-system tokens.
34
+ * Plots one or more datasets as point clouds on an X/Y grid.
35
+ */
36
+ export declare const ScatterChart: ({ datasets, xKey, yKey, xLabel, yLabel, title, subtitle, summaryItems, height, className, }: ScatterChartProps) => import("react").JSX.Element;
@@ -0,0 +1,109 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { useCallback } from "react";
3
+ import { ResponsiveContainer, ScatterChart as ScatterChart$1, CartesianGrid, XAxis, YAxis, ZAxis, Tooltip, Scatter, Legend } from "recharts";
4
+ import "./Chart.css";
5
+ const PALETTE = [
6
+ "#118AB2",
7
+ // teal-07
8
+ "#06D6A0",
9
+ // green-07
10
+ "#EF476F",
11
+ // red-07
12
+ "#FFD166",
13
+ // yellow-07
14
+ "#9E47EF"
15
+ // purple-07
16
+ ];
17
+ function getCSSVar(name, fallback) {
18
+ if (typeof window === "undefined") return fallback;
19
+ return getComputedStyle(document.documentElement).getPropertyValue(name).trim() || fallback;
20
+ }
21
+ function ScatterTooltip({ active, payload, xLabel, yLabel }) {
22
+ if (!active || !payload?.length) return null;
23
+ const xEntry = payload.find((p) => p.dataKey === payload[0]?.dataKey);
24
+ const yEntry = payload.find((p) => p.name === yLabel) || payload[1];
25
+ return /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip", children: [
26
+ /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip-row", children: [
27
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-name", children: xLabel }),
28
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-value", children: xEntry?.value?.toLocaleString() })
29
+ ] }),
30
+ yEntry && /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip-row", children: [
31
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-name", children: yLabel }),
32
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-value", children: yEntry.value?.toLocaleString() })
33
+ ] })
34
+ ] });
35
+ }
36
+ const ScatterChart = ({
37
+ datasets,
38
+ xKey = "x",
39
+ yKey = "y",
40
+ xLabel = "X",
41
+ yLabel = "Y",
42
+ title,
43
+ subtitle,
44
+ summaryItems,
45
+ height = 350,
46
+ className = ""
47
+ }) => {
48
+ const baseClass = "ds-chart";
49
+ const classes = [baseClass, className].filter(Boolean).join(" ");
50
+ const textSecondary = getCSSVar("--color-text-secondary", "#A2A2A2");
51
+ const gridColor = getCSSVar("--color-divider", "#232323");
52
+ const renderTooltip = useCallback(
53
+ /* eslint-disable-next-line @typescript-eslint/no-explicit-any */
54
+ (props) => /* @__PURE__ */ jsx(ScatterTooltip, { ...props, xLabel, yLabel }),
55
+ [xLabel, yLabel]
56
+ );
57
+ return /* @__PURE__ */ jsxs("div", { className: classes, children: [
58
+ (title || subtitle || summaryItems) && /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header`, children: [
59
+ /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header-text`, children: [
60
+ title && /* @__PURE__ */ jsx("h3", { className: `${baseClass}__title`, children: title }),
61
+ subtitle && /* @__PURE__ */ jsx("p", { className: `${baseClass}__subtitle`, children: subtitle })
62
+ ] }),
63
+ summaryItems && summaryItems.length > 0 && /* @__PURE__ */ jsx("div", { className: `${baseClass}__summary`, children: summaryItems.map((item, i) => /* @__PURE__ */ jsxs("div", { className: `${baseClass}__summary-item`, children: [
64
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-label`, children: item.label }),
65
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-value`, children: typeof item.value === "number" ? item.value.toLocaleString() : item.value })
66
+ ] }, i)) })
67
+ ] }),
68
+ /* @__PURE__ */ jsx("div", { className: `${baseClass}__body`, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height, children: /* @__PURE__ */ jsxs(ScatterChart$1, { margin: { top: 8, right: 4, bottom: 0, left: -12 }, children: [
69
+ /* @__PURE__ */ jsx(CartesianGrid, { stroke: gridColor }),
70
+ /* @__PURE__ */ jsx(
71
+ XAxis,
72
+ {
73
+ type: "number",
74
+ dataKey: xKey,
75
+ name: xLabel,
76
+ tick: { fill: textSecondary, fontSize: 12 },
77
+ tickLine: false,
78
+ axisLine: { stroke: gridColor }
79
+ }
80
+ ),
81
+ /* @__PURE__ */ jsx(
82
+ YAxis,
83
+ {
84
+ type: "number",
85
+ dataKey: yKey,
86
+ name: yLabel,
87
+ tick: { fill: textSecondary, fontSize: 12 },
88
+ tickLine: false,
89
+ axisLine: false
90
+ }
91
+ ),
92
+ /* @__PURE__ */ jsx(ZAxis, { range: [48, 48] }),
93
+ /* @__PURE__ */ jsx(Tooltip, { content: renderTooltip }),
94
+ datasets.map((ds, i) => /* @__PURE__ */ jsx(
95
+ Scatter,
96
+ {
97
+ name: ds.name,
98
+ data: ds.data,
99
+ fill: ds.color || PALETTE[i % PALETTE.length]
100
+ },
101
+ ds.name
102
+ )),
103
+ datasets.length > 1 && /* @__PURE__ */ jsx(Legend, { wrapperStyle: { color: textSecondary, fontSize: 12 } })
104
+ ] }) }) })
105
+ ] });
106
+ };
107
+ export {
108
+ ScatterChart
109
+ };
@@ -0,0 +1,34 @@
1
+ import { ChartSummaryItem } from './BarChart';
2
+ export interface BarSeriesConfig {
3
+ /** Key in data for this series */
4
+ dataKey: string;
5
+ /** Display name (shown in tooltip & legend) */
6
+ label: string;
7
+ /** Bar fill colour */
8
+ color?: string;
9
+ }
10
+ export interface StackedBarChartProps {
11
+ /** Array of data objects */
12
+ data: Record<string, unknown>[];
13
+ /** Key in data for x-axis values */
14
+ xKey?: string;
15
+ /** One or more bar series to render (stacked) */
16
+ series: BarSeriesConfig[];
17
+ /** Chart title */
18
+ title?: string;
19
+ /** Description text below the title */
20
+ subtitle?: string;
21
+ /** Summary stats displayed in the header */
22
+ summaryItems?: ChartSummaryItem[];
23
+ /** Chart area height in pixels */
24
+ height?: number;
25
+ /** Y-axis tick formatter */
26
+ yAxisFormatter?: (value: number) => string;
27
+ /** Additional CSS classes on the wrapper */
28
+ className?: string;
29
+ }
30
+ /**
31
+ * Stacked bar chart built on Recharts with design-system tokens.
32
+ * Supports multiple series stacked on top of each other.
33
+ */
34
+ export declare const StackedBarChart: ({ data, xKey, series, title, subtitle, summaryItems, height, yAxisFormatter, className, }: StackedBarChartProps) => import("react").JSX.Element;
@@ -0,0 +1,111 @@
1
+ import { jsx, jsxs } from "react/jsx-runtime";
2
+ import { useCallback } from "react";
3
+ import { ResponsiveContainer, BarChart, CartesianGrid, XAxis, YAxis, Tooltip, Bar } from "recharts";
4
+ import "./Chart.css";
5
+ function getCSSVar(name, fallback) {
6
+ if (typeof window === "undefined") return fallback;
7
+ return getComputedStyle(document.documentElement).getPropertyValue(name).trim() || fallback;
8
+ }
9
+ function getDefaultColors() {
10
+ if (typeof window === "undefined") {
11
+ return ["#118AB2", "#06D6A0", "#FFD166", "#EF476F", "#9E47EF", "#EF8247"];
12
+ }
13
+ const get = (v, fb) => getComputedStyle(document.documentElement).getPropertyValue(v).trim() || fb;
14
+ return [
15
+ get("--color-action-primary-bg", "#118AB2"),
16
+ get("--color-core-accent-mint", "#06D6A0"),
17
+ get("--color-core-accent-gold", "#FFD166"),
18
+ get("--color-core-accent-coral", "#EF476F"),
19
+ get("--color-core-accent-violet", "#9E47EF"),
20
+ get("--color-core-accent-amber", "#EF8247")
21
+ ];
22
+ }
23
+ function StackedTooltip({ active, payload, label }) {
24
+ if (!active || !payload?.length) return null;
25
+ return /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip", children: [
26
+ /* @__PURE__ */ jsx("div", { className: "ds-chart__tooltip-label", children: label }),
27
+ payload.map((entry, i) => /* @__PURE__ */ jsxs("div", { className: "ds-chart__tooltip-row", children: [
28
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-dot", style: { backgroundColor: entry.color } }),
29
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-name", children: entry.name }),
30
+ /* @__PURE__ */ jsx("span", { className: "ds-chart__tooltip-value", children: entry.value?.toLocaleString() })
31
+ ] }, i))
32
+ ] });
33
+ }
34
+ const StackedBarChart = ({
35
+ data,
36
+ xKey = "label",
37
+ series,
38
+ title,
39
+ subtitle,
40
+ summaryItems,
41
+ height = 350,
42
+ yAxisFormatter,
43
+ className = ""
44
+ }) => {
45
+ const baseClass = "ds-chart";
46
+ const classes = [baseClass, className].filter(Boolean).join(" ");
47
+ const textSecondary = getCSSVar("--color-text-secondary", "#A2A2A2");
48
+ const gridColor = getCSSVar("--color-divider", "#232323");
49
+ const cursorColor = getCSSVar("--color-bg-container-secondary", "#303030");
50
+ const defaultColors = getDefaultColors();
51
+ const renderTooltip = useCallback(
52
+ /* eslint-disable-next-line @typescript-eslint/no-explicit-any */
53
+ (props) => /* @__PURE__ */ jsx(StackedTooltip, { ...props }),
54
+ []
55
+ );
56
+ return /* @__PURE__ */ jsxs("div", { className: classes, children: [
57
+ (title || subtitle || summaryItems) && /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header`, children: [
58
+ /* @__PURE__ */ jsxs("div", { className: `${baseClass}__header-text`, children: [
59
+ title && /* @__PURE__ */ jsx("h3", { className: `${baseClass}__title`, children: title }),
60
+ subtitle && /* @__PURE__ */ jsx("p", { className: `${baseClass}__subtitle`, children: subtitle })
61
+ ] }),
62
+ summaryItems && summaryItems.length > 0 && /* @__PURE__ */ jsx("div", { className: `${baseClass}__summary`, children: summaryItems.map((item, i) => /* @__PURE__ */ jsxs("div", { className: `${baseClass}__summary-item`, children: [
63
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-label`, children: item.label }),
64
+ /* @__PURE__ */ jsx("span", { className: `${baseClass}__summary-value`, children: typeof item.value === "number" ? item.value.toLocaleString() : item.value })
65
+ ] }, i)) })
66
+ ] }),
67
+ /* @__PURE__ */ jsx("div", { className: `${baseClass}__body`, children: /* @__PURE__ */ jsx(ResponsiveContainer, { width: "100%", height, children: /* @__PURE__ */ jsxs(BarChart, { data, margin: { top: 8, right: 4, bottom: 0, left: -12 }, children: [
68
+ /* @__PURE__ */ jsx(CartesianGrid, { vertical: false, stroke: gridColor }),
69
+ /* @__PURE__ */ jsx(
70
+ XAxis,
71
+ {
72
+ dataKey: xKey,
73
+ tick: { fill: textSecondary, fontSize: 12 },
74
+ tickLine: false,
75
+ axisLine: { stroke: gridColor }
76
+ }
77
+ ),
78
+ /* @__PURE__ */ jsx(
79
+ YAxis,
80
+ {
81
+ tick: { fill: textSecondary, fontSize: 12 },
82
+ tickLine: false,
83
+ axisLine: false,
84
+ tickFormatter: yAxisFormatter
85
+ }
86
+ ),
87
+ /* @__PURE__ */ jsx(
88
+ Tooltip,
89
+ {
90
+ content: renderTooltip,
91
+ cursor: { fill: cursorColor, opacity: 0.4 }
92
+ }
93
+ ),
94
+ series.map((s, i) => /* @__PURE__ */ jsx(
95
+ Bar,
96
+ {
97
+ dataKey: s.dataKey,
98
+ name: s.label,
99
+ fill: s.color || defaultColors[i % defaultColors.length],
100
+ stackId: "stack",
101
+ radius: i === series.length - 1 ? [3, 3, 0, 0] : [0, 0, 0, 0],
102
+ maxBarSize: 32
103
+ },
104
+ s.dataKey
105
+ ))
106
+ ] }) }) })
107
+ ] });
108
+ };
109
+ export {
110
+ StackedBarChart
111
+ };
@@ -0,0 +1,33 @@
1
+ import { ChartSummaryItem } from './BarChart';
2
+ export interface TreemapDataItem {
3
+ /** Display name for the node */
4
+ name: string;
5
+ /** Numeric size — determines rectangle area */
6
+ size: number;
7
+ /** Optional fill colour */
8
+ color?: string;
9
+ /** Nested children for hierarchical data */
10
+ children?: TreemapDataItem[];
11
+ [key: string]: unknown;
12
+ }
13
+ export interface TreemapProps {
14
+ /** Hierarchical data — each item needs `name` and `size` (or `children`) */
15
+ data: TreemapDataItem[];
16
+ /** Key used for sizing rectangles */
17
+ dataKey?: string;
18
+ /** Chart title */
19
+ title?: string;
20
+ /** Description text below the title */
21
+ subtitle?: string;
22
+ /** Summary stats displayed in the header */
23
+ summaryItems?: ChartSummaryItem[];
24
+ /** Chart area height in pixels */
25
+ height?: number;
26
+ /** Additional CSS classes on the wrapper */
27
+ className?: string;
28
+ }
29
+ /**
30
+ * Treemap chart built on Recharts with design-system tokens.
31
+ * Displays hierarchical data as nested coloured rectangles sized by value.
32
+ */
33
+ export declare const Treemap: ({ data, dataKey, title, subtitle, summaryItems, height, className, }: TreemapProps) => import("react").JSX.Element;