Chart.js v2图表在Angular 2中无法显示(但Chart.js v1可以完美工作)

8

我正在一个 Angular2 属性指令内呈现图表(Angular2 团队采用的方法)。这种方法适用于 chart.js,但不适用于 chart.js 2.x

属性指令的代码如下...

import {Directive, ElementRef, Input} from '@angular/core';

declare var Chart:any;

@Directive({
  selector: '[bargraph]'
})

export class BarGraphDirective {

  el:any;
  myChart:any;

  constructor(element:ElementRef) {
    this.el = element.nativeElement;
  }

  ngAfterViewInit() {
    var canvas = this.el;
    var ctx = canvas.getContext('2d');

    var _data = {
      labels: ["01-01",
        "01-04",
        "01-15",
        "02-03",
        "03-25",
        "04-03",
        "04-14",
        "05-27",
        "05-27",
        "08-03"],
      datasets: [{
        data: [5, 13, 23, 20, 5, 13, 23, 20, 110, 2],
        label: "female",
        borderColor: "rgba(197,23,1,0.8)",
        backgroundColor: "rgba(197,23,1,0.4)",
        hoverBackgroundColor: "rgba(197,23,1,1)",
        borderWidth: 1,
        pointBorderColor: "rgba(197,23,1,1)",
        pointBackgroundColor: "rgba(255,255,255,0.8)",
        pointBorderWidth: 1.5,
        tension: -1,
        yAxisID: "y-axis-1",
      }, ],
    };

    var _options = {
      scales: {
        xAxes: [{
          categorySpacing: 0
        }],
        yAxes: [{
          type: "linear",
          display: true,
          position: "left",
          id: "y-axis-1",
        }]
      }
    };

    this.myChart = new Chart(ctx, {
      type: "line",
      data: _data,
      options: _options
    });

    console.log(ctx);
    console.log(this.myChart);
  }
}

styling is ...

canvas[bargraph] {
  height: 400px !important;
  width: 700px !important;
}

这个组件使用了以下的内容...
<canvas bargraph width="700" height="400"></canvas>

在模板中。

一切都如预期的那样。 console.log语句显示ctx和this.myChart都在ngAfterViewInit生命周期钩子内定义。 没有错误。 图表只是不显示。

PS:Chart.js v2代码在Angular2之外可以正常工作,就像这个JS Fiddle一样 - http://jsfiddle.net/beehe4eg/

唯一的区别是DOM的钩子...

document.getElementById("barChart") // for the fiddle

element.nativeElement // in my code as per the approach in the angular 2 docs

文档中的属性指令以及特别针对DOM hook的介绍是...

https://angular.io/docs/ts/latest/guide/attribute-directives.html#!#our-first-draft

element.nativeElement钩子在使用相同方法的情况下,可与chart.js v1与angular2很好地配合使用。

请注意,github repo...https://github.com/valor-software/ng2-charts 正在使用chart.js v1,因此这并没有帮助。

希望有人能解决这个问题或修复它!先感谢了。


1
我无法重现你的问题。请查看此plunkr https://plnkr.co/edit/dYJuHrtEfVi5sPMpAQVP?p=preview chart^2.0.0-alpha - yurzui
@yurzui - 非常感谢您的关注 - 初步调查发现将SRC更改为https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.0-alpha/Chart.js会破坏它!!!即使它应该是相同的版本 - 有什么想法吗? - danday74
2个回答

10
< p>Canvas元素的父级必须是有效的HTML元素,不能是Angular2组件标签,如my-app

因此,在使用Chart.js时,这种方法不起作用:

<my-chart-component>
  <canvas></canvas>
</my-chart-component>

这个有效:

<div>
  <canvas></canvas>
</div>

不确定这是否是您的问题。


感谢您的回答 - 没有解决问题,但仍然非常有用,再次感谢 :) - danday74
1
谢谢,这正是我遇到的问题。 - Tim Green
那不完全正确。您可以使用任何元素作为根元素,然后使用ViewChild获取画布元素。 - Rosdi Kasim

4

跟进:

另一个可能的问题是您尝试在非块级元素中呈现画布。

默认情况下,任何使用标签选择器的Angular组件都是内联的

所以您可以将其改为块级元素:

:host {
  display: block;
}

答案

当前版本是2.1.0,API已经有所改变。2.0-alpha版本于2015年6月5日发布。https://github.com/chartjs/Chart.js/releases/tag/v2.0-alpha 您在jsfiddle中使用的版本是2.0.0-alpha4(发布于2015年6月22日,哈希值为9368c6079d989527dcd2072b6f18780b53e3113c)。

请按照下面的说明更改您的代码:

this.myChart = new Chart(ctx).Line({
  data: _data,
  options: _options
});

查看使用图表v2.0-alpha的工作范例,链接为:https://plnkr.co/edit/IFdEeMcS9lHGWrsUwkGb?p=preview

如果您使用语法2.1.3,则可以这样编写:

this.myChart = new Chart(ctx, {
  type: 'line',
  data: _data,
  options: _options
});

以下是使用v2.1.3的示例代码https://plnkr.co/edit/GubwdD9Voo3mBPYYKEEL?p=preview


感谢您的回答。我很想使用2.1.0版本,但在这个fiddle上...https://plnkr.co/edit/dYJuHrtEfVi5sPMpAQVP?p=preview...如果我切换到2.1.0版本,会得到奇怪的结果...您能帮忙吗?我想避免使用.Line,因为它是旧的API - 我想继续使用新的API - 谢谢。 - danday74
你好,我已经授予你这个赏金,但是这个问题还没有得到解答! - danday74
@danday74 我已经编辑了我的回答。你也可以在这个页面上看到很好的示例 https://github.com/chartjs/Chart.js/blob/master/samples/line.html - yurzui
非常感谢 @yurzui,非常感激,看起来正是我想要的 :) - danday74
@danday74 老实说,我很惊讶直接回答问题的答案没有被选为解决方案。在这种情况下,我至少会重新表述问题。 - yurzui

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接