概要
SvelteでChart.jsを使ってグラフを表示するときに、いくつかつまずきポイントがあったのでメモ
環境
Svelte: 3.54.0
chart.js: 4.2.1
TypeScript: 4.9.3
実装
途中のデータは適当
<script lang="ts">
import {
Chart,
LineController,
LineElement,
PointElement,
CategoryScale,
LinearScale,
Tooltip,
Legend,
} from 'chart.js';
import { onMount } from 'svelte';
let chartData = {
labels: ['January', 'February', 'March', 'April', 'May', 'June', 'July'],
datasets: [
{
label: 'Sample',
backgroundColor: 'rgb(255, 99, 132)',
borderColor: 'rgb(255, 99, 132)',
data: [0, 10, 5, 2, 20, 30, 45]
}
]
};
Chart.register(
LineController,
LineElement,
PointElement,
CategoryScale,
LinearScale,
Tooltip, // ツールチップ表示用,お好みで
Legend // 凡例表示用,お好みで
);
let chartCanvas: HTMLCanvasElement;
function renderChart() {
let chart = new Chart(chartCanvas, {
type: 'line',
data: chartData,
options: {}
});
}
onMount(renderChart);
</script>
<canvas bind:this={chartCanvas} />
つまずきポイント
Error: "category" is not a registered scale.
categoryとはなんぞや???となったが,どうもcontrollerやpluginなどを最初にimportして登録しなければならないらしい.前に使ったのが2系だったので解決法を探すのに時間を取られた…(categoryってなに?)
データの渡し方
bindを使えばいいらしい.
追加つまずき:データを時系列で表示する
https://www.chartjs.org/docs/latest/migration/v3-migration.html
moment is no longer specified as an npm dependency. If you are using the time or timeseries scales, you must include one of the available adapters and corresponding date library. You no longer need to exclude moment from your build.
とあるようにまず時系列で表示するためのライブラリを入れる必要がある.筆者はchartjs-adapter-moment
とmoment
を入れた.
npm install moment chartjs-adapter-moment --save
次に先程のコードを下記のように修正する.
<script lang="ts">
import {
Chart,
LineController,
LineElement,
PointElement,
CategoryScale,
LinearScale,
Tooltip,
Legend,
+ TimeScale
} from 'chart.js';
+ import 'chartjs-adapter-moment';
import { onMount } from 'svelte';
let chartData = {
labels: ['January', 'February', 'March', 'April', 'May', 'June', 'July'],
datasets: [
{
label: 'Sample',
backgroundColor: 'rgb(255, 99, 132)',
borderColor: 'rgb(255, 99, 132)',
data: [0, 10, 5, 2, 20, 30, 45]
}
]
};
Chart.register(
LineController,
LineElement,
PointElement,
CategoryScale,
LinearScale,
Tooltip,
Legend,
+ TimeScale
);
let chartCanvas: HTMLCanvasElement;
function renderChart() {
let chart = new Chart(chartCanvas, {
type: 'line',
data: chartData,
options: {
+ scales: {
+ x: {
+ type: 'time',
+ time: { unit: 'day'}
}
});
}
onMount(renderChart);
</script>
<canvas bind:this={chartCanvas} />
labelsの部分はDate型の配列を渡せば良い(書くのが面倒なので上記の例では変更していないが)
あとがき
React使えばよかったのでは?と何度か心折れかけたが,なんとかグラフの表示まではたどり着いた. 余裕があれば複合グラフの表示をしたいが,ドキュメント見てもやり方がわからん…