How implement Chart.js in Angular 2?

2020-07-14 05:57发布

问题:

I am using the latest version of Angular 2, V4.0.0 and I want to use graphs from the Chart.js library in my project without many complications.

How can I implement Chart.js in my angular project that does not give me problems in the final production?

回答1:

You can implement Chart.js in a simple way with the following instructions:

1. Create a new project with angular-cli, skip if you already have one created

ng new example-chartjs

2. Install Chart.js in your project

npm install chart.js --save

3. Import Chart into its component

import Chart from 'chart.js';

4. Use Chart in your view and component

In your view:

<canvas id="myChart" width="400" height="400"></canvas>

In your component:

ngOnInit() {

    var ctx = document.getElementById("myChart");
    var myChart = new Chart(ctx, {...});

}

The component should look similar to the following

import { Component, OnInit } from '@angular/core';
import Chart from 'chart.js';

@Component({
  selector: 'app-chart',
  templateUrl: './chart.component.html'
})

export class DashboardComponent implements OnInit {

  constructor() { }

  ngOnInit() {

    var ctx = document.getElementById("myChart");
    var myChart = new Chart(ctx, {....});

  }

}

Another alternative to use is to include the library from the file ".angular-cli.json"

1. Include in the scripts the library

"styles": [
  "styles.css"
],
"scripts": [
  "../node_modules/jquery/dist/jquery.min.js",
  "../node_modules/chart.js/dist/Chart.min.js"
]

2. Declare a variable of type "any" in the controller

declare var Chart:any;

3. Use Chart in your view and component

In your view:

<canvas id="myChart" width="400" height="400"></canvas>

In your component:

ngOnInit() {

    var ctx = document.getElementById("myChart");
    var myChart = new Chart(ctx, {...});

}

The component should look similar to the following

import { Component, OnInit } from '@angular/core';

declare var Chart:any;

@Component({
  selector: 'app-chart',
  templateUrl: './chart.component.html'
})

export class DashboardComponent implements OnInit {

  constructor() { }

  ngOnInit() {

    var ctx = document.getElementById("myChart");
    var myChart = new Chart(ctx, {....});

  }

}


回答2:

First
npm install chart.js --save

Second
npm install @types/chart.js --save

Third - import Chart into component this way
import * as Chart from 'chart.js';



回答3:

I've implemented the Chart.js on Angular at this way(first you'll need to install it using npm install chart.js --save):

The folder structure of my project

src/
  assets/
  app/
    charjs/
    services/

First I've created a service called report.service.ts :

src/app/services/report.service.ts

import { Injectable } from '@angular/core';
import { Http } from '@angular/http';
import 'rxjs/add/operator/map';
@Injectable()
export class ReportService {
  constructor(public http: Http) {
  }
  getReports() {
    return this.http.get('assets/report.json')
      .map(res => res.json());
  }
}

This service it's created based on Angular tutorial showing how to get a external file(or link) and retriece a Json data.

This is important to collect the data from external source(if you must)

The difference between a service and a component, It's you need to to insert this service as a provider on the app.module.ts :

src/app/app.module.ts

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { AppComponent } from './app.component';
import { HttpModule, JsonpModule } from '@angular/http';
import { ReportService } from './services/report.service';
import { ChartjsComponent } from './chartjs/chartjs.component';

@NgModule({
  declarations: [
    AppComponent,
    ChartjsComponent
  ],
  imports: [
    BrowserModule,
    HttpModule,
    JsonpModule
  ],
  providers: [ReportService],
  bootstrap: [AppComponent]
})
export class AppModule { }

After that I've created the component chartjs.component.js , and used AfterViewInit instead of OnInit. I've user this approach because our service retrieve the data in a asynchronous way and, because of that, the data might be provided before the view has been initiated.

src/app/chartjs/chartjs.component.ts

import { Component, AfterViewInit,ViewChild, ElementRef } from '@angular/core';
import Chart from 'chart.js';
import { Respon2se } from '@angular/http';
import 'rxjs/add/operator/map';
import { ReportService } from '../services/report.service';


@Component({
  selector: 'app-chartjs',
  templateUrl: './chartjs.component.html',
  styleUrls: ['./chartjs.component.css']
})
export class ChartjsComponent implements AfterViewInit {

  @ViewChild('graphcanvas') mycanvas:ElementRef;
  createData;
  chartOptions;

  constructor(public reportService: ReportService) {

  }

  ngAfterViewInit() {

    this.reportService.getReports().subscribe(reportsData => {
      this.createData = {
        labels: 'Scatter Dataset',
        datasets: [{
          label: "reportRetrieve",
          data: reportsData,

        }]
      };

      this.chartOptions = {
        legend: {
          display: false,
          position: 'top',
          labels: {
            boxWidth: 80,
            fontColor: 'black'
          }
        },
        scales: {
          xAxes: [{
            gridLines: {
              display: false,
              color: "black"
            },
            scaleLabel: {
              display: true,
              labelString: "Report Size",
              fontColor: "red"
            }

          }],
          yAxes: [{
            gridLines: {
              color: "black",
              display: false
            },
            scaleLabel: {
              display: true,
              labelString: "Chart Report",
              fontColor: "green"
            }
          }]
        },
        layout: {
          padding: {
            left: 0,
            right: 50,
            top: 50,
            bottom: 0
          }
        },
        maintainAspectRatio: false
      };

      let ctx = this.mycanvas.nativeElement.getContext('2d');

      new Chart(ctx, {
        type: 'bubble',
        data: this.createData,
        options: this.chartOptions,
        responsive: false
      });

    });
  }

}

A few comments about this file;

. After imported the service, I've used subscribe,to allow charjs library to get the data and push it on new Chart . ChartOptions its just a variable to change the chart view the way you want, I've used to create a bubble chart. . You can define if it's responsive or not.

After you've done that, you'll need to set your html:

src/app/chartjs/chartjs.component.html

<div style="height: 600px;width: 600px">
  <canvas #graphcanvas></canvas>
</div>

I hope that helps someone who couldn't implement on the other ways.



回答4:

I believe, on Angular, chartjs will work like below, because context is available afterViewInit() not onInit()

  import { Component, ViewChild, ElementRef, AfterViewInit} from '@angular/core';
    import Chart from 'chart.js';

    @Component({
        selector: 'app-statistics',
        templateUrl: './statistics.component.html',
        styleUrls: ['./statistics.component.css']
    })
    export class StatisticsComponent implements AfterViewInit{
        @ViewChild('myChart') Chart: ElementRef;
        constructor() { 

        }

        ngAfterViewInit() {
            var ctx = this.Chart.nativeElement.getContext('2d')
            var myChart = new Chart(ctx,{...})
        }
    }