victorgarciaesgi / vue-chart-3

📊 A simple wrapper around Chart.js 3 for Vue 2 & 3
https://vue-chart-3.netlify.app/
MIT License
309 stars 108 forks source link

Reactive chart on watch event #87

Closed chiptu closed 2 years ago

chiptu commented 2 years ago

Hey , Thanks a lot for your package .

The problem

Concisely i would like to know how to refresh the chartInstance data with an on watch event for example.

I noticed in the doc that you update data with a function in the setup function.

In the ChartJs documentation it seems possible to update data on any events and i can't access and update data ( first time i'm using chartjs it maybe comes from my knowledge lack).

Here in my example i'm having the props weekstat updated which triggers the watch event but i can't update the chartInstance in it ...

My code

<template>
    <div class=" w-full h-full  " >
        <LineChart ref='lineChartRef' :chartData="testData" :height="this.myheight" :options="options"/>
    </div>
</template>

<script >
import { computed, ref } from "vue";
import { LineChart, useLineChart } from "vue-chart-3";
import { Chart, ChartData, ChartOptions, registerables } from "chart.js";
import {usePage} from "@inertiajs/inertia-vue3";

Chart.register(...registerables);
Chart.defaults.font.size = 20;
Chart.defaults.font.style = "oblique";
Chart.defaults.color="#fff";
Chart.defaults.borderColor ="#fff";
Chart.defaults.elements.point.radius =5;

export default {
    name: "Line",
    components: {LineChart},
    props: ['weekstat','qrid'],

    mounted() {

    },

    watch:{
        ['weekstat']: function () {
            console.log('watch in Line');
            console.log(this.weekstat);
            console.log(this.$refs.lineChartRef.chartInstance);
            console.log(this.$refs.lineChartRef.data);

            //this.$refs.lineChartRef.chartInstance.datasets.data = JSON.parse(this.weekstat);
            //this.$refs.lineChartRef.chartInstance.update();
            //this.$forceUpdate();
        },
    },

    setup(props) {

        const testData =  {
            labels: ["Lundi", "Mardi", "Mercredi", "Jeudi", "Vendredi","Samedi","Dimanche"],
            datasets: [
                {
                    label: 'Scan/jour',
                    data: JSON.parse(props.weekstat),
                    fill: {target: 'origin',
                    above: 'rgb(189, 189, 189)'},

                    borderColor: 'rgb(255, 255, 255)',
                    tension: 0.3,
                    borderWidth:3,
                },
            ]
        };
        const options ={
            scales: {
                y:{
                    beginAtZero: true
                }
            },

        };

        return {
            testData,
            options,
        };
    },
    beforeMount(){
        if (window.matchMedia("(min-width: 768px)").matches) {
            this.myheight = 360;
        } else {
            this.myheight = 420;
        }

    },

    data: () => {
        return {
            myheight :null,
        }
    }

};
</script>

Version of vue-chart-3

vue-chart-3: 3.0.7 chart.js: 3.7.0

Version of Vue

Vue 3.0.5

victorgarciaesgi commented 2 years ago

You need to make your testData reactive by using computed if your are using Composition Api. In your exemple you are using the two syntax so that's wrong. Use either one and testData needs to be reactive

chiptu commented 2 years ago

Thanks a lot i wasn't used to new syntax and misunderstand few things !