@automattic/charts 0.57.0 → 0.59.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.
- package/CHANGELOG.md +36 -2
- package/README.md +7 -54
- package/dist/index.cjs +9607 -21
- package/dist/index.cjs.map +1 -1
- package/dist/index.css +32 -49
- package/dist/index.css.map +1 -1
- package/dist/index.d.cts +1612 -33
- package/dist/index.d.ts +1612 -33
- package/dist/index.js +9640 -54
- package/dist/index.js.map +1 -1
- package/package.json +9 -126
- package/src/charts/bar-chart/bar-chart.module.scss +0 -5
- package/src/charts/bar-chart/bar-chart.tsx +142 -149
- package/src/charts/bar-chart/test/bar-chart.test.tsx +48 -31
- package/src/charts/leaderboard-chart/leaderboard-chart.tsx +54 -74
- package/src/charts/leaderboard-chart/test/leaderboard-chart.test.tsx +4 -5
- package/src/charts/leaderboard-chart/types.ts +1 -11
- package/src/charts/line-chart/line-chart.module.scss +0 -5
- package/src/charts/line-chart/line-chart.tsx +202 -193
- package/src/charts/line-chart/private/line-chart-annotations-overlay.tsx +1 -2
- package/src/charts/line-chart/test/line-chart.test.tsx +49 -27
- package/src/charts/line-chart/types.ts +0 -1
- package/src/charts/pie-chart/pie-chart.module.scss +2 -10
- package/src/charts/pie-chart/pie-chart.tsx +212 -212
- package/src/charts/pie-chart/test/composition-api.test.tsx +44 -3
- package/src/charts/pie-chart/test/pie-chart.test.tsx +51 -44
- package/src/charts/pie-semi-circle-chart/pie-semi-circle-chart.module.scss +2 -8
- package/src/charts/pie-semi-circle-chart/pie-semi-circle-chart.tsx +166 -168
- package/src/charts/pie-semi-circle-chart/test/pie-semi-circle-chart.test.tsx +58 -30
- package/src/charts/private/chart-composition/index.ts +2 -0
- package/src/charts/private/chart-composition/render-legend-slot.ts +22 -0
- package/src/charts/private/chart-composition/test/render-legend-slot.test.tsx +60 -0
- package/src/charts/private/chart-composition/test/use-chart-children.test.tsx +91 -0
- package/src/charts/private/chart-composition/use-chart-children.ts +34 -2
- package/src/charts/private/chart-layout/chart-layout.module.scss +7 -0
- package/src/charts/private/chart-layout/chart-layout.tsx +106 -0
- package/src/charts/private/chart-layout/index.ts +2 -0
- package/src/charts/private/chart-layout/test/chart-layout.test.tsx +167 -0
- package/src/charts/private/single-chart-context/single-chart-context.tsx +2 -2
- package/src/charts/private/svg-empty-state/index.ts +1 -0
- package/src/charts/private/svg-empty-state/svg-empty-state.module.scss +7 -0
- package/src/charts/private/svg-empty-state/svg-empty-state.tsx +40 -0
- package/src/components/legend/hooks/test/use-chart-legend-items.test.tsx +12 -8
- package/src/components/legend/hooks/use-chart-legend-items.ts +12 -13
- package/src/components/legend/index.ts +1 -8
- package/src/components/legend/legend.tsx +33 -8
- package/src/components/legend/private/base-legend.module.scss +19 -37
- package/src/components/legend/private/base-legend.tsx +0 -2
- package/src/components/legend/test/legend.test.tsx +93 -1
- package/src/components/legend/types.ts +7 -34
- package/src/hooks/index.ts +1 -1
- package/src/hooks/use-data-with-percentages.ts +24 -0
- package/src/hooks/use-interactive-legend-data.ts +18 -15
- package/src/index.ts +66 -9
- package/src/providers/chart-context/global-charts-provider.tsx +7 -1
- package/src/providers/chart-context/hooks/use-chart-registration.ts +2 -1
- package/src/providers/chart-context/types.ts +2 -2
- package/src/types.ts +110 -45
- package/src/utils/date-parsing.ts +10 -1
- package/src/utils/test/date-parsing.test.ts +12 -0
- package/src/utils/test/resolve-css-var.test.ts +4 -2
- package/tsup.config.ts +1 -1
- package/dist/base-tooltip-DOq93wjU.d.cts +0 -38
- package/dist/base-tooltip-DOq93wjU.d.ts +0 -38
- package/dist/charts/bar-chart/index.cjs +0 -15
- package/dist/charts/bar-chart/index.cjs.map +0 -1
- package/dist/charts/bar-chart/index.css +0 -153
- package/dist/charts/bar-chart/index.css.map +0 -1
- package/dist/charts/bar-chart/index.d.cts +0 -37
- package/dist/charts/bar-chart/index.d.ts +0 -37
- package/dist/charts/bar-chart/index.js +0 -15
- package/dist/charts/bar-chart/index.js.map +0 -1
- package/dist/charts/bar-list-chart/index.cjs +0 -16
- package/dist/charts/bar-list-chart/index.cjs.map +0 -1
- package/dist/charts/bar-list-chart/index.css +0 -153
- package/dist/charts/bar-list-chart/index.css.map +0 -1
- package/dist/charts/bar-list-chart/index.d.cts +0 -92
- package/dist/charts/bar-list-chart/index.d.ts +0 -92
- package/dist/charts/bar-list-chart/index.js +0 -16
- package/dist/charts/bar-list-chart/index.js.map +0 -1
- package/dist/charts/conversion-funnel-chart/index.cjs +0 -11
- package/dist/charts/conversion-funnel-chart/index.cjs.map +0 -1
- package/dist/charts/conversion-funnel-chart/index.css +0 -251
- package/dist/charts/conversion-funnel-chart/index.css.map +0 -1
- package/dist/charts/conversion-funnel-chart/index.d.cts +0 -97
- package/dist/charts/conversion-funnel-chart/index.d.ts +0 -97
- package/dist/charts/conversion-funnel-chart/index.js +0 -11
- package/dist/charts/conversion-funnel-chart/index.js.map +0 -1
- package/dist/charts/geo-chart/index.cjs +0 -13
- package/dist/charts/geo-chart/index.cjs.map +0 -1
- package/dist/charts/geo-chart/index.css +0 -117
- package/dist/charts/geo-chart/index.css.map +0 -1
- package/dist/charts/geo-chart/index.d.cts +0 -67
- package/dist/charts/geo-chart/index.d.ts +0 -67
- package/dist/charts/geo-chart/index.js +0 -13
- package/dist/charts/geo-chart/index.js.map +0 -1
- package/dist/charts/leaderboard-chart/index.cjs +0 -20
- package/dist/charts/leaderboard-chart/index.cjs.map +0 -1
- package/dist/charts/leaderboard-chart/index.css +0 -172
- package/dist/charts/leaderboard-chart/index.css.map +0 -1
- package/dist/charts/leaderboard-chart/index.d.cts +0 -46
- package/dist/charts/leaderboard-chart/index.d.ts +0 -46
- package/dist/charts/leaderboard-chart/index.js +0 -20
- package/dist/charts/leaderboard-chart/index.js.map +0 -1
- package/dist/charts/line-chart/index.cjs +0 -15
- package/dist/charts/line-chart/index.cjs.map +0 -1
- package/dist/charts/line-chart/index.css +0 -225
- package/dist/charts/line-chart/index.css.map +0 -1
- package/dist/charts/line-chart/index.d.cts +0 -99
- package/dist/charts/line-chart/index.d.ts +0 -99
- package/dist/charts/line-chart/index.js +0 -15
- package/dist/charts/line-chart/index.js.map +0 -1
- package/dist/charts/pie-chart/index.cjs +0 -18
- package/dist/charts/pie-chart/index.cjs.map +0 -1
- package/dist/charts/pie-chart/index.css +0 -143
- package/dist/charts/pie-chart/index.css.map +0 -1
- package/dist/charts/pie-chart/index.d.cts +0 -97
- package/dist/charts/pie-chart/index.d.ts +0 -97
- package/dist/charts/pie-chart/index.js +0 -18
- package/dist/charts/pie-chart/index.js.map +0 -1
- package/dist/charts/pie-semi-circle-chart/index.cjs +0 -17
- package/dist/charts/pie-semi-circle-chart/index.cjs.map +0 -1
- package/dist/charts/pie-semi-circle-chart/index.css +0 -144
- package/dist/charts/pie-semi-circle-chart/index.css.map +0 -1
- package/dist/charts/pie-semi-circle-chart/index.d.cts +0 -94
- package/dist/charts/pie-semi-circle-chart/index.d.ts +0 -94
- package/dist/charts/pie-semi-circle-chart/index.js +0 -17
- package/dist/charts/pie-semi-circle-chart/index.js.map +0 -1
- package/dist/charts/sparkline/index.cjs +0 -16
- package/dist/charts/sparkline/index.cjs.map +0 -1
- package/dist/charts/sparkline/index.css +0 -242
- package/dist/charts/sparkline/index.css.map +0 -1
- package/dist/charts/sparkline/index.d.cts +0 -113
- package/dist/charts/sparkline/index.d.ts +0 -113
- package/dist/charts/sparkline/index.js +0 -16
- package/dist/charts/sparkline/index.js.map +0 -1
- package/dist/chunk-2A34OA5O.cjs +0 -51
- package/dist/chunk-2A34OA5O.cjs.map +0 -1
- package/dist/chunk-2NCY7R4G.js +0 -3897
- package/dist/chunk-2NCY7R4G.js.map +0 -1
- package/dist/chunk-32DH6JDF.js +0 -1263
- package/dist/chunk-32DH6JDF.js.map +0 -1
- package/dist/chunk-4OPFE4RM.js +0 -614
- package/dist/chunk-4OPFE4RM.js.map +0 -1
- package/dist/chunk-6CCZL2JJ.js +0 -63
- package/dist/chunk-6CCZL2JJ.js.map +0 -1
- package/dist/chunk-77OKCVQN.cjs +0 -421
- package/dist/chunk-77OKCVQN.cjs.map +0 -1
- package/dist/chunk-7FQX4ALL.cjs +0 -219
- package/dist/chunk-7FQX4ALL.cjs.map +0 -1
- package/dist/chunk-ASLARV7L.cjs +0 -81
- package/dist/chunk-ASLARV7L.cjs.map +0 -1
- package/dist/chunk-BCX5THDQ.js +0 -403
- package/dist/chunk-BCX5THDQ.js.map +0 -1
- package/dist/chunk-BPYKWMI7.js +0 -194
- package/dist/chunk-BPYKWMI7.js.map +0 -1
- package/dist/chunk-CZGYJKG6.js +0 -421
- package/dist/chunk-CZGYJKG6.js.map +0 -1
- package/dist/chunk-D2UH4CFE.cjs +0 -120
- package/dist/chunk-D2UH4CFE.cjs.map +0 -1
- package/dist/chunk-DAU3HNEG.js +0 -344
- package/dist/chunk-DAU3HNEG.js.map +0 -1
- package/dist/chunk-H2V4JMSA.js +0 -219
- package/dist/chunk-H2V4JMSA.js.map +0 -1
- package/dist/chunk-I2276W3I.cjs +0 -66
- package/dist/chunk-I2276W3I.cjs.map +0 -1
- package/dist/chunk-I35UYJJR.cjs +0 -468
- package/dist/chunk-I35UYJJR.cjs.map +0 -1
- package/dist/chunk-IU4DYUAV.js +0 -120
- package/dist/chunk-IU4DYUAV.js.map +0 -1
- package/dist/chunk-KXRWNFQJ.js +0 -51
- package/dist/chunk-KXRWNFQJ.js.map +0 -1
- package/dist/chunk-OP6PHB2U.js +0 -81
- package/dist/chunk-OP6PHB2U.js.map +0 -1
- package/dist/chunk-PXLEMUGJ.js +0 -165
- package/dist/chunk-PXLEMUGJ.js.map +0 -1
- package/dist/chunk-RCY6XLGU.cjs +0 -63
- package/dist/chunk-RCY6XLGU.cjs.map +0 -1
- package/dist/chunk-RHHVEJHJ.cjs +0 -1263
- package/dist/chunk-RHHVEJHJ.cjs.map +0 -1
- package/dist/chunk-TO3OQBXG.cjs +0 -165
- package/dist/chunk-TO3OQBXG.cjs.map +0 -1
- package/dist/chunk-V36ERY7Y.js +0 -375
- package/dist/chunk-V36ERY7Y.js.map +0 -1
- package/dist/chunk-VJM5XCB4.cjs +0 -614
- package/dist/chunk-VJM5XCB4.cjs.map +0 -1
- package/dist/chunk-VTS3PNMS.cjs +0 -344
- package/dist/chunk-VTS3PNMS.cjs.map +0 -1
- package/dist/chunk-WLODYNLB.js +0 -1067
- package/dist/chunk-WLODYNLB.js.map +0 -1
- package/dist/chunk-XKRJL2QT.cjs +0 -375
- package/dist/chunk-XKRJL2QT.cjs.map +0 -1
- package/dist/chunk-XWYZIFZW.js +0 -66
- package/dist/chunk-XWYZIFZW.js.map +0 -1
- package/dist/chunk-Y3NNQMAX.cjs +0 -194
- package/dist/chunk-Y3NNQMAX.cjs.map +0 -1
- package/dist/chunk-YE2T52VZ.cjs +0 -1067
- package/dist/chunk-YE2T52VZ.cjs.map +0 -1
- package/dist/chunk-Z26M4V2M.js +0 -468
- package/dist/chunk-Z26M4V2M.js.map +0 -1
- package/dist/chunk-Z45KX47P.cjs +0 -3897
- package/dist/chunk-Z45KX47P.cjs.map +0 -1
- package/dist/chunk-ZH4F5RMG.cjs +0 -403
- package/dist/chunk-ZH4F5RMG.cjs.map +0 -1
- package/dist/components/legend/index.cjs +0 -11
- package/dist/components/legend/index.cjs.map +0 -1
- package/dist/components/legend/index.css +0 -103
- package/dist/components/legend/index.css.map +0 -1
- package/dist/components/legend/index.d.cts +0 -37
- package/dist/components/legend/index.d.ts +0 -37
- package/dist/components/legend/index.js +0 -11
- package/dist/components/legend/index.js.map +0 -1
- package/dist/components/tooltip/index.cjs +0 -12
- package/dist/components/tooltip/index.cjs.map +0 -1
- package/dist/components/tooltip/index.css +0 -13
- package/dist/components/tooltip/index.css.map +0 -1
- package/dist/components/tooltip/index.d.cts +0 -71
- package/dist/components/tooltip/index.d.ts +0 -71
- package/dist/components/tooltip/index.js +0 -12
- package/dist/components/tooltip/index.js.map +0 -1
- package/dist/components/trend-indicator/index.cjs +0 -8
- package/dist/components/trend-indicator/index.cjs.map +0 -1
- package/dist/components/trend-indicator/index.css +0 -27
- package/dist/components/trend-indicator/index.css.map +0 -1
- package/dist/components/trend-indicator/index.d.cts +0 -44
- package/dist/components/trend-indicator/index.d.ts +0 -44
- package/dist/components/trend-indicator/index.js +0 -8
- package/dist/components/trend-indicator/index.js.map +0 -1
- package/dist/format-metric-value-MXm5DtQ_.d.cts +0 -24
- package/dist/format-metric-value-MXm5DtQ_.d.ts +0 -24
- package/dist/hooks/index.cjs +0 -31
- package/dist/hooks/index.cjs.map +0 -1
- package/dist/hooks/index.css +0 -103
- package/dist/hooks/index.css.map +0 -1
- package/dist/hooks/index.d.cts +0 -272
- package/dist/hooks/index.d.ts +0 -272
- package/dist/hooks/index.js +0 -31
- package/dist/hooks/index.js.map +0 -1
- package/dist/leaderboard-chart-BKYYXcg2.d.ts +0 -83
- package/dist/leaderboard-chart-DR7CGb0L.d.cts +0 -83
- package/dist/legend-C2grwnWk.d.cts +0 -9
- package/dist/legend-Cj0xM5dU.d.ts +0 -9
- package/dist/providers/index.cjs +0 -21
- package/dist/providers/index.cjs.map +0 -1
- package/dist/providers/index.css +0 -103
- package/dist/providers/index.css.map +0 -1
- package/dist/providers/index.d.cts +0 -28
- package/dist/providers/index.d.ts +0 -28
- package/dist/providers/index.js +0 -21
- package/dist/providers/index.js.map +0 -1
- package/dist/themes-BmVGrYnF.d.ts +0 -67
- package/dist/themes-CyjKm-P_.d.cts +0 -67
- package/dist/types-CuUEszrM.d.ts +0 -19
- package/dist/types-DZordNiO.d.cts +0 -505
- package/dist/types-DZordNiO.d.ts +0 -505
- package/dist/types-I67mddpr.d.cts +0 -78
- package/dist/types-I67mddpr.d.ts +0 -78
- package/dist/types-KtOPPzPX.d.cts +0 -19
- package/dist/utils/index.cjs +0 -44
- package/dist/utils/index.cjs.map +0 -1
- package/dist/utils/index.d.cts +0 -226
- package/dist/utils/index.d.ts +0 -226
- package/dist/utils/index.js +0 -44
- package/dist/utils/index.js.map +0 -1
- package/dist/with-responsive-CNfhzAUu.d.cts +0 -18
- package/dist/with-responsive-CNfhzAUu.d.ts +0 -18
- package/src/hooks/use-has-legend-child.ts +0 -22
|
@@ -26,10 +26,12 @@ describe( 'BarChart', () => {
|
|
|
26
26
|
],
|
|
27
27
|
};
|
|
28
28
|
|
|
29
|
-
const renderWithTheme = ( props = {} ) => {
|
|
29
|
+
const renderWithTheme = ( props = {}, children = undefined ) => {
|
|
30
30
|
return render(
|
|
31
31
|
<GlobalChartsProvider>
|
|
32
|
-
<BarChart { ...defaultProps } { ...props }
|
|
32
|
+
<BarChart { ...defaultProps } { ...props }>
|
|
33
|
+
{ children }
|
|
34
|
+
</BarChart>
|
|
33
35
|
</GlobalChartsProvider>
|
|
34
36
|
);
|
|
35
37
|
};
|
|
@@ -123,39 +125,54 @@ describe( 'BarChart', () => {
|
|
|
123
125
|
} );
|
|
124
126
|
|
|
125
127
|
describe( 'Legend', () => {
|
|
128
|
+
const multiSeriesData = [
|
|
129
|
+
{
|
|
130
|
+
label: 'Series A',
|
|
131
|
+
data: [ { date: new Date( '2024-01-01' ), value: 10, label: 'Jan 1' } ],
|
|
132
|
+
options: {},
|
|
133
|
+
},
|
|
134
|
+
{
|
|
135
|
+
label: 'Series B',
|
|
136
|
+
data: [ { date: new Date( '2024-01-01' ), value: 20, label: 'Jan 1' } ],
|
|
137
|
+
options: {},
|
|
138
|
+
},
|
|
139
|
+
];
|
|
140
|
+
|
|
126
141
|
test( 'shows legend when showLegend is true', () => {
|
|
127
|
-
renderWithTheme( {
|
|
128
|
-
showLegend: true,
|
|
129
|
-
data: [
|
|
130
|
-
{
|
|
131
|
-
label: 'Series A',
|
|
132
|
-
data: [ { date: new Date( '2024-01-01' ), value: 10, label: 'Jan 1' } ],
|
|
133
|
-
options: {},
|
|
134
|
-
},
|
|
135
|
-
{
|
|
136
|
-
label: 'Series B',
|
|
137
|
-
data: [ { date: new Date( '2024-01-01' ), value: 20, label: 'Jan 1' } ],
|
|
138
|
-
options: {},
|
|
139
|
-
},
|
|
140
|
-
],
|
|
141
|
-
} );
|
|
142
|
+
renderWithTheme( { showLegend: true, data: multiSeriesData } );
|
|
142
143
|
expect( screen.getByText( 'Series A' ) ).toBeInTheDocument();
|
|
143
144
|
expect( screen.getByText( 'Series B' ) ).toBeInTheDocument();
|
|
144
145
|
} );
|
|
145
146
|
|
|
146
147
|
test( 'hides legend when showLegend is false', () => {
|
|
147
|
-
renderWithTheme( {
|
|
148
|
-
showLegend: false,
|
|
149
|
-
data: [
|
|
150
|
-
{
|
|
151
|
-
label: 'Series A',
|
|
152
|
-
data: [ { date: new Date( '2024-01-01' ), value: 10, label: 'Jan 1' } ],
|
|
153
|
-
options: {},
|
|
154
|
-
},
|
|
155
|
-
],
|
|
156
|
-
} );
|
|
148
|
+
renderWithTheme( { showLegend: false, data: multiSeriesData } );
|
|
157
149
|
expect( screen.queryByText( 'Series A' ) ).not.toBeInTheDocument();
|
|
158
150
|
} );
|
|
151
|
+
|
|
152
|
+
test( 'renders composition legend as child component', () => {
|
|
153
|
+
renderWithTheme( { data: multiSeriesData }, <BarChart.Legend /> );
|
|
154
|
+
|
|
155
|
+
expect( screen.getAllByTestId( 'legend-item' ) ).toHaveLength( 2 );
|
|
156
|
+
expect( screen.getByText( 'Series A' ) ).toBeInTheDocument();
|
|
157
|
+
expect( screen.getByText( 'Series B' ) ).toBeInTheDocument();
|
|
158
|
+
} );
|
|
159
|
+
|
|
160
|
+
test( 'renders composition legend regardless of showLegend value', () => {
|
|
161
|
+
renderWithTheme( { data: multiSeriesData, showLegend: false }, <BarChart.Legend /> );
|
|
162
|
+
|
|
163
|
+
expect( screen.getAllByTestId( 'legend-item' ) ).toHaveLength( 2 );
|
|
164
|
+
} );
|
|
165
|
+
|
|
166
|
+
test( 'renders composition legend in top position', () => {
|
|
167
|
+
renderWithTheme( { data: multiSeriesData }, <BarChart.Legend position="top" /> );
|
|
168
|
+
|
|
169
|
+
// Legend should appear before the chart content in DOM order
|
|
170
|
+
expect( screen.getAllByTestId( 'legend-item' ) ).toHaveLength( 2 );
|
|
171
|
+
const html = document.body.innerHTML;
|
|
172
|
+
expect( html.indexOf( 'data-testid="legend-horizontal"' ) ).toBeLessThan(
|
|
173
|
+
html.indexOf( 'role="grid"' )
|
|
174
|
+
);
|
|
175
|
+
} );
|
|
159
176
|
} );
|
|
160
177
|
|
|
161
178
|
describe( 'Grid Visibility', () => {
|
|
@@ -743,7 +760,7 @@ describe( 'BarChart', () => {
|
|
|
743
760
|
|
|
744
761
|
renderWithTheme( {
|
|
745
762
|
showLegend: true,
|
|
746
|
-
|
|
763
|
+
legend: { interactive: true },
|
|
747
764
|
chartId: 'test-interactive-bar-chart',
|
|
748
765
|
data: [
|
|
749
766
|
{
|
|
@@ -771,7 +788,7 @@ describe( 'BarChart', () => {
|
|
|
771
788
|
it( 'does not filter series when legendInteractive is false', () => {
|
|
772
789
|
renderWithTheme( {
|
|
773
790
|
showLegend: true,
|
|
774
|
-
|
|
791
|
+
legend: { interactive: false },
|
|
775
792
|
chartId: 'test-non-interactive-bar-chart',
|
|
776
793
|
data: [
|
|
777
794
|
{
|
|
@@ -795,7 +812,7 @@ describe( 'BarChart', () => {
|
|
|
795
812
|
it( 'shows all series when chartId is missing even if legendInteractive is true', () => {
|
|
796
813
|
renderWithTheme( {
|
|
797
814
|
showLegend: true,
|
|
798
|
-
|
|
815
|
+
legend: { interactive: true },
|
|
799
816
|
// No chartId provided
|
|
800
817
|
data: [
|
|
801
818
|
{
|
|
@@ -823,7 +840,7 @@ describe( 'BarChart', () => {
|
|
|
823
840
|
|
|
824
841
|
renderWithTheme( {
|
|
825
842
|
showLegend: true,
|
|
826
|
-
|
|
843
|
+
legend: { interactive: true },
|
|
827
844
|
chartId: 'test-all-hidden-bar-chart',
|
|
828
845
|
data: [
|
|
829
846
|
{
|
|
@@ -17,6 +17,7 @@ import {
|
|
|
17
17
|
} from '../../providers';
|
|
18
18
|
import { formatMetricValue, attachSubComponents } from '../../utils';
|
|
19
19
|
import { useChartChildren } from '../private/chart-composition';
|
|
20
|
+
import { ChartLayout } from '../private/chart-layout';
|
|
20
21
|
import { SingleChartContext } from '../private/single-chart-context';
|
|
21
22
|
import { withResponsive } from '../private/with-responsive';
|
|
22
23
|
import { useLeaderboardLegendItems } from './hooks';
|
|
@@ -110,31 +111,26 @@ const BarWithLabel = ( {
|
|
|
110
111
|
* LeaderboardChart component displays a ranked list of data with progress bars
|
|
111
112
|
* and optional comparison values.
|
|
112
113
|
*
|
|
113
|
-
* @param props
|
|
114
|
-
* @param props.data
|
|
115
|
-
* @param props.chartId
|
|
116
|
-
* @param props.width
|
|
117
|
-
* @param props.height
|
|
118
|
-
* @param props.withComparison
|
|
119
|
-
* @param props.withOverlayLabel
|
|
120
|
-
* @param props.primaryColor
|
|
121
|
-
* @param props.secondaryColor
|
|
122
|
-
* @param props.valueFormatter
|
|
123
|
-
* @param props.deltaFormatter
|
|
124
|
-
* @param props.loading
|
|
125
|
-
* @param props.animation
|
|
126
|
-
* @param props.showLegend
|
|
127
|
-
* @param props.
|
|
128
|
-
* @param props.
|
|
129
|
-
* @param props.
|
|
130
|
-
* @param props.
|
|
131
|
-
* @param props.
|
|
132
|
-
* @param props.
|
|
133
|
-
* @param props.legendInteractive - Whether legend items are interactive (clickable to toggle series visibility)
|
|
134
|
-
* @param props.gap - Spacing between legend and chart content
|
|
135
|
-
* @param props.children - Child components for composition API
|
|
136
|
-
* @param props.className - Additional CSS class name
|
|
137
|
-
* @param props.style - Custom styling for the chart container
|
|
114
|
+
* @param props - Component props
|
|
115
|
+
* @param props.data - Array of leaderboard entries to display
|
|
116
|
+
* @param props.chartId - Optional unique identifier for the chart
|
|
117
|
+
* @param props.width - Optional width of the chart container in pixels
|
|
118
|
+
* @param props.height - Optional height of the chart container in pixels
|
|
119
|
+
* @param props.withComparison - Whether to show comparison data
|
|
120
|
+
* @param props.withOverlayLabel - Whether to overlay the label on top of the bar
|
|
121
|
+
* @param props.primaryColor - Primary color for current period bars
|
|
122
|
+
* @param props.secondaryColor - Secondary color for comparison period bars
|
|
123
|
+
* @param props.valueFormatter - Custom formatter for values
|
|
124
|
+
* @param props.deltaFormatter - Custom formatter for delta values
|
|
125
|
+
* @param props.loading - Whether the chart is in loading state
|
|
126
|
+
* @param props.animation - Whether the chart should animate on load
|
|
127
|
+
* @param props.showLegend - Whether to show legend
|
|
128
|
+
* @param props.legend - Legend configuration (orientation, position, alignment, shape, shapeStyles, interactive)
|
|
129
|
+
* @param props.legendLabels - Custom labels for legend items
|
|
130
|
+
* @param props.gap - Spacing between legend and chart content
|
|
131
|
+
* @param props.children - Child components for composition API
|
|
132
|
+
* @param props.className - Additional CSS class name
|
|
133
|
+
* @param props.style - Custom styling for the chart container
|
|
138
134
|
* @return JSX element representing the leaderboard chart
|
|
139
135
|
*/
|
|
140
136
|
const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
@@ -151,24 +147,22 @@ const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
|
151
147
|
animation,
|
|
152
148
|
loading = false,
|
|
153
149
|
showLegend = false,
|
|
154
|
-
|
|
155
|
-
legendPosition = 'bottom',
|
|
156
|
-
legendAlignment = 'center',
|
|
157
|
-
legendShape = 'circle',
|
|
158
|
-
legendShapeStyles: legendShapeStylesProp,
|
|
150
|
+
legend = {},
|
|
159
151
|
legendLabels,
|
|
160
|
-
legendInteractive = false,
|
|
161
152
|
gap = 'md',
|
|
162
153
|
className,
|
|
163
154
|
style,
|
|
164
155
|
children,
|
|
165
156
|
} ) => {
|
|
157
|
+
const legendInteractive = legend.interactive ?? false;
|
|
158
|
+
const legendPosition = legend.position ?? 'bottom';
|
|
159
|
+
|
|
166
160
|
const chartId = useChartId( providedChartId );
|
|
167
161
|
const { leaderboardChart: leaderboardChartSettings } = useGlobalChartsTheme();
|
|
168
|
-
const legendShapeStyles = { width: 8, height: 8, ...
|
|
162
|
+
const legendShapeStyles = { width: 8, height: 8, ...legend.shapeStyles };
|
|
169
163
|
|
|
170
164
|
// Process children to extract compound components
|
|
171
|
-
const {
|
|
165
|
+
const { legendChildren, nonLegendChildren } = useChartChildren( children, 'LeaderboardChart' );
|
|
172
166
|
const {
|
|
173
167
|
labelSpacing,
|
|
174
168
|
rowGap,
|
|
@@ -253,47 +247,43 @@ const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
|
253
247
|
// Handle empty or undefined data
|
|
254
248
|
if ( ! data || data.length === 0 ) {
|
|
255
249
|
return (
|
|
256
|
-
<SingleChartContext.Provider
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
} }
|
|
262
|
-
>
|
|
263
|
-
<Stack
|
|
264
|
-
direction="column"
|
|
265
|
-
data-testid="leaderboard-chart-container"
|
|
250
|
+
<SingleChartContext.Provider value={ { chartId } }>
|
|
251
|
+
<ChartLayout
|
|
252
|
+
legendPosition={ legendPosition }
|
|
253
|
+
legendElement={ false }
|
|
254
|
+
legendChildren={ legendChildren }
|
|
266
255
|
className={ clsx(
|
|
267
256
|
styles.leaderboardChart,
|
|
268
|
-
{
|
|
269
|
-
|
|
257
|
+
{
|
|
258
|
+
[ styles[ 'leaderboardChart--responsive' ] ]: ! propWidth && ! propHeight,
|
|
259
|
+
[ styles[ 'leaderboardChart--loading' ] ]: loading,
|
|
260
|
+
},
|
|
270
261
|
className
|
|
271
262
|
) }
|
|
272
263
|
gap={ gap }
|
|
273
|
-
style={ {
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
height: propHeight || undefined,
|
|
277
|
-
} }
|
|
264
|
+
style={ { ...style, width: propWidth || undefined, height: propHeight || undefined } }
|
|
265
|
+
data-testid="leaderboard-chart-container"
|
|
266
|
+
trailingContent={ nonLegendChildren }
|
|
278
267
|
>
|
|
279
268
|
<div className={ styles.emptyState }>
|
|
280
269
|
{ loading
|
|
281
270
|
? __( 'Loading…', 'jetpack-charts' )
|
|
282
271
|
: __( 'No data available', 'jetpack-charts' ) }
|
|
283
272
|
</div>
|
|
284
|
-
|
|
285
|
-
{ otherChildren }
|
|
286
|
-
</Stack>
|
|
273
|
+
</ChartLayout>
|
|
287
274
|
</SingleChartContext.Provider>
|
|
288
275
|
);
|
|
289
276
|
}
|
|
290
277
|
|
|
291
278
|
const legendElement = showLegend && (
|
|
292
279
|
<Legend
|
|
293
|
-
orientation={
|
|
280
|
+
orientation={ legend.orientation ?? 'horizontal' }
|
|
294
281
|
position={ legendPosition }
|
|
295
|
-
alignment={
|
|
296
|
-
|
|
282
|
+
alignment={ legend.alignment ?? 'center' }
|
|
283
|
+
labelStyles={ legend.labelStyles }
|
|
284
|
+
itemClassName={ legend.itemClassName }
|
|
285
|
+
itemStyles={ legend.itemStyles }
|
|
286
|
+
shape={ legend.shape ?? 'circle' }
|
|
297
287
|
shapeStyles={ legendShapeStyles }
|
|
298
288
|
chartId={ chartId }
|
|
299
289
|
interactive={ legendInteractive }
|
|
@@ -301,16 +291,11 @@ const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
|
301
291
|
);
|
|
302
292
|
|
|
303
293
|
return (
|
|
304
|
-
<SingleChartContext.Provider
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
} }
|
|
310
|
-
>
|
|
311
|
-
<Stack
|
|
312
|
-
direction="column"
|
|
313
|
-
data-testid="leaderboard-chart-container"
|
|
294
|
+
<SingleChartContext.Provider value={ { chartId } }>
|
|
295
|
+
<ChartLayout
|
|
296
|
+
legendPosition={ legendPosition }
|
|
297
|
+
legendElement={ legendElement }
|
|
298
|
+
legendChildren={ legendChildren }
|
|
314
299
|
className={ clsx(
|
|
315
300
|
styles.leaderboardChart,
|
|
316
301
|
{
|
|
@@ -325,9 +310,9 @@ const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
|
325
310
|
width: propWidth || undefined,
|
|
326
311
|
height: propHeight || undefined,
|
|
327
312
|
} }
|
|
313
|
+
data-testid="leaderboard-chart-container"
|
|
314
|
+
trailingContent={ nonLegendChildren }
|
|
328
315
|
>
|
|
329
|
-
{ legendPosition === 'top' && legendElement }
|
|
330
|
-
|
|
331
316
|
<div className={ styles.leaderboardChart__content }>
|
|
332
317
|
{ allSeriesHidden ? (
|
|
333
318
|
<div className={ styles.emptyState }>
|
|
@@ -375,12 +360,7 @@ const LeaderboardChartInternal: FC< LeaderboardChartProps > = ( {
|
|
|
375
360
|
</Grid>
|
|
376
361
|
) }
|
|
377
362
|
</div>
|
|
378
|
-
|
|
379
|
-
{ legendPosition === 'bottom' && legendElement }
|
|
380
|
-
|
|
381
|
-
{ /* Render children from composition API */ }
|
|
382
|
-
{ otherChildren }
|
|
383
|
-
</Stack>
|
|
363
|
+
</ChartLayout>
|
|
384
364
|
</SingleChartContext.Provider>
|
|
385
365
|
);
|
|
386
366
|
};
|
|
@@ -169,8 +169,7 @@ describe( 'LeaderboardChart', () => {
|
|
|
169
169
|
data={ mockData }
|
|
170
170
|
withComparison={ true }
|
|
171
171
|
showLegend={ true }
|
|
172
|
-
|
|
173
|
-
legendShapeStyles={ { width: 10, height: 6 } }
|
|
172
|
+
legend={ { shape: 'rect', shapeStyles: { width: 10, height: 6 } } }
|
|
174
173
|
/>
|
|
175
174
|
);
|
|
176
175
|
|
|
@@ -306,7 +305,7 @@ describe( 'LeaderboardChart', () => {
|
|
|
306
305
|
data={ mockData }
|
|
307
306
|
withComparison={ true }
|
|
308
307
|
showLegend={ true }
|
|
309
|
-
|
|
308
|
+
legend={ { interactive: true } }
|
|
310
309
|
/>
|
|
311
310
|
);
|
|
312
311
|
|
|
@@ -320,7 +319,7 @@ describe( 'LeaderboardChart', () => {
|
|
|
320
319
|
data={ mockData }
|
|
321
320
|
withComparison={ true }
|
|
322
321
|
showLegend={ true }
|
|
323
|
-
|
|
322
|
+
legend={ { interactive: false } }
|
|
324
323
|
/>
|
|
325
324
|
);
|
|
326
325
|
|
|
@@ -335,7 +334,7 @@ describe( 'LeaderboardChart', () => {
|
|
|
335
334
|
data={ mockData }
|
|
336
335
|
withComparison={ true }
|
|
337
336
|
showLegend={ true }
|
|
338
|
-
|
|
337
|
+
legend={ { interactive: true } }
|
|
339
338
|
/>
|
|
340
339
|
);
|
|
341
340
|
|
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import { type ReactNode } from 'react';
|
|
2
2
|
import { BaseChartProps, LeaderboardEntry } from '../../types';
|
|
3
|
-
import type { LegendShapeStyles } from '../../components/legend';
|
|
4
3
|
|
|
5
4
|
export interface LeaderboardChartProps
|
|
6
5
|
extends Pick<
|
|
@@ -8,16 +7,12 @@ export interface LeaderboardChartProps
|
|
|
8
7
|
| 'className'
|
|
9
8
|
| 'data'
|
|
10
9
|
| 'showLegend'
|
|
11
|
-
| '
|
|
12
|
-
| 'legendPosition'
|
|
13
|
-
| 'legendAlignment'
|
|
14
|
-
| 'legendShape'
|
|
10
|
+
| 'legend'
|
|
15
11
|
| 'chartId'
|
|
16
12
|
| 'width'
|
|
17
13
|
| 'height'
|
|
18
14
|
| 'size'
|
|
19
15
|
| 'gap'
|
|
20
|
-
| 'legendInteractive'
|
|
21
16
|
| 'animation'
|
|
22
17
|
> {
|
|
23
18
|
/**
|
|
@@ -62,11 +57,6 @@ export interface LeaderboardChartProps
|
|
|
62
57
|
'--a8c--charts--leaderboard--bar--border-radius'?: string;
|
|
63
58
|
};
|
|
64
59
|
|
|
65
|
-
/**
|
|
66
|
-
* Styles for legend shapes (width, height, margin).
|
|
67
|
-
*/
|
|
68
|
-
legendShapeStyles?: LegendShapeStyles;
|
|
69
|
-
|
|
70
60
|
/**
|
|
71
61
|
* Custom labels for legend items
|
|
72
62
|
*/
|