はじめに
CoreUIのReact Chart.jsで100%積み上げ棒グラフを描画することになりました。
調べてみるとChart.jsにはchartjs-plugin-stacked100
という物があり
ふむふむこれシンプルだしCoreUIのChart.jsでもできるかなと使ってみましたが描画できなかったので、素直にdata
やoption
を設定し実装を行いました。
今回はその説明をします。
実装
以下コードには含んでいませんが色の設定を追加して描画しています。
1. 表示したいデータ
const chartData: ChartData<'bar'> = {
labels: ['January', 'February', 'March', 'April', 'May', 'June', 'July'],
datasets: [
{
label: 'My First Dataset',
data: [65, 59, 80, 81, 56, 55, 40],
},
{
label: 'My Second Dataset',
data: [28, 48, 40, 19, 86, 27, 90],
},
],
};
return (
<CChart type="bar" data={chartData} />
)

ただデータを入れるだけではデフォルトの表示になってしまいます。
2. グラフを100%表示にするために今回追加した関数
const calculatePercentage = (data: ChartData<'bar'>): ChartData<'bar'> => {
const totals = data.datasets.reduce((acc, dataset) => {
dataset.data.forEach((value, index) => {
acc[index] = (acc[index] || 0) + value;
});
return acc;
}, [] as number[]);
const datasetsWithPercentage = data.datasets.map((dataset) => ({
...dataset,
data: dataset.data.map((value, index) => {
const total = totals[index];
const percentage = total ? (value / total) * 100 : 0;
return percentage;
}),
}));
return { ...data, datasets: datasetsWithPercentage };
};
return (
<CChart type="bar" data={calculatePercentage(chartData)} />
)

このままではまだ積み上がっていないし、カーソルを当てた時に表示される数字も違う、、、
3. optionsでグラフの設定を行う
ここでグラフの描画に関する具体的な設定を行います。
今回行ったのは
・横に並んで表示されてしまうグラフを縦に積み上げて表示
・tooltipに表示される内容の変更
です。
labelの部分を変更することで表示する内容を変えるができます。
const chartOption = (data: ChartData<'bar'>) => ({
scales: {
x: {
stacked: true,
},
y: {
stacked: true,
},
},
plugins: {
tooltip: {
callbacks: {
label: (context: TooltipItem<'bar'>) => {
const label = context.dataset.label || '';
const valueIndex = context.dataIndex;
const originalValue =
data.datasets[context.datasetIndex]?.data[valueIndex];
return `${label}: ${originalValue}`;
},
},
},
},
});
return (
<CChart type="bar" data={calculatePercentage(chartData)} options={chartOption(chartData)} />
)

以上のようにすることでpluginなしで100%積み上げ棒グラフを描画することができました。
終わりに
今回はCoreUIのReact Chart.jsで100%積み上げ棒グラフを描画する方法を紹介しました。
違うやり方があるよーとか別のパッケージ使えるよとかあったらじゃんじゃんコメント待っています。
最後まで読んでいただきありがとうございました。