首页 > 解决方案 > options.scales.yAxes[0].ticks.callback 没有在 ember-cli-chart 中动态更新

问题描述

我已经嵌入ember-cli-chart到我的hbs文件中

<div class="chart">
    {{ember-chart type='line' data=data options=options}}
</div>

在我的组件文件中,我创建了一个选项属性为

options: computed('metric', function() {
  let opts = defaultOptions;
  if (this.metric === 'height') {
     opts.scales.yAxes = [{
         ticks: {
             callback: function(value, index, values) {
              // code to return labels
             }
        }
     }]
  } else {
     opts.scales.yAxes = [{
         ticks: {
             callback: function(item, index, items) {
                 // code to return labels
             }
        }
     }]
  }

  return opts;
});

我想根据当前选定的指标显示 Y 轴标签。当第一次加载图表时,它会在 y 轴上呈现正确的标签,如果我更改指标,那么将使用相同的回调而不是另一个(在其他部分)并呈现相同的标签,但具有更新的数据值。有人可以帮忙吗?

标签: ember.jscharts

解决方案


嗯,我不知道插件或chart.js此事,但在查看ember-chart组件的源代码时,我看到

didUpdateAttrs() {
    this._super(...arguments);
    this.updateChart();
},

updateChart() {
    let chart   = this.get('chart');
    let data    = this.get('data');
    let options = this.get('options');
    let animate = this.get('animate');

    if (chart) {
        chart.config.data = data;
        chart.config.options = options;
        if (animate) {
            chart.update();
        } else {
            chart.update(0);
        }
    }
}

所以,为了chart.js更新,你需要didUpdateAttrs开火,这意味着在你的情况下,它options本身需要改变。我不知道你是如何创建defaultOptions的,但假设这个引用永远不会改变,没有理由didUpdateAttrs会触发,因为你没有更改对的引用options(你只是defaultOptions在计算中更改子道具)。我会假设:

import { assign } from '@ember/polyfills';
...
options: computed('metric', function() {
  let opts = assign({}, defaultOptions);
  if (this.metric === 'height') {
     opts.scales.yAxes = [{
         ticks: {
             callback: function(value, index, values) {
              // code to return labels
             }
        }
     }]
  } else {
     opts.scales.yAxes = [{
         ticks: {
             callback: function(item, index, items) {
                 // code to return labels
             }
        }
     }]
  }

  return opts;
})

足以触发您想要的行为,因为我们总是在重新计算options发生时返回一个新对象。


推荐阅读