@thebuoyant-tsdev/mui-ts-library 3.26.0 → 3.27.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 (23) hide show
  1. package/README.de.md +22 -0
  2. package/README.md +22 -0
  3. package/dist/components/chord-chart/ChordChart.d.ts +1 -1
  4. package/dist/components/chord-chart/ChordChart.js +138 -128
  5. package/dist/components/chord-chart/ChordChart.types.d.ts +4 -0
  6. package/dist/components/circle-packing-chart/CirclePackingChart.d.ts +1 -1
  7. package/dist/components/circle-packing-chart/CirclePackingChart.js +142 -142
  8. package/dist/components/circle-packing-chart/CirclePackingChart.types.d.ts +2 -0
  9. package/dist/components/gantt-chart/GanttChart.js +29 -29
  10. package/dist/components/horizontal-tree-chart/HorizontalTreeChart.d.ts +1 -1
  11. package/dist/components/horizontal-tree-chart/HorizontalTreeChart.js +131 -125
  12. package/dist/components/horizontal-tree-chart/HorizontalTreeChart.types.d.ts +2 -0
  13. package/dist/components/radial-stacked-bar-chart/RadialStackedBarChart.d.ts +1 -1
  14. package/dist/components/radial-stacked-bar-chart/RadialStackedBarChart.js +60 -50
  15. package/dist/components/radial-stacked-bar-chart/RadialStackedBarChart.types.d.ts +2 -0
  16. package/dist/components/radial-tree-chart/RadialTreeChart.d.ts +1 -1
  17. package/dist/components/radial-tree-chart/RadialTreeChart.js +115 -111
  18. package/dist/components/radial-tree-chart/RadialTreeChart.types.d.ts +2 -0
  19. package/dist/components/sunburst-chart/SunburstChart.d.ts +1 -1
  20. package/dist/components/sunburst-chart/SunburstChart.js +120 -106
  21. package/dist/components/sunburst-chart/SunburstChart.types.d.ts +2 -0
  22. package/dist/index.cjs +2 -2
  23. package/package.json +1 -1
package/README.de.md CHANGED
@@ -483,6 +483,28 @@ Dieses Projekt folgt [Semantic Versioning](https://semver.org/):
483
483
 
484
484
  ## Changelog
485
485
 
486
+ ### [3.26.1] — 2026-07-13
487
+
488
+ **Behoben**
489
+ - README-Changelog-Abschnitte (EN + DE) fehlten auf npmjs.com die Einträge für `[3.25.0]` und `[3.26.0]`. Keine Code-Änderungen.
490
+
491
+ ---
492
+
493
+ ### [3.26.0] — 2026-07-13
494
+
495
+ **Hinzugefügt**
496
+ - **`PopoverColorPicker`** — Convenience-Wrapper, der einen farbigen Swatch-Trigger-Button mit einem MUI-Popover und dem vollen `ColorPicker` kombiniert. Kein `Popover`, `anchorEl` oder Open/Close-State nötig — nur `value` + `onChange`. Alle `ColorPicker`-Props werden direkt durchgereicht. Neue Props: `swatchSize` (Standard `28`) und `swatchShape` (`"square"` | `"circle"`). Vollständig barrierefrei. Neue Exports: `popoverColorPickerClasses`. Vollständig rückwärtskompatibel. Siehe [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.de.md) für Details.
497
+
498
+ ---
499
+
500
+ ### [3.25.0] — 2026-07-12
501
+
502
+ **Hinzugefügt**
503
+ - **`JsonEditor` — Download-Button:** Neuer Toolbar-Button der den Editor-Inhalt als `.json`-Datei exportiert. Standardmäßig sichtbar (`showDownload: true`). Dateiname per `downloadFilename` steuerbar (Standard `"file.json"`). Mit `toolbarConfig={{ showDownload: false }}` ausblendbar. Vollständig rückwärtskompatibel. Siehe [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.de.md) für Details.
504
+ - **`GanttChart` — Tastaturnavigation:** Das Task-Panel ist jetzt per Tastatur bedienbar — `Tab` fokussiert, `↑`/`↓` bewegen die Auswahl, `Enter` öffnet den Bearbeiten-Dialog, `Escape` hebt die Auswahl auf. Keine neuen Props erforderlich. Siehe [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.de.md) für Details.
505
+
506
+ ---
507
+
486
508
  ### [3.24.1] — 2026-07-10
487
509
 
488
510
  **Behoben**
package/README.md CHANGED
@@ -483,6 +483,28 @@ This project follows [Semantic Versioning](https://semver.org/):
483
483
 
484
484
  ## Changelog
485
485
 
486
+ ### [3.26.1] — 2026-07-13
487
+
488
+ **Fixed**
489
+ - README changelog sections (EN + DE) were missing the `[3.25.0]` and `[3.26.0]` entries on npmjs.com. No code changes.
490
+
491
+ ---
492
+
493
+ ### [3.26.0] — 2026-07-13
494
+
495
+ **Added**
496
+ - **`PopoverColorPicker`** — a convenience wrapper that combines a colored swatch trigger button with a MUI Popover containing the full `ColorPicker`. No `Popover`, `anchorEl`, or open/close state needed — just `value` + `onChange`. All `ColorPicker` props pass through directly. New props: `swatchSize` (default `28`) and `swatchShape` (`"square"` | `"circle"`). Fully accessible (aria-expanded, aria-haspopup, keyboard support). New exports: `popoverColorPickerClasses`. Fully backwards-compatible. See [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.md) for details.
497
+
498
+ ---
499
+
500
+ ### [3.25.0] — 2026-07-12
501
+
502
+ **Added**
503
+ - **`JsonEditor` — Download button:** New toolbar button that exports the current editor content as a `.json` file. Shown by default (`showDownload: true`). Control the filename via `downloadFilename` (default `"file.json"`). Add `toolbarConfig={{ showDownload: false }}` to opt out. Fully backwards-compatible. See [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.md) for details.
504
+ - **`GanttChart` — Keyboard Navigation:** The task panel is now keyboard-accessible — `Tab` to focus, `↑`/`↓` to move selection, `Enter` to open the edit dialog, `Escape` to deselect. No new props required. See [Full Changelog](https://github.com/thebuoyant/mui-ts-library/blob/main/CHANGELOG.md) for details.
505
+
506
+ ---
507
+
486
508
  ### [3.24.1] — 2026-07-10
487
509
 
488
510
  **Fixed**
@@ -1,5 +1,5 @@
1
1
  import { type ChordChartProps } from "./ChordChart.types";
2
- export declare function ChordChart({ data, size, innerRadius, ringThickness, padAngle, ribbonPadAngle, sortSubgroups, sortChords, chartColors, groupColorConfigs, showGroupLabels, labelOffset, ribbonOpacity, ribbonBlendMode, directed, valueDecimalCount, valueDecimalSeparator, valueThousandsSeparator, valueFormatter, onGroupClick, onChordClick, zoomable, disabled, translation, }: ChordChartProps): import("react/jsx-runtime").JSX.Element;
2
+ export declare function ChordChart({ data, size, innerRadius, ringThickness, padAngle, ribbonPadAngle, sortSubgroups, sortChords, chartColors, groupColorConfigs, showGroupLabels, labelOffset, ribbonOpacity, ribbonBlendMode, directed, valueDecimalCount, valueDecimalSeparator, valueThousandsSeparator, valueFormatter, onGroupClick, onGroupHover, onChordClick, onChordHover, zoomable, disabled, translation, }: ChordChartProps): import("react/jsx-runtime").JSX.Element;
3
3
  export declare namespace ChordChart {
4
4
  var displayName: string;
5
5
  }
@@ -1,19 +1,19 @@
1
1
  import { DEFAULT_CHORD_CHART_TRANSLATION as e } from "./ChordChart.types.js";
2
2
  import { useCallback as t, useLayoutEffect as n, useMemo as r, useRef as i, useState as a } from "react";
3
- import { Box as o, Tooltip as s, Typography as c, useTheme as ee } from "@mui/material";
4
- import { jsx as l, jsxs as u } from "react/jsx-runtime";
5
- import * as d from "d3";
3
+ import { Box as o, Tooltip as s, Typography as c, useTheme as l } from "@mui/material";
4
+ import { jsx as u, jsxs as d } from "react/jsx-runtime";
5
+ import * as f from "d3";
6
6
  //#region src/components/chord-chart/ChordChart.tsx
7
- function f(e, t = 0, n = ".", r = ",") {
7
+ function p(e, t = 0, n = ".", r = ",") {
8
8
  if (!isFinite(e)) return String(e);
9
9
  let [i, a] = e.toFixed(Math.max(0, t)).split("."), o = i.replace(/\B(?=(\d{3})+(?!\d))/g, r);
10
10
  return a ? `${o}${n}${a}` : o;
11
11
  }
12
- function te({ name: e, valueOut: t, valueIn: n, fmt: r }) {
13
- return /* @__PURE__ */ u(o, {
12
+ function m({ name: e, valueOut: t, valueIn: n, fmt: r }) {
13
+ return /* @__PURE__ */ d(o, {
14
14
  sx: { py: .25 },
15
15
  children: [
16
- /* @__PURE__ */ l(c, {
16
+ /* @__PURE__ */ u(c, {
17
17
  variant: "caption",
18
18
  sx: {
19
19
  fontWeight: "bold",
@@ -21,7 +21,7 @@ function te({ name: e, valueOut: t, valueIn: n, fmt: r }) {
21
21
  },
22
22
  children: e
23
23
  }),
24
- /* @__PURE__ */ u(c, {
24
+ /* @__PURE__ */ d(c, {
25
25
  variant: "caption",
26
26
  sx: {
27
27
  display: "block",
@@ -29,7 +29,7 @@ function te({ name: e, valueOut: t, valueIn: n, fmt: r }) {
29
29
  },
30
30
  children: [r(t), " outgoing →"]
31
31
  }),
32
- /* @__PURE__ */ u(c, {
32
+ /* @__PURE__ */ d(c, {
33
33
  variant: "caption",
34
34
  sx: {
35
35
  display: "block",
@@ -40,11 +40,11 @@ function te({ name: e, valueOut: t, valueIn: n, fmt: r }) {
40
40
  ]
41
41
  });
42
42
  }
43
- function ne({ sourceName: e, targetName: t, sourceValue: n, targetValue: r, directed: i, fmt: a }) {
44
- return /* @__PURE__ */ u(o, {
43
+ function h({ sourceName: e, targetName: t, sourceValue: n, targetValue: r, directed: i, fmt: a }) {
44
+ return /* @__PURE__ */ d(o, {
45
45
  sx: { py: .25 },
46
46
  children: [
47
- /* @__PURE__ */ u(c, {
47
+ /* @__PURE__ */ d(c, {
48
48
  variant: "caption",
49
49
  sx: {
50
50
  fontWeight: "bold",
@@ -56,7 +56,7 @@ function ne({ sourceName: e, targetName: t, sourceValue: n, targetValue: r, dire
56
56
  t
57
57
  ]
58
58
  }),
59
- /* @__PURE__ */ l(c, {
59
+ /* @__PURE__ */ u(c, {
60
60
  variant: "caption",
61
61
  sx: {
62
62
  display: "block",
@@ -64,7 +64,7 @@ function ne({ sourceName: e, targetName: t, sourceValue: n, targetValue: r, dire
64
64
  },
65
65
  children: a(n)
66
66
  }),
67
- i && r > 0 && r !== n && /* @__PURE__ */ u(c, {
67
+ i && r > 0 && r !== n && /* @__PURE__ */ d(c, {
68
68
  variant: "caption",
69
69
  sx: {
70
70
  display: "block",
@@ -82,24 +82,24 @@ function ne({ sourceName: e, targetName: t, sourceValue: n, targetValue: r, dire
82
82
  ]
83
83
  });
84
84
  }
85
- function p({ data: c, size: p = 500, innerRadius: m, ringThickness: h = 20, padAngle: g, ribbonPadAngle: _, sortSubgroups: v = "descending", sortChords: y = "descending", chartColors: b, groupColorConfigs: x, showGroupLabels: re = !0, labelOffset: S = 8, ribbonOpacity: C = .75, ribbonBlendMode: w, directed: T = !0, valueDecimalCount: E = 0, valueDecimalSeparator: D = ".", valueThousandsSeparator: O = ",", valueFormatter: k, onGroupClick: ie, onChordClick: ae, zoomable: A = !1, disabled: j = !1, translation: oe }) {
86
- let M = ee(), se = {
85
+ function g({ data: c, size: g = 500, innerRadius: _, ringThickness: ee = 20, padAngle: te, ribbonPadAngle: ne, sortSubgroups: v = "descending", sortChords: y = "descending", chartColors: b, groupColorConfigs: x, showGroupLabels: re = !0, labelOffset: ie = 8, ribbonOpacity: ae = .75, ribbonBlendMode: oe, directed: S = !0, valueDecimalCount: C = 0, valueDecimalSeparator: w = ".", valueThousandsSeparator: T = ",", valueFormatter: E, onGroupClick: D, onGroupHover: O, onChordClick: k, onChordHover: A, zoomable: j = !1, disabled: M = !1, translation: se }) {
86
+ let N = l(), ce = {
87
87
  ...e,
88
- ...oe
89
- }, ce = c.length === 0, le = w ?? (M.palette.mode === "dark" ? "normal" : "multiply"), ue = [
90
- M.palette.primary.main,
91
- M.palette.secondary.main,
92
- M.palette.error.main,
93
- M.palette.warning.main,
94
- M.palette.success.main,
95
- M.palette.info.main
96
- ], N = b && b.length > 0 ? b : ue, de = m ?? Math.min(p, p) * .5 - 90, P = Math.max(10, de), F = P + Math.max(1, h), I = g ?? 10 / P, L = _ ?? 1 / P, R = t((e) => k ? k(e) : f(e, E, D, O), [
97
- k,
88
+ ...se
89
+ }, le = c.length === 0, ue = oe ?? (N.palette.mode === "dark" ? "normal" : "multiply"), de = [
90
+ N.palette.primary.main,
91
+ N.palette.secondary.main,
92
+ N.palette.error.main,
93
+ N.palette.warning.main,
94
+ N.palette.success.main,
95
+ N.palette.info.main
96
+ ], P = b && b.length > 0 ? b : de, fe = _ ?? Math.min(g, g) * .5 - 90, F = Math.max(10, fe), I = F + Math.max(1, ee), L = te ?? 10 / F, R = ne ?? 1 / F, z = t((e) => E ? E(e) : p(e, C, w, T), [
98
97
  E,
99
- D,
100
- O
101
- ]), { names: z, matrix: B } = r(() => {
102
- let e = d.sort(d.union(c.map((e) => e.source), c.map((e) => e.target))), t = new Map(e.map((e, t) => [e, t])), n = Array.from({ length: e.length }, () => Array(e.length).fill(0));
98
+ C,
99
+ w,
100
+ T
101
+ ]), { names: B, matrix: V } = r(() => {
102
+ let e = f.sort(f.union(c.map((e) => e.source), c.map((e) => e.target))), t = new Map(e.map((e, t) => [e, t])), n = Array.from({ length: e.length }, () => Array(e.length).fill(0));
103
103
  for (let { source: e, target: r, value: i } of c) {
104
104
  let a = t.get(e), o = t.get(r);
105
105
  a == null || o == null || (n[a][o] += i);
@@ -108,187 +108,197 @@ function p({ data: c, size: p = 500, innerRadius: m, ringThickness: h = 20, padA
108
108
  names: e,
109
109
  matrix: n
110
110
  };
111
- }, [c]), V = r(() => {
112
- let e = (T ? d.chordDirected() : d.chord()).padAngle(I);
113
- return v === "ascending" && (e = e.sortSubgroups(d.ascending)), v === "descending" && (e = e.sortSubgroups(d.descending)), y === "ascending" && (e = e.sortChords(d.ascending)), y === "descending" && (e = e.sortChords(d.descending)), e(B);
111
+ }, [c]), H = r(() => {
112
+ let e = (S ? f.chordDirected() : f.chord()).padAngle(L);
113
+ return v === "ascending" && (e = e.sortSubgroups(f.ascending)), v === "descending" && (e = e.sortSubgroups(f.descending)), y === "ascending" && (e = e.sortChords(f.ascending)), y === "descending" && (e = e.sortChords(f.descending)), e(V);
114
114
  }, [
115
- B,
116
- I,
117
- T,
115
+ V,
116
+ L,
117
+ S,
118
118
  v,
119
119
  y
120
- ]), fe = r(() => d.arc().innerRadius(P).outerRadius(F), [P, F]), H = r(() => (T ? d.ribbonArrow() : d.ribbon()).radius(P - 1).padAngle(L), [
121
- P,
122
- L,
123
- T
124
- ]), pe = t((e) => H({
120
+ ]), pe = r(() => f.arc().innerRadius(F).outerRadius(I), [F, I]), U = r(() => (S ? f.ribbonArrow() : f.ribbon()).radius(F - 1).padAngle(R), [
121
+ F,
122
+ R,
123
+ S
124
+ ]), me = t((e) => U({
125
125
  source: {
126
126
  startAngle: e.source.startAngle,
127
127
  endAngle: e.source.endAngle,
128
- radius: P - 1
128
+ radius: F - 1
129
129
  },
130
130
  target: {
131
131
  startAngle: e.target.startAngle,
132
132
  endAngle: e.target.endAngle,
133
- radius: P - 1
133
+ radius: F - 1
134
134
  }
135
- }) ?? "", [H, P]), U = r(() => d.scaleOrdinal().domain(d.range(z.length)).range(N.length >= z.length ? N : [...Array(Math.ceil(z.length / N.length))].flatMap(() => N).slice(0, z.length)), [N, z.length]), W = t((e) => x?.[z[e]]?.fill ?? U(e), [
135
+ }) ?? "", [U, F]), W = r(() => f.scaleOrdinal().domain(f.range(B.length)).range(P.length >= B.length ? P : [...Array(Math.ceil(B.length / P.length))].flatMap(() => P).slice(0, B.length)), [P, B.length]), G = t((e) => x?.[B[e]]?.fill ?? W(e), [
136
136
  x,
137
- z,
138
- U
139
- ]), G = i(null), [K, q] = a(`-${p / 2} -${p / 2} ${p} ${p}`), [J, Y] = a(1), me = r(() => {
140
- if (J === 1) return K;
141
- let [e, t, n, r] = K.split(" ").map(Number), i = n / J, a = r / J;
137
+ B,
138
+ W
139
+ ]), K = i(null), [q, J] = a(`-${g / 2} -${g / 2} ${g} ${g}`), [Y, X] = a(1), he = r(() => {
140
+ if (Y === 1) return q;
141
+ let [e, t, n, r] = q.split(" ").map(Number), i = n / Y, a = r / Y;
142
142
  return `${e + (n - i) / 2} ${t + (r - a) / 2} ${i} ${a}`;
143
- }, [K, J]);
143
+ }, [q, Y]);
144
144
  n(() => {
145
- let e = G.current;
145
+ let e = K.current;
146
146
  if (!e) return;
147
147
  let t = requestAnimationFrame(() => {
148
148
  try {
149
149
  let t = e.getBBox();
150
- q(`${t.x - 8} ${t.y - 8} ${t.width + 16} ${t.height + 16}`);
150
+ J(`${t.x - 8} ${t.y - 8} ${t.width + 16} ${t.height + 16}`);
151
151
  } catch {
152
- q(`-${p / 2} -${p / 2} ${p} ${p}`);
152
+ J(`-${g / 2} -${g / 2} ${g} ${g}`);
153
153
  }
154
154
  });
155
155
  return () => cancelAnimationFrame(t);
156
156
  }, [
157
- p,
158
- P,
157
+ g,
159
158
  F,
160
- z.length,
161
- V
159
+ I,
160
+ B.length,
161
+ H
162
162
  ]);
163
- let [X, Z] = a(null), he = t((e) => ({
164
- name: z[e.index],
163
+ let [Z, Q] = a(null), ge = t((e) => ({
164
+ name: B[e.index],
165
165
  index: e.index,
166
- valueOut: d.sum(V, (t) => (t.source.index === e.index ? t.source.value : 0) + (!T && t.target.index === e.index ? t.target.value : 0)),
167
- valueIn: d.sum(V, (t) => (t.target.index === e.index ? t.source.value : 0) + (!T && t.source.index === e.index ? t.target.value : 0))
166
+ valueOut: f.sum(H, (t) => (t.source.index === e.index ? t.source.value : 0) + (!S && t.target.index === e.index ? t.target.value : 0)),
167
+ valueIn: f.sum(H, (t) => (t.target.index === e.index ? t.source.value : 0) + (!S && t.source.index === e.index ? t.target.value : 0))
168
168
  }), [
169
- z,
170
- V,
171
- T
172
- ]), ge = t((e) => ({
169
+ B,
170
+ H,
171
+ S
172
+ ]), _e = t((e) => ({
173
173
  source: {
174
- name: z[e.source.index],
174
+ name: B[e.source.index],
175
175
  index: e.source.index,
176
176
  value: e.source.value
177
177
  },
178
178
  target: {
179
- name: z[e.target.index],
179
+ name: B[e.target.index],
180
180
  index: e.target.index,
181
181
  value: e.target.value
182
182
  }
183
- }), [z]), _e = (e) => {
183
+ }), [B]), ve = (e) => {
184
184
  let t = (e.startAngle + e.endAngle) / 2, n = t * 180 / Math.PI - 90, r = t > Math.PI ? " rotate(180)" : "";
185
- return `rotate(${n}) translate(${F + S})${r}`;
186
- }, Q = (e) => (e.startAngle + e.endAngle) / 2 > Math.PI ? "end" : "start", ve = t((e) => {
187
- if (!A || j || !e.ctrlKey) return;
185
+ return `rotate(${n}) translate(${I + ie})${r}`;
186
+ }, ye = (e) => (e.startAngle + e.endAngle) / 2 > Math.PI ? "end" : "start", be = t((e) => {
187
+ if (!j || M || !e.ctrlKey) return;
188
188
  e.preventDefault();
189
189
  let t = e.deltaY < 0 ? 1.15 : 1 / 1.15;
190
- Y((e) => Math.max(.25, Math.min(8, e * t)));
191
- }, [A, j]);
190
+ X((e) => Math.max(.25, Math.min(8, e * t)));
191
+ }, [j, M]);
192
192
  n(() => {
193
- if (!A) return;
193
+ if (!j) return;
194
194
  let e = (e) => {
195
- e.key === "Escape" && Y(1);
195
+ e.key === "Escape" && X(1);
196
196
  };
197
197
  return window.addEventListener("keydown", e), () => window.removeEventListener("keydown", e);
198
- }, [A]);
198
+ }, [j]);
199
199
  let $ = {
200
200
  followCursor: !0,
201
201
  enterDelay: 50,
202
202
  enterNextDelay: 0,
203
- disableHoverListener: j,
203
+ disableHoverListener: M,
204
204
  slotProps: { tooltip: { sx: { maxWidth: 240 } } }
205
- }, ye = M.palette.text.primary, be = M.typography.fontFamily;
206
- return /* @__PURE__ */ l(o, {
205
+ }, xe = N.palette.text.primary, Se = N.typography.fontFamily;
206
+ return /* @__PURE__ */ u(o, {
207
207
  sx: {
208
208
  display: "inline-flex",
209
- opacity: j ? .5 : 1,
210
- cursor: j ? "not-allowed" : "default",
209
+ opacity: M ? .5 : 1,
210
+ cursor: M ? "not-allowed" : "default",
211
211
  userSelect: "none"
212
212
  },
213
- children: /* @__PURE__ */ l("svg", {
214
- width: p,
215
- height: p,
216
- viewBox: me,
217
- onWheel: ve,
213
+ children: /* @__PURE__ */ u("svg", {
214
+ width: g,
215
+ height: g,
216
+ viewBox: he,
217
+ onWheel: be,
218
218
  style: {
219
- fontFamily: be ?? "sans-serif",
220
- overflow: A && J > 1 ? "hidden" : "visible"
219
+ fontFamily: Se ?? "sans-serif",
220
+ overflow: j && Y > 1 ? "hidden" : "visible"
221
221
  },
222
222
  role: "img",
223
223
  "aria-label": "Chord chart",
224
- children: /* @__PURE__ */ u("g", {
225
- ref: G,
224
+ children: /* @__PURE__ */ d("g", {
225
+ ref: K,
226
226
  children: [
227
- ce && /* @__PURE__ */ l("text", {
227
+ le && /* @__PURE__ */ u("text", {
228
228
  textAnchor: "middle",
229
229
  dy: "0.35em",
230
230
  fontSize: 13,
231
- fill: M.palette.text.secondary,
232
- children: se.noData
231
+ fill: N.palette.text.secondary,
232
+ children: ce.noData
233
233
  }),
234
- /* @__PURE__ */ l("g", { children: V.groups.map((e) => {
235
- let t = he(e), n = X === e.index, r = X !== null && !n;
236
- return /* @__PURE__ */ l(s, {
234
+ /* @__PURE__ */ u("g", { children: H.groups.map((e) => {
235
+ let t = ge(e), n = Z === e.index, r = Z !== null && !n;
236
+ return /* @__PURE__ */ u(s, {
237
237
  ...$,
238
- title: /* @__PURE__ */ l(te, {
238
+ title: /* @__PURE__ */ u(m, {
239
239
  name: t.name,
240
240
  valueOut: t.valueOut,
241
241
  valueIn: t.valueIn,
242
- fmt: R
242
+ fmt: z
243
243
  }),
244
- children: /* @__PURE__ */ u("g", {
245
- style: { cursor: j ? "not-allowed" : "pointer" },
246
- onMouseEnter: () => !j && Z(e.index),
247
- onMouseLeave: () => Z(null),
248
- onClick: (e) => !j && ie?.(t, e),
249
- children: [/* @__PURE__ */ l("path", {
250
- d: fe(e) || "",
251
- fill: W(e.index),
252
- stroke: M.palette.divider,
244
+ children: /* @__PURE__ */ d("g", {
245
+ style: { cursor: M ? "not-allowed" : "pointer" },
246
+ onMouseEnter: (n) => {
247
+ M || (Q(e.index), O?.(t, n));
248
+ },
249
+ onMouseLeave: (e) => {
250
+ Q(null), O?.(null, e);
251
+ },
252
+ onClick: (e) => !M && D?.(t, e),
253
+ children: [/* @__PURE__ */ u("path", {
254
+ d: pe(e) || "",
255
+ fill: G(e.index),
256
+ stroke: N.palette.divider,
253
257
  opacity: r ? .35 : 1,
254
258
  style: { transition: "opacity 0.15s" }
255
- }), re && /* @__PURE__ */ l("text", {
259
+ }), re && /* @__PURE__ */ u("text", {
256
260
  dy: "0.35em",
257
261
  fontSize: 11,
258
- fill: ye,
259
- transform: _e(e),
260
- textAnchor: Q(e),
262
+ fill: xe,
263
+ transform: ve(e),
264
+ textAnchor: ye(e),
261
265
  pointerEvents: "none",
262
- children: z[e.index]
266
+ children: B[e.index]
263
267
  })]
264
268
  })
265
269
  }, `grp-tt-${e.index}`);
266
270
  }) }),
267
- /* @__PURE__ */ l("g", {
268
- fillOpacity: C,
269
- style: { mixBlendMode: le },
270
- children: V.map((e, t) => {
271
- let n = ge(e), r = X === null || e.source.index === X || e.target.index === X;
272
- return /* @__PURE__ */ l(s, {
271
+ /* @__PURE__ */ u("g", {
272
+ fillOpacity: ae,
273
+ style: { mixBlendMode: ue },
274
+ children: H.map((e, t) => {
275
+ let n = _e(e), r = Z === null || e.source.index === Z || e.target.index === Z;
276
+ return /* @__PURE__ */ u(s, {
273
277
  ...$,
274
- title: /* @__PURE__ */ l(ne, {
278
+ title: /* @__PURE__ */ u(h, {
275
279
  sourceName: n.source.name,
276
280
  targetName: n.target.name,
277
281
  sourceValue: n.source.value,
278
282
  targetValue: n.target.value,
279
- directed: T,
280
- fmt: R
283
+ directed: S,
284
+ fmt: z
281
285
  }),
282
- children: /* @__PURE__ */ l("path", {
283
- d: pe(e),
284
- fill: W(e.target.index),
286
+ children: /* @__PURE__ */ u("path", {
287
+ d: me(e),
288
+ fill: G(e.target.index),
285
289
  stroke: "none",
286
290
  opacity: r ? 1 : .12,
287
291
  style: {
288
- cursor: j ? "not-allowed" : "pointer",
292
+ cursor: M ? "not-allowed" : "pointer",
289
293
  transition: "opacity 0.15s"
290
294
  },
291
- onClick: (e) => !j && ae?.(n, e)
295
+ onMouseEnter: (e) => {
296
+ M || A?.(n, e);
297
+ },
298
+ onMouseLeave: (e) => {
299
+ A?.(null, e);
300
+ },
301
+ onClick: (e) => !M && k?.(n, e)
292
302
  })
293
303
  }, `chord-tt-${t}`);
294
304
  })
@@ -298,6 +308,6 @@ function p({ data: c, size: p = 500, innerRadius: m, ringThickness: h = 20, padA
298
308
  })
299
309
  });
300
310
  }
301
- p.displayName = "ChordChart";
311
+ g.displayName = "ChordChart";
302
312
  //#endregion
303
- export { p as ChordChart };
313
+ export { g as ChordChart };
@@ -91,8 +91,12 @@ export type ChordChartProps = {
91
91
  valueFormatter?: (value: number) => string;
92
92
  /** Fired on click of a group arc */
93
93
  onGroupClick?: (info: ChordGroupInfo, event: React.MouseEvent<SVGGElement>) => void;
94
+ /** Fired on mouse enter/leave a group arc — `null` on leave. Use for linked-view highlighting. */
95
+ onGroupHover?: (info: ChordGroupInfo | null, event: React.MouseEvent<SVGGElement> | null) => void;
94
96
  /** Fired on click of a ribbon */
95
97
  onChordClick?: (info: ChordInfo, event: React.MouseEvent<SVGPathElement>) => void;
98
+ /** Fired on mouse enter/leave a ribbon — `null` on leave. Use for linked-view highlighting. */
99
+ onChordHover?: (info: ChordInfo | null, event: React.MouseEvent<SVGPathElement> | null) => void;
96
100
  /** Enable Ctrl / Cmd ⌘ + Scroll visual zoom — clips content at `size` boundary (default: false) */
97
101
  zoomable?: boolean;
98
102
  /** Disables all interactions (default: false) */
@@ -1,5 +1,5 @@
1
1
  import { type CirclePackingChartProps } from "./CirclePackingChart.types";
2
- export declare function CirclePackingChart({ data, size, padding, sortBy, showLabels, showAllLabels, labelFontSize, innerLabelFontSize, labelColor, chartColors, depthColorStart, depthColorEnd, background, duration, zoomable, disabled, onCircleClick, onZoomChange, valueFormatter, translation, }: CirclePackingChartProps): import("react/jsx-runtime").JSX.Element;
2
+ export declare function CirclePackingChart({ data, size, padding, sortBy, showLabels, showAllLabels, labelFontSize, innerLabelFontSize, labelColor, chartColors, depthColorStart, depthColorEnd, background, duration, zoomable, disabled, onCircleClick, onCircleHover, onZoomChange, valueFormatter, translation, }: CirclePackingChartProps): import("react/jsx-runtime").JSX.Element;
3
3
  export declare namespace CirclePackingChart {
4
4
  var displayName: string;
5
5
  }