ioloco-charts 0.2.1 → 0.2.2
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.
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
import{jsx as r}from"react/jsx-runtime"
|
|
3
3
|
import{useRef as t,useEffect as o}from"react"
|
|
4
4
|
import{max as e}from"d3-array"
|
|
5
|
-
import{scaleBand as
|
|
5
|
+
import{scaleBand as a,scaleLinear as i}from"d3-scale"
|
|
6
6
|
import{select as s}from"d3-selection"
|
|
7
7
|
import"d3-transition"
|
|
8
8
|
import{chartPalette as m}from"../../tokens.stylex.js"
|
|
@@ -12,19 +12,20 @@ import{renderXAxis as c,renderYAxis as d}from"../shared/chartAxisLayout/render.j
|
|
|
12
12
|
import{chartFrameInteractionProps as l,chartPointerHandlers as f}from"../shared/chartBinding.js"
|
|
13
13
|
import{bindChartPointer as p,applyPointerOpacity as u}from"../shared/chartInteraction.js"
|
|
14
14
|
import{formatChartHint as j}from"../shared/chartLabels.js"
|
|
15
|
-
import{
|
|
15
|
+
import{appendBarSeriesGradient as x,sanitizeGradientKey as y,SHAPE_STROKE_WIDTH as g}from"../shared/chartVisualStyle.js"
|
|
16
16
|
import{useChartInteraction as k}from"../shared/useChartInteraction.js"
|
|
17
|
-
import{innerSize as
|
|
18
|
-
function
|
|
17
|
+
import{innerSize as b}from"../shared/chartUtils.js"
|
|
18
|
+
function v({data:v,title:$="Bar chart",description:C,height:w=320,compact:L=!1,valueLabel:B,hoverHint:F="Hover a bar for details.",onDatumClick:A}){const H=t(null),I=k(F),M=t(A)
|
|
19
19
|
return M.current=A,o(()=>{const r=H.current
|
|
20
20
|
if(!r)return
|
|
21
|
-
const t=r.clientWidth||640,o=L?Math.min(w,280):w,n=h(L),l=n.margin,{width:k,height
|
|
22
|
-
|
|
23
|
-
const
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
21
|
+
const t=r.clientWidth||640,o=L?Math.min(w,280):w,n=h(L),l=n.margin,{width:k,height:$}=b(t,o,l),C=s(r)
|
|
22
|
+
C.selectAll("*").remove(),C.attr("viewBox",`0 0 ${t} ${o}`)
|
|
23
|
+
const F=C.append("defs")
|
|
24
|
+
v.forEach((r,t)=>{const o=r.color??m[t%m.length]
|
|
25
|
+
x(F,`bar-${y(r.label)}`,o,L)})
|
|
26
|
+
const A=C.append("g").attr("transform",`translate(${l.left},${l.top})`),D=a().domain(v.map(r=>r.label)).range([0,k]).padding(.25),R=i().domain([0,e(v,r=>r.value)??0]).nice().range([$,0])
|
|
27
|
+
c(A,D,$,n.x),d(A,R,n.y)
|
|
28
|
+
const S=A.selectAll("rect").data(v).join("rect").attr("x",r=>D(r.label)??0).attr("width",D.bandwidth()).attr("y",$).attr("height",0).attr("fill",r=>`url(#bar-${y(r.label)})`).attr("stroke",(r,t)=>r.color??m[t%m.length]).attr("stroke-width",g).attr("stroke-opacity",.35).attr("rx",4)
|
|
29
|
+
S.transition().duration(500).attr("y",r=>R(r.value)).attr("height",r=>$-R(r.value)),p(S,{keyFn:r=>r.label,hintFn:r=>j(r.label,r.value,B),...f(I),onClick:r=>M.current?.(r)})
|
|
30
|
+
const U=I.registerFocusApply(()=>{u(S,r=>r.label,I.getFocusOpacity)})
|
|
31
|
+
return()=>{U(),S.on("mouseenter mouseleave click",null)}},[L,v,w,I.getFocusOpacity,I.onHover,I.onHoverEnd,I.onToggleSelect,I.registerFocusApply,F,B]),r(n,{title:$,description:C,height:L?Math.min(w,280):w,compact:L,...l(I),svgRef:H})}export{v as BarChart}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
import type { StackedBarChartProps } from './types';
|
|
2
|
-
export declare function StackedBarChart({ data, seriesKeys, title, description, height, compact, valueLabel, hoverHint, onSegmentClick }: Readonly<StackedBarChartProps>): import("react").JSX.Element;
|
|
2
|
+
export declare function StackedBarChart({ data, seriesKeys, seriesColors, title, description, height, compact, valueLabel, hoverHint, onSegmentClick }: Readonly<StackedBarChartProps>): import("react").JSX.Element;
|
|
@@ -1,40 +1,40 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import{jsx as
|
|
3
|
-
import{useRef as
|
|
4
|
-
import{max as
|
|
5
|
-
import{scaleBand as
|
|
6
|
-
import{select as
|
|
7
|
-
import{stack as
|
|
2
|
+
import{jsx as r}from"react/jsx-runtime"
|
|
3
|
+
import{useRef as e,useMemo as t,useCallback as o,useEffect as s}from"react"
|
|
4
|
+
import{max as a}from"d3-array"
|
|
5
|
+
import{scaleBand as i,scaleLinear as n,scaleOrdinal as c}from"d3-scale"
|
|
6
|
+
import{select as m}from"d3-selection"
|
|
7
|
+
import{stack as l}from"d3-shape"
|
|
8
8
|
import{chartPalette as d}from"../../tokens.stylex.js"
|
|
9
9
|
import{ChartFrame as h}from"../shared/ChartFrame/index.js"
|
|
10
|
-
import{ChartLegend as
|
|
11
|
-
import{renderXAxis as
|
|
12
|
-
import{stackedBarChartAxisLayout as
|
|
13
|
-
import{chartFrameInteractionProps as
|
|
14
|
-
import{bindChartPointer as
|
|
15
|
-
import{formatChartHint as
|
|
16
|
-
import{useChartInteraction as
|
|
17
|
-
import{useChartLegendToggle as
|
|
18
|
-
import{innerSize as
|
|
19
|
-
import{appendBarSeriesGradient as
|
|
20
|
-
function
|
|
21
|
-
for(const
|
|
22
|
-
return[...
|
|
23
|
-
|
|
24
|
-
const
|
|
25
|
-
|
|
26
|
-
if(!
|
|
27
|
-
const
|
|
28
|
-
|
|
29
|
-
const
|
|
30
|
-
|
|
31
|
-
const
|
|
32
|
-
|
|
33
|
-
const
|
|
34
|
-
|
|
35
|
-
const
|
|
36
|
-
|
|
37
|
-
const
|
|
38
|
-
return()=>{
|
|
39
|
-
const
|
|
40
|
-
return
|
|
10
|
+
import{ChartLegend as f}from"../shared/ChartLegend/index.js"
|
|
11
|
+
import{renderXAxis as p,renderYAxis as g}from"../shared/chartAxisLayout/render.js"
|
|
12
|
+
import{stackedBarChartAxisLayout as u}from"../shared/chartAxisLayout/stackedBarChart.js"
|
|
13
|
+
import{chartFrameInteractionProps as j,chartPointerHandlers as k}from"../shared/chartBinding.js"
|
|
14
|
+
import{bindChartPointer as y,applyPointerOpacity as $}from"../shared/chartInteraction.js"
|
|
15
|
+
import{formatChartHint as b}from"../shared/chartLabels.js"
|
|
16
|
+
import{useChartInteraction as x}from"../shared/useChartInteraction.js"
|
|
17
|
+
import{useChartLegendToggle as v}from"../shared/useChartLegendToggle.js"
|
|
18
|
+
import{innerSize as C}from"../shared/chartUtils.js"
|
|
19
|
+
import{appendBarSeriesGradient as L,sanitizeGradientKey as w,SHAPE_STROKE_WIDTH as I}from"../shared/chartVisualStyle.js"
|
|
20
|
+
function S(r){const e=new Set
|
|
21
|
+
for(const t of r)for(const r of Object.keys(t.segments))e.add(r)
|
|
22
|
+
return[...e]}function B({data:B,seriesKeys:F,seriesColors:A,title:H="Stacked bar chart",description:M,height:T=320,compact:K=!1,valueLabel:O,hoverHint:R="Hover a segment for details.",onSegmentClick:U}){const V=e(null),q=x(R),z=e(U)
|
|
23
|
+
z.current=U
|
|
24
|
+
const D=t(()=>F??S(B),[B,F]),{hiddenIds:E,visibleIds:G,toggle:J}=v(D),N=t(()=>D.filter(r=>G.includes(r)),[D,G]),P=o((r,e)=>A?.[r]??d[e%d.length],[A])
|
|
25
|
+
s(()=>{const r=V.current
|
|
26
|
+
if(!r||0===N.length)return
|
|
27
|
+
const e=B.map(r=>({label:r.label,...r.segments})),t=r.clientWidth||640,o=K?Math.min(T,280):T,s=u(K),d=s.margin,{width:h,height:f}=C(t,o,d),j=m(r)
|
|
28
|
+
j.selectAll("*").remove(),j.attr("viewBox",`0 0 ${t} ${o}`)
|
|
29
|
+
const x=j.append("defs")
|
|
30
|
+
D.forEach((r,e)=>{if(!N.includes(r))return
|
|
31
|
+
const t=P(r,e)
|
|
32
|
+
L(x,`stacked-${w(r)}`,t,K)})
|
|
33
|
+
const v=j.append("g").attr("transform",`translate(${d.left},${d.top})`),S=i().domain(e.map(r=>r.label)).range([0,h]).padding(.25),F=l().keys(N)(e),A=n().domain([0,a(F,r=>a(r,r=>r[1])??0)??0]).nice().range([f,0]),H=c().domain(D).range(D.map((r,e)=>P(r,e)))
|
|
34
|
+
p(v,S,f,s.x),g(v,A,s.y),v.selectAll("g.layer").data(F).join("g").attr("class","layer").selectAll("rect").data(r=>r.map(e=>({...e,key:r.key}))).join("rect").attr("x",r=>S(r.data.label)??0).attr("y",r=>A(r[1])).attr("height",r=>A(r[0])-A(r[1])).attr("width",S.bandwidth()).attr("fill",r=>`url(#stacked-${w(r.key)})`).attr("stroke",r=>H(r.key)).attr("stroke-width",I).attr("stroke-opacity",.3)
|
|
35
|
+
const M=v.selectAll("g.layer rect")
|
|
36
|
+
y(M,{keyFn:r=>`${r.data.label}:${r.key}`,hintFn:r=>b(`${r.data.label} · ${r.key}`,r[1]-r[0],O),...k(q),onClick:r=>z.current?.({label:r.data.label,segment:r.key,value:r[1]-r[0]})})
|
|
37
|
+
const R=q.registerFocusApply(()=>{$(M,r=>`${r.data.label}:${r.key}`,q.getFocusOpacity)})
|
|
38
|
+
return()=>{R(),M.on("mouseenter mouseleave click",null)}},[P,K,B,T,q.getFocusOpacity,q.onHover,q.onHoverEnd,q.onPointerMove,q.onToggleSelect,q.registerFocusApply,R,O,D,A,N])
|
|
39
|
+
const Q=t(()=>r(f,{ariaLabel:"Series",hiddenIds:E,onToggle:J,items:D.map((r,e)=>({id:r,label:r,color:P(r,e)}))}),[P,E,D,J])
|
|
40
|
+
return r(h,{title:H,description:M,height:K?Math.min(T,280):T,compact:K,...j(q),svgRef:V,legend:Q})}export{B as StackedBarChart}
|
|
@@ -5,6 +5,8 @@ export type StackedBarRow = {
|
|
|
5
5
|
export type StackedBarChartProps = {
|
|
6
6
|
data: StackedBarRow[];
|
|
7
7
|
seriesKeys?: string[];
|
|
8
|
+
/** Optional color per series key; falls back to the default chart palette. */
|
|
9
|
+
seriesColors?: Record<string, string>;
|
|
8
10
|
title?: string;
|
|
9
11
|
description?: string;
|
|
10
12
|
height?: number;
|