3

我目前正在学习 VueJs 并摆弄 Chart.js ( https://github.com/apertureless/vue-chartjs )。我试图让甜甜圈具有反应性行为,但我只能使用 ref 属性让它工作,据我了解,这是不好的风格。我的第一个问题是,避免$refs是好的风格的假设是否正确。

我的方法的第一个问题是我不知道 mixins,但是关于如何使用 vue-chartjs 的唯一示例反应性地使用了它(https://github.com/apertureless/vue-chartjs/blob/master/src/ examples/ReactiveExample.js是参考点)我在我的 Vue 组件中创建了一个名为 updateData 的方法,它将重置我的组件 chartData,然后将其设置为道具数据。首先,这是我的代码:

chart.blade.php(网页视图):

<html>
    <head>
        <meta charset="utf-8">
        <title>Testchart</title>
        <link rel="stylesheet" href="css/app.css">
    </head>
    <body>
        <div id="app">
            <h1>Testchart</h1>
            <doughnut :data="doughnut_data" :options="doughnut_options" ref="chart"></doughnut>
            <button-reduce v-on:numberreduced="reduce"></button-reduce>
        </div>
        <script src="js/app.js" charset="utf-8"></script>
        </body>
</html>

应用程序.js:

/**
 * First we will load all of this project's JavaScript dependencies which
 * includes Vue and other libraries. It is a great starting point when
 * building robust, powerful web applications using Vue and Laravel.
 */

require('./bootstrap');

/**
 * Next, we will create a fresh Vue application instance and attach it to
 * the page. Then, you may begin adding components to this application
 * or customize the JavaScript scaffolding to fit your unique needs.
 */



Vue.component('doughnut', require('./components/testDoughnut.vue'));
Vue.component('button-reduce', require('./components/button.vue'));

const app = new Vue({
    el: '#app',
    data: {
        doughnut_data: {
                labels: ['VueJs', 'EmberJs', 'ReactJs', 'AngularJs'],
                datasets: [
                    {
                        backgroundColor: [
                            '#41B883',
                            '#E46651',
                            '#00D8FF',
                            '#DD1B16'
                        ],
                        data: [40, 20, 80, 10]
                    }
                ]
            },
        doughnut_options: {
            responsive: true, 
            maintainAspectRatio: false
        }
    },
    methods: {
        reduce() {
            this.doughnut_data.datasets[0].data[2] = this.doughnut_data.datasets[0].data[2] - 5;
            this.$refs.chart.updateData();
        }
    }
});

最后但同样重要的是,我的 Vue 组件 testDoughnut.vue

<script>
import { Doughnut, mixins } from 'vue-chartjs'

export default Doughnut.extend({
  mixins: [mixins.reactiveData],
  props: ["data", "options"],
  data() {
    return {
      chartData: ''
    }
  },
  created() {
     this.updateData();
  },
  mounted () {
    this.renderChart(this.chartData, this.options)
  },
  methods: {
    updateData() {
      this.chartData = {}; // without this step, it does not work (no reactive behaviour). Why is this necessary?
      this.chartData = this.data;
   }
  }
})

</script>

出现了以下问题:

  1. (从上面):避免$refs是一件好事吗?
  2. 为什么无法直接从我的 web 视图更新 chartData? :chartData="doughnut_data"没用,我需要使用自定义道具“数据”
  3. 在我的 testDoughnut.vue 中,需要先将 chartData 重置为一个空的 JSON 对象,然后再将其分配给 this.data。为什么需要此重置?从桌面开发(C#)开始,我认为我可以this.chartData = this.data在不需要空对象的情况下进行编写。
  4. 有没有更好的方法来处理这个问题,而不是我做的方式(使用 ref)?
4

1 回答 1

3

vue-chartjs 作者在这里。

关于混入: 包括两个混入。vue 中的 Mixins 只是将一些逻辑和功能提取到单独的文件中,以便您可以重用它们。

就像在文档中所说的那样,有两个 mixin。

  • reactiveProp 和
  • 反应数据

因为,有两个主要场景,如何将数据传递给图表组件。一种可能的情况是,例如在 laravel 环境中,您可以通过 props 将数据直接传递给组件。

<my-chart :chart-data="..."></my-chart>

另一个用例是,如果您有 API 并发出 fetch / API 请求。但是你的图表数据不是道具,是 vue 的 data() 函数中的一个变量。

使固定

好吧,您的代码有点过于复杂了。

你宁愿需要 reactiveProp mixin。

<script>
import { Doughnut, mixins } from 'vue-chartjs'

export default Doughnut.extend({
  mixins: [mixins.reactiveProp],
  props: ["options"],


  mounted () {
    this.renderChart(this.chartData, this.options)
  }

})

</script>

mixin 将创建一个名为 chartData 的道具并为其添加一个观察者。每次数据更改时,它都会更新图表或重新渲染。如果添加新数据集,则需要重新渲染图表。

你的问题

  1. 好吧,如果你使用正确的 mixin,你就不需要 $ref
  2. 模板中的camelCase需要用破折号'-'编写
  3. 也许它有问题,因为您复制了 data 属性。mixin 总是自动将您的 chartData 创建为属性或 data() 函数变量。所以你不需要自己创建它。但是我想这可能是一个竞争条件。在 vue 的 create() 钩子中没有设置数据的地方。https://vuejs.org/v2/guide/instance.html#Lifecycle-Diagram
于 2017-02-03T16:39:49.347 回答