vue3 で chart.js

php側でグラフを生成しようかなと思ったがまともなライブラリが無い
（古すぎる or googleChartも非推奨）

ということで chart.js で出力して、当該画像を png 化してやろう。

参考
https://zenn.dev/sa2knight/articles/cc60e3e7c44968

![hogera.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/31338/94ae98e9-ec70-7e30-9c1f-0ecd48fdbcef.png)


# インスコ ♡
```
npm install chart.js@^3.1.0 vue-chart-3
```

# コード

```
<template>
    <div>
        <PieChart :chartData="pieData" />
    </div>
</template>

<script>

    import { Chart, registerables } from "chart.js";
    import { PieChart, LineChart } from "vue-chart-3";
    Chart.register(...registerables);

    export default {

        components: {
            PieChart,
            LineChart,
        },

        //computed に指定すること！！
        computed: {
            pieData() {
                return {
                    labels: ["Red", "Blue", "Yellow"],
                    datasets: [
                        {
                            label: "My First Dataset",
                            data: [300, 50, 100],
                            backgroundColor: [
                                "rgb(255, 99, 132)",
                                "rgb(54, 162, 235)",
                                "rgb(255, 205, 86)",
                            ],
                            hoverOffset: 4,
                        },
                    ],
                };
            },
        },

        data(){
            return {
            }
        },

        mounted() {
        },

        created(){
        },

        methods: {
        },
    }

</script>
```

とりあえず、これで出力はできましたね。

# つづいて背景色を白に

サーバーで保存する際、グラフの背景色を指定しないと真っ黒になる。
以下、対応版。

```hoge.js
<template>
    <div>
        <div>
            <PieChart :chartData="pieData" />
        </div>
        <el-button @click="saveCanvas"  type="danger">グラフを画像化して保存</el-button>
    </div>
</template>

<script>

    import { Chart, registerables } from "chart.js";
    import { PieChart, LineChart } from "vue-chart-3";

    Chart.register(
        {
            id: 'customPluginName',
            beforeDraw: function(c){
                var ctx = c.ctx;
                ctx.fillStyle = "#ffffff";
                ctx.fillRect(0, 0, ctx.canvas.width,ctx.canvas.height);
                ctx.save();
            }
        }
    );

    Chart.register(...registerables);

    export default {

        components: {
            PieChart,
            LineChart,
        },


        // mixins: [reactiveProp],
        props: ['options'],

        //computed に指定すること！！
        computed: {
            pieData() {
                return {

                    labels: ["Red", "Blue", "Yellow"],
                    datasets: [
                        {
                            label: "My First Dataset",
                            data: [300, 50, 100],
                            backgroundColor: [
                                "rgb(255, 99, 132)",
                                "rgb(54, 162, 235)",
                                "rgb(255, 205, 86)",
                            ],
                            hoverOffset: 4,
                        },
                    ],
                };
            },
        },

        data(){
            return {
            }
        },

        mounted () {

        },

        created(){
        },

        methods: {

            // グラフを 画像にして保存
            saveCanvas(){
                var canvas = document.getElementsByTagName('canvas')[0].toDataURL();
                canvas = canvas.replace(/^data:image\/png;base64,/, '');

                let dataform = new FormData();
                dataform.append('canvas',canvas);

                axios.post('/hoges/upload/', dataform).then(e => {

                    console.log("成功");
                }).catch((error) => {
                    console.log("エラー");
                });

            },

        },
    }

</script>


```

いやー久しぶりにはまった。
vue2のときと違うんだよな。