@x-plat/design-system 0.5.32 → 0.5.34
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.
- package/dist/components/Chart/index.cjs +148 -144
- package/dist/components/Chart/index.css +54 -10
- package/dist/components/Chart/index.js +148 -144
- package/dist/components/index.cjs +148 -144
- package/dist/components/index.css +54 -10
- package/dist/components/index.js +148 -144
- package/dist/index.cjs +148 -144
- package/dist/index.css +54 -10
- package/dist/index.js +148 -144
- package/package.json +1 -1
|
@@ -116,45 +116,35 @@ var useChartAnimation = (containerRef, dataKey) => {
|
|
|
116
116
|
prevDataKey.current = dataKey;
|
|
117
117
|
if (prefersReducedMotion()) return;
|
|
118
118
|
setAnimate(false);
|
|
119
|
-
requestAnimationFrame(() =>
|
|
119
|
+
requestAnimationFrame(() => {
|
|
120
|
+
requestAnimationFrame(() => setAnimate(true));
|
|
121
|
+
});
|
|
120
122
|
}
|
|
121
123
|
}, [dataKey]);
|
|
122
124
|
return animate || prefersReducedMotion();
|
|
123
125
|
};
|
|
126
|
+
var TOOLTIP_OFFSET = 12;
|
|
124
127
|
var useChartTooltip = (enabled) => {
|
|
125
128
|
const [tooltip, setTooltip] = React.useState({
|
|
126
129
|
visible: false,
|
|
127
|
-
|
|
128
|
-
|
|
130
|
+
clientX: 0,
|
|
131
|
+
clientY: 0,
|
|
129
132
|
content: ""
|
|
130
133
|
});
|
|
131
134
|
const containerRef = React.useRef(null);
|
|
132
135
|
const rafRef = React.useRef(0);
|
|
133
136
|
const move = React.useCallback((e) => {
|
|
134
137
|
if (!enabled) return;
|
|
135
|
-
const
|
|
136
|
-
const
|
|
138
|
+
const cx = e.clientX;
|
|
139
|
+
const cy = e.clientY;
|
|
137
140
|
cancelAnimationFrame(rafRef.current);
|
|
138
141
|
rafRef.current = requestAnimationFrame(() => {
|
|
139
|
-
|
|
140
|
-
if (!rect) return;
|
|
141
|
-
setTooltip((prev) => ({
|
|
142
|
-
...prev,
|
|
143
|
-
x: clientX - rect.left,
|
|
144
|
-
y: clientY - rect.top - 12
|
|
145
|
-
}));
|
|
142
|
+
setTooltip((prev) => ({ ...prev, clientX: cx, clientY: cy }));
|
|
146
143
|
});
|
|
147
144
|
}, [enabled]);
|
|
148
145
|
const show = React.useCallback((e, content) => {
|
|
149
146
|
if (!enabled) return;
|
|
150
|
-
|
|
151
|
-
if (!rect) return;
|
|
152
|
-
setTooltip({
|
|
153
|
-
visible: true,
|
|
154
|
-
x: e.clientX - rect.left,
|
|
155
|
-
y: e.clientY - rect.top - 12,
|
|
156
|
-
content
|
|
157
|
-
});
|
|
147
|
+
setTooltip({ visible: true, clientX: e.clientX, clientY: e.clientY, content });
|
|
158
148
|
}, [enabled]);
|
|
159
149
|
const hide = React.useCallback(() => {
|
|
160
150
|
cancelAnimationFrame(rafRef.current);
|
|
@@ -188,14 +178,14 @@ var AxisLabels = React.memo(({ labels, count, chartW, height }) => {
|
|
|
188
178
|
AxisLabels.displayName = "AxisLabels";
|
|
189
179
|
var useCrosshair = (seriesPoints, entries, labels, chartH) => {
|
|
190
180
|
const [activeIndex, setActiveIndex] = React.useState(null);
|
|
191
|
-
const [mouseX, setMouseX] = React.useState(null);
|
|
192
181
|
const handleMouseMove = React.useCallback((e) => {
|
|
193
182
|
const svg = e.currentTarget;
|
|
194
183
|
const rect = svg.getBoundingClientRect();
|
|
195
184
|
const mx = (e.clientX - rect.left) / rect.width * svg.viewBox.baseVal.width;
|
|
196
|
-
setMouseX(mx);
|
|
197
185
|
if (seriesPoints.length === 0 || seriesPoints[0].length === 0) return;
|
|
198
186
|
const points = seriesPoints[0];
|
|
187
|
+
const step = points.length > 1 ? Math.abs(points[1].x - points[0].x) : 20;
|
|
188
|
+
const threshold = step / 2;
|
|
199
189
|
let closest = 0;
|
|
200
190
|
let minDist = Math.abs(points[0].x - mx);
|
|
201
191
|
for (let i = 1; i < points.length; i++) {
|
|
@@ -205,11 +195,10 @@ var useCrosshair = (seriesPoints, entries, labels, chartH) => {
|
|
|
205
195
|
closest = i;
|
|
206
196
|
}
|
|
207
197
|
}
|
|
208
|
-
setActiveIndex(closest);
|
|
198
|
+
setActiveIndex(minDist <= threshold ? closest : null);
|
|
209
199
|
}, [seriesPoints]);
|
|
210
200
|
const handleMouseLeave = React.useCallback(() => {
|
|
211
201
|
setActiveIndex(null);
|
|
212
|
-
setMouseX(null);
|
|
213
202
|
}, []);
|
|
214
203
|
const tooltipContent = React.useMemo(() => {
|
|
215
204
|
if (activeIndex === null) return "";
|
|
@@ -218,7 +207,13 @@ var useCrosshair = (seriesPoints, entries, labels, chartH) => {
|
|
|
218
207
|
return p ? `${key}: ${p.v}` : "";
|
|
219
208
|
}).filter(Boolean).join(" / ");
|
|
220
209
|
}, [activeIndex, entries, seriesPoints]);
|
|
221
|
-
|
|
210
|
+
const getTooltipAt = React.useCallback((idx) => {
|
|
211
|
+
return entries.map(([key], di) => {
|
|
212
|
+
const p = seriesPoints[di]?.[idx];
|
|
213
|
+
return p ? `${key}: ${p.v}` : "";
|
|
214
|
+
}).filter(Boolean).join(" / ");
|
|
215
|
+
}, [entries, seriesPoints]);
|
|
216
|
+
return { activeIndex, handleMouseMove, handleMouseLeave, tooltipContent, getTooltipAt };
|
|
222
217
|
};
|
|
223
218
|
var LineChart = React.memo(({ data, labels, width, height, animate, onHover, onMove, onLeave }) => {
|
|
224
219
|
const entries = React.useMemo(() => Object.entries(data), [data]);
|
|
@@ -239,33 +234,19 @@ var LineChart = React.memo(({ data, labels, width, height, animate, onHover, onM
|
|
|
239
234
|
),
|
|
240
235
|
[entries, count, chartW, chartH, maxVal]
|
|
241
236
|
);
|
|
242
|
-
const lineRefs = React.useRef([]);
|
|
243
237
|
const clipRef = React.useRef(null);
|
|
244
|
-
const { activeIndex,
|
|
238
|
+
const { activeIndex, handleMouseMove, handleMouseLeave, getTooltipAt } = useCrosshair(seriesPoints, entries, labels, chartH);
|
|
245
239
|
React.useEffect(() => {
|
|
246
|
-
if (!animate) return;
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
el.style.transition = "stroke-dashoffset 1200ms ease-out 200ms";
|
|
254
|
-
el.style.strokeDashoffset = "0";
|
|
255
|
-
});
|
|
240
|
+
if (!animate || !clipRef.current) return;
|
|
241
|
+
clipRef.current.setAttribute("width", "0");
|
|
242
|
+
requestAnimationFrame(() => {
|
|
243
|
+
if (clipRef.current) {
|
|
244
|
+
clipRef.current.style.transition = "width 1200ms ease-out 200ms";
|
|
245
|
+
clipRef.current.setAttribute("width", `${width}`);
|
|
246
|
+
}
|
|
256
247
|
});
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
requestAnimationFrame(() => {
|
|
260
|
-
if (clipRef.current) {
|
|
261
|
-
clipRef.current.style.transition = "width 1200ms ease-out 200ms";
|
|
262
|
-
clipRef.current.setAttribute("width", `${width}`);
|
|
263
|
-
}
|
|
264
|
-
});
|
|
265
|
-
}
|
|
266
|
-
}, [animate, seriesPoints, width]);
|
|
267
|
-
const guideX = mouseX != null && mouseX >= PADDING.left && mouseX <= width - PADDING.right ? mouseX : null;
|
|
268
|
-
const activeX = activeIndex !== null ? seriesPoints[0]?.[activeIndex]?.x : null;
|
|
248
|
+
}, [animate, width]);
|
|
249
|
+
const activeX = activeIndex !== null ? seriesPoints[0]?.[activeIndex]?.x ?? null : null;
|
|
269
250
|
const lineClipId = "line-area-clip";
|
|
270
251
|
return /* @__PURE__ */ jsxs(
|
|
271
252
|
"svg",
|
|
@@ -274,7 +255,26 @@ var LineChart = React.memo(({ data, labels, width, height, animate, onHover, onM
|
|
|
274
255
|
className: "chart-svg",
|
|
275
256
|
onMouseMove: (e) => {
|
|
276
257
|
handleMouseMove(e);
|
|
277
|
-
|
|
258
|
+
const svg = e.currentTarget;
|
|
259
|
+
const rect = svg.getBoundingClientRect();
|
|
260
|
+
const mx = (e.clientX - rect.left) / rect.width * svg.viewBox.baseVal.width;
|
|
261
|
+
const points = seriesPoints[0];
|
|
262
|
+
if (!points || points.length === 0) return;
|
|
263
|
+
const step = points.length > 1 ? Math.abs(points[1].x - points[0].x) : 20;
|
|
264
|
+
let closest = 0;
|
|
265
|
+
let minDist = Math.abs(points[0].x - mx);
|
|
266
|
+
for (let i = 1; i < points.length; i++) {
|
|
267
|
+
const dist = Math.abs(points[i].x - mx);
|
|
268
|
+
if (dist < minDist) {
|
|
269
|
+
minDist = dist;
|
|
270
|
+
closest = i;
|
|
271
|
+
}
|
|
272
|
+
}
|
|
273
|
+
if (minDist <= step / 2) {
|
|
274
|
+
onHover(e, `${labels[closest]} \u2014 ${getTooltipAt(closest)}`);
|
|
275
|
+
} else {
|
|
276
|
+
onLeave();
|
|
277
|
+
}
|
|
278
278
|
},
|
|
279
279
|
onMouseLeave: () => {
|
|
280
280
|
handleMouseLeave();
|
|
@@ -297,26 +297,10 @@ var LineChart = React.memo(({ data, labels, width, height, animate, onHover, onM
|
|
|
297
297
|
/* @__PURE__ */ jsx("stop", { offset: "0%", stopColor: areaColor, stopOpacity: "0.2" }),
|
|
298
298
|
/* @__PURE__ */ jsx("stop", { offset: "100%", stopColor: areaColor, stopOpacity: "0" })
|
|
299
299
|
] }) }),
|
|
300
|
-
/* @__PURE__ */
|
|
301
|
-
"path",
|
|
302
|
-
{
|
|
303
|
-
|
|
304
|
-
fill: `url(#${gradientId})`,
|
|
305
|
-
clipPath: animate ? `url(#${lineClipId})` : void 0
|
|
306
|
-
}
|
|
307
|
-
),
|
|
308
|
-
/* @__PURE__ */ jsx(
|
|
309
|
-
"polyline",
|
|
310
|
-
{
|
|
311
|
-
ref: (el) => {
|
|
312
|
-
lineRefs.current[di] = el;
|
|
313
|
-
},
|
|
314
|
-
points: polyPoints,
|
|
315
|
-
fill: "none",
|
|
316
|
-
stroke: color,
|
|
317
|
-
strokeWidth: "2"
|
|
318
|
-
}
|
|
319
|
-
),
|
|
300
|
+
/* @__PURE__ */ jsxs("g", { clipPath: animate ? `url(#${lineClipId})` : void 0, children: [
|
|
301
|
+
/* @__PURE__ */ jsx("path", { d: areaD, fill: `url(#${gradientId})` }),
|
|
302
|
+
/* @__PURE__ */ jsx("polyline", { points: polyPoints, fill: "none", stroke: color, strokeWidth: "2" })
|
|
303
|
+
] }),
|
|
320
304
|
activeIndex !== null && points[activeIndex] && /* @__PURE__ */ jsx(
|
|
321
305
|
"circle",
|
|
322
306
|
{
|
|
@@ -329,21 +313,16 @@ var LineChart = React.memo(({ data, labels, width, height, animate, onHover, onM
|
|
|
329
313
|
)
|
|
330
314
|
] }, di);
|
|
331
315
|
}),
|
|
332
|
-
|
|
316
|
+
activeX !== null && /* @__PURE__ */ jsx(
|
|
333
317
|
"line",
|
|
334
318
|
{
|
|
335
|
-
x1:
|
|
319
|
+
x1: activeX,
|
|
336
320
|
y1: PADDING.top,
|
|
337
|
-
x2:
|
|
321
|
+
x2: activeX,
|
|
338
322
|
y2: PADDING.top + chartH,
|
|
339
323
|
className: "chart-crosshair"
|
|
340
324
|
}
|
|
341
325
|
),
|
|
342
|
-
activeIndex !== null && activeX !== null && /* @__PURE__ */ jsx("foreignObject", { x: activeX - 100, y: 0, width: "200", height: PADDING.top, children: /* @__PURE__ */ jsxs("div", { className: "chart-crosshair-label", children: [
|
|
343
|
-
labels[activeIndex],
|
|
344
|
-
" \u2014 ",
|
|
345
|
-
tooltipContent
|
|
346
|
-
] }) }),
|
|
347
326
|
/* @__PURE__ */ jsx(
|
|
348
327
|
"rect",
|
|
349
328
|
{
|
|
@@ -379,33 +358,19 @@ var CurveChart = React.memo(({ data, labels, width, height, animate, onHover, on
|
|
|
379
358
|
),
|
|
380
359
|
[entries, count, chartW, chartH, maxVal]
|
|
381
360
|
);
|
|
382
|
-
const lineRefs = React.useRef([]);
|
|
383
361
|
const curveClipRef = React.useRef(null);
|
|
384
|
-
const { activeIndex,
|
|
362
|
+
const { activeIndex, handleMouseMove, handleMouseLeave, getTooltipAt } = useCrosshair(seriesPoints, entries, labels, chartH);
|
|
385
363
|
React.useEffect(() => {
|
|
386
|
-
if (!animate) return;
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
el.style.transition = "stroke-dashoffset 1200ms ease-out 200ms";
|
|
394
|
-
el.style.strokeDashoffset = "0";
|
|
395
|
-
});
|
|
364
|
+
if (!animate || !curveClipRef.current) return;
|
|
365
|
+
curveClipRef.current.setAttribute("width", "0");
|
|
366
|
+
requestAnimationFrame(() => {
|
|
367
|
+
if (curveClipRef.current) {
|
|
368
|
+
curveClipRef.current.style.transition = "width 1200ms ease-out 200ms";
|
|
369
|
+
curveClipRef.current.setAttribute("width", `${width}`);
|
|
370
|
+
}
|
|
396
371
|
});
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
requestAnimationFrame(() => {
|
|
400
|
-
if (curveClipRef.current) {
|
|
401
|
-
curveClipRef.current.style.transition = "width 1200ms ease-out 200ms";
|
|
402
|
-
curveClipRef.current.setAttribute("width", `${width}`);
|
|
403
|
-
}
|
|
404
|
-
});
|
|
405
|
-
}
|
|
406
|
-
}, [animate, seriesPoints, width]);
|
|
407
|
-
const guideX = mouseX != null && mouseX >= PADDING.left && mouseX <= width - PADDING.right ? mouseX : null;
|
|
408
|
-
const activeX = activeIndex !== null ? seriesPoints[0]?.[activeIndex]?.x : null;
|
|
372
|
+
}, [animate, width]);
|
|
373
|
+
const activeX = activeIndex !== null ? seriesPoints[0]?.[activeIndex]?.x ?? null : null;
|
|
409
374
|
const curveClipId = "curve-area-clip";
|
|
410
375
|
return /* @__PURE__ */ jsxs(
|
|
411
376
|
"svg",
|
|
@@ -414,7 +379,26 @@ var CurveChart = React.memo(({ data, labels, width, height, animate, onHover, on
|
|
|
414
379
|
className: "chart-svg",
|
|
415
380
|
onMouseMove: (e) => {
|
|
416
381
|
handleMouseMove(e);
|
|
417
|
-
|
|
382
|
+
const svg = e.currentTarget;
|
|
383
|
+
const rect = svg.getBoundingClientRect();
|
|
384
|
+
const mx = (e.clientX - rect.left) / rect.width * svg.viewBox.baseVal.width;
|
|
385
|
+
const points = seriesPoints[0];
|
|
386
|
+
if (!points || points.length === 0) return;
|
|
387
|
+
const step = points.length > 1 ? Math.abs(points[1].x - points[0].x) : 20;
|
|
388
|
+
let closest = 0;
|
|
389
|
+
let minDist = Math.abs(points[0].x - mx);
|
|
390
|
+
for (let i = 1; i < points.length; i++) {
|
|
391
|
+
const dist = Math.abs(points[i].x - mx);
|
|
392
|
+
if (dist < minDist) {
|
|
393
|
+
minDist = dist;
|
|
394
|
+
closest = i;
|
|
395
|
+
}
|
|
396
|
+
}
|
|
397
|
+
if (minDist <= step / 2) {
|
|
398
|
+
onHover(e, `${labels[closest]} \u2014 ${getTooltipAt(closest)}`);
|
|
399
|
+
} else {
|
|
400
|
+
onLeave();
|
|
401
|
+
}
|
|
418
402
|
},
|
|
419
403
|
onMouseLeave: () => {
|
|
420
404
|
handleMouseLeave();
|
|
@@ -437,26 +421,10 @@ var CurveChart = React.memo(({ data, labels, width, height, animate, onHover, on
|
|
|
437
421
|
/* @__PURE__ */ jsx("stop", { offset: "0%", stopColor: areaColor, stopOpacity: "0.4" }),
|
|
438
422
|
/* @__PURE__ */ jsx("stop", { offset: "100%", stopColor: areaColor, stopOpacity: "0.02" })
|
|
439
423
|
] }) }),
|
|
440
|
-
/* @__PURE__ */
|
|
441
|
-
"path",
|
|
442
|
-
{
|
|
443
|
-
|
|
444
|
-
fill: `url(#${gradientId})`,
|
|
445
|
-
clipPath: animate ? `url(#${curveClipId})` : void 0
|
|
446
|
-
}
|
|
447
|
-
),
|
|
448
|
-
/* @__PURE__ */ jsx(
|
|
449
|
-
"path",
|
|
450
|
-
{
|
|
451
|
-
ref: (el) => {
|
|
452
|
-
lineRefs.current[di] = el;
|
|
453
|
-
},
|
|
454
|
-
d: linePath,
|
|
455
|
-
fill: "none",
|
|
456
|
-
stroke: color,
|
|
457
|
-
strokeWidth: "2"
|
|
458
|
-
}
|
|
459
|
-
),
|
|
424
|
+
/* @__PURE__ */ jsxs("g", { clipPath: animate ? `url(#${curveClipId})` : void 0, children: [
|
|
425
|
+
/* @__PURE__ */ jsx("path", { d: areaPath, fill: `url(#${gradientId})` }),
|
|
426
|
+
/* @__PURE__ */ jsx("path", { d: linePath, fill: "none", stroke: color, strokeWidth: "2" })
|
|
427
|
+
] }),
|
|
460
428
|
activeIndex !== null && points[activeIndex] && /* @__PURE__ */ jsx(
|
|
461
429
|
"circle",
|
|
462
430
|
{
|
|
@@ -469,21 +437,16 @@ var CurveChart = React.memo(({ data, labels, width, height, animate, onHover, on
|
|
|
469
437
|
)
|
|
470
438
|
] }, di);
|
|
471
439
|
}),
|
|
472
|
-
|
|
440
|
+
activeX !== null && /* @__PURE__ */ jsx(
|
|
473
441
|
"line",
|
|
474
442
|
{
|
|
475
|
-
x1:
|
|
443
|
+
x1: activeX,
|
|
476
444
|
y1: PADDING.top,
|
|
477
|
-
x2:
|
|
445
|
+
x2: activeX,
|
|
478
446
|
y2: PADDING.top + chartH,
|
|
479
447
|
className: "chart-crosshair"
|
|
480
448
|
}
|
|
481
449
|
),
|
|
482
|
-
activeIndex !== null && activeX !== null && /* @__PURE__ */ jsx("foreignObject", { x: activeX - 100, y: 0, width: "200", height: PADDING.top, children: /* @__PURE__ */ jsxs("div", { className: "chart-crosshair-label", children: [
|
|
483
|
-
labels[activeIndex],
|
|
484
|
-
" \u2014 ",
|
|
485
|
-
tooltipContent
|
|
486
|
-
] }) }),
|
|
487
450
|
/* @__PURE__ */ jsx(
|
|
488
451
|
"rect",
|
|
489
452
|
{
|
|
@@ -662,30 +625,70 @@ var PieDonutChart = React.memo(
|
|
|
662
625
|
}
|
|
663
626
|
);
|
|
664
627
|
PieDonutChart.displayName = "PieDonutChart";
|
|
665
|
-
var
|
|
628
|
+
var ChartTooltipPortal = ({ clientX, clientY, visible, children }) => {
|
|
666
629
|
const ref = React.useRef(null);
|
|
667
|
-
const [
|
|
668
|
-
React.
|
|
630
|
+
const [pos, setPos] = React.useState({ left: 0, top: 0 });
|
|
631
|
+
React.useLayoutEffect(() => {
|
|
669
632
|
const el = ref.current;
|
|
670
633
|
if (!el) return;
|
|
671
634
|
const w = el.offsetWidth;
|
|
672
|
-
const
|
|
673
|
-
const
|
|
674
|
-
let
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
635
|
+
const h = el.offsetHeight;
|
|
636
|
+
const vw = window.innerWidth;
|
|
637
|
+
let left = clientX + TOOLTIP_OFFSET;
|
|
638
|
+
let top = clientY - h - TOOLTIP_OFFSET;
|
|
639
|
+
if (left + w > vw - 8) left = clientX - w - TOOLTIP_OFFSET;
|
|
640
|
+
if (top < 8) top = clientY + TOOLTIP_OFFSET;
|
|
641
|
+
if (left < 8) left = 8;
|
|
642
|
+
setPos({ left, top });
|
|
643
|
+
}, [clientX, clientY]);
|
|
679
644
|
return /* @__PURE__ */ jsx(
|
|
680
645
|
"div",
|
|
681
646
|
{
|
|
682
647
|
ref,
|
|
683
|
-
className: "chart-tooltip"
|
|
684
|
-
style: { left:
|
|
648
|
+
className: `chart-tooltip ${visible ? "chart-tooltip-show" : "chart-tooltip-hide"}`,
|
|
649
|
+
style: { position: "fixed", left: pos.left, top: pos.top, zIndex: 1100 },
|
|
685
650
|
children
|
|
686
651
|
}
|
|
687
652
|
);
|
|
688
653
|
};
|
|
654
|
+
var ChartLegend = ({ data, labels, type }) => {
|
|
655
|
+
const entries = Object.entries(data);
|
|
656
|
+
if (type === "pie" || type === "doughnut") {
|
|
657
|
+
const values = entries.flatMap(([, v]) => v);
|
|
658
|
+
const total = values.reduce((a, b) => a + b, 0) || 1;
|
|
659
|
+
const firstKey = entries[0]?.[0] ?? "";
|
|
660
|
+
const colorOffset = hashString(firstKey);
|
|
661
|
+
return /* @__PURE__ */ jsx("div", { className: "chart-legend", children: values.map((v, i) => {
|
|
662
|
+
const pct = Math.round(v / total * 100);
|
|
663
|
+
const color = PIE_COLORS[(i + colorOffset) % PIE_COLORS.length];
|
|
664
|
+
return /* @__PURE__ */ jsxs("div", { className: "chart-legend-item", children: [
|
|
665
|
+
/* @__PURE__ */ jsx("span", { className: "chart-legend-dot", style: { backgroundColor: color } }),
|
|
666
|
+
/* @__PURE__ */ jsxs("div", { className: "chart-legend-text", children: [
|
|
667
|
+
/* @__PURE__ */ jsx("span", { className: "chart-legend-label", children: labels[i] || `${i + 1}` }),
|
|
668
|
+
/* @__PURE__ */ jsxs("span", { className: "chart-legend-value", children: [
|
|
669
|
+
v.toLocaleString(),
|
|
670
|
+
"(",
|
|
671
|
+
pct,
|
|
672
|
+
"%)"
|
|
673
|
+
] })
|
|
674
|
+
] })
|
|
675
|
+
] }, i);
|
|
676
|
+
}) });
|
|
677
|
+
}
|
|
678
|
+
return /* @__PURE__ */ jsx("div", { className: "chart-legend", children: entries.map(([key], di) => {
|
|
679
|
+
const palette = getPalette(LINE_BAR_PALETTES, di, key);
|
|
680
|
+
const color = palette[2];
|
|
681
|
+
const values = entries[di][1];
|
|
682
|
+
const sum = values.reduce((a, b) => a + b, 0);
|
|
683
|
+
return /* @__PURE__ */ jsxs("div", { className: "chart-legend-item", children: [
|
|
684
|
+
/* @__PURE__ */ jsx("span", { className: "chart-legend-dot", style: { backgroundColor: color } }),
|
|
685
|
+
/* @__PURE__ */ jsxs("div", { className: "chart-legend-text", children: [
|
|
686
|
+
/* @__PURE__ */ jsx("span", { className: "chart-legend-label", children: key }),
|
|
687
|
+
/* @__PURE__ */ jsx("span", { className: "chart-legend-value", children: sum.toLocaleString() })
|
|
688
|
+
] })
|
|
689
|
+
] }, di);
|
|
690
|
+
}) });
|
|
691
|
+
};
|
|
689
692
|
var Chart = React.memo((props) => {
|
|
690
693
|
const { type, data, labels, tooltip: showTooltip = true } = props;
|
|
691
694
|
const { tooltip, show, hide, move, containerRef } = useChartTooltip(showTooltip);
|
|
@@ -701,7 +704,8 @@ var Chart = React.memo((props) => {
|
|
|
701
704
|
ready && type === "bar" && /* @__PURE__ */ jsx(BarChart, { data: stableData, labels: stableLabels, width, height, animate, onHover: show, onMove: move, onLeave: hide }),
|
|
702
705
|
ready && type === "pie" && /* @__PURE__ */ jsx(PieDonutChart, { data: stableData, labels: stableLabels, width, height, animate, onHover: show, onMove: move, onLeave: hide }),
|
|
703
706
|
ready && type === "doughnut" && /* @__PURE__ */ jsx(PieDonutChart, { data: stableData, labels: stableLabels, width, height, animate, isDoughnut: true, onHover: show, onMove: move, onLeave: hide }),
|
|
704
|
-
|
|
707
|
+
ready && (type === "bar" || type === "pie" || type === "doughnut") && /* @__PURE__ */ jsx(ChartLegend, { data: stableData, labels: stableLabels, type }),
|
|
708
|
+
tooltip.content && /* @__PURE__ */ jsx(ChartTooltipPortal, { clientX: tooltip.clientX, clientY: tooltip.clientY, visible: tooltip.visible, children: tooltip.content })
|
|
705
709
|
] });
|
|
706
710
|
});
|
|
707
711
|
Chart.displayName = "Chart";
|