Introduction

Chart.js is a popular JavaScript charting library and ng2-charts is a wrapper for Angular 2+ to integrate Chart.js in Angular.
In this tutorial, you will use Chart.js and ng2-charts to create sample charts in an Angular application.

Prerequisites

To complete this tutorial, you will need:

Node.js installed locally, which you can do by following How to Install Node.js and Create a Local Development Environment.
Some familiarity with setting up an Angular project and using Angular components may be beneficial.

This tutorial was verified with Node v14.13.1, npm v6.14.8, angular v10.1.6, chart.js v2.9.4, and ng2-charts v2.4.2.

Step 1 — Setting Up the Project

You can use @angular/cli to create a new Angular Project.
In your terminal window, use the following command:

npx @angular/cli new angular-chartjs-example --style=css --routing=false --skip-tests

This will configure a new Angular project with styles set to “CSS” (as opposed to “Sass”, Less”, or “Stylus”), no routing, and skipping tests.
Navigate to the newly created project directory:

cd angular-chartjs-example

From your project folder, run the following command to install chart.js:

npm install chart.js@2.9.4 ng2-charts@2.4.2

Next, add chart.js to your Angular application by opening angular.json in your code editor and modifying it to include Chart.min.js:
angular.json

{
  // ...
  "projects": {
    "angular-chartjs-example": {
      // ...
      "architect": {
        "build": {
          // ...
          "options": {
            // ...
            "scripts": [
              "node_modules/chart.js/dist/Chart.min.js"
            ],
            "allowedCommonJsDependencies": [
              "chart.js"
            ]
          },
          // ...
        },
      }
    }},
  // ...
}

Note: Adding chart.js to allowedCommonJsDependencies will prevent the “CommonJS or AMD dependencies can cause optimization bailouts.” warning.

Then, open app.module.ts in your code editor and modify it to import ChartsModule:
src/app/app.module.ts

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { ChartsModule } from 'ng2-charts';

import { AppComponent } from './app.component';

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    ChartsModule
  ],
  providers: [],
  bootstrap: [AppComponent]
})
export class AppModule { }

With this scaffolding set in place, you can begin work on the chart component.

Step 2 — Creating the Chart Component

Let’s begin with an example that uses some of the options to pass-in as inputs to plot values associated with three different accounts over the course of four months.
ng2-charts gives you a baseChart directive that can be applied on an HTML canvas element.
Open app.component.html in a code editor and replace the content with the following lines of code:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    baseChart
  >
  </canvas>
</div>

Then, modify the canvas to pass in chartType and legend:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    ...
    [chartType]="'line'"
    [legend]="true"
  >
  </canvas>
</div>

chartType: This sets the base type of the chart. The value can be pie, doughnut, bar, line, polarArea, radar, or horizontalBar.
legend: A boolean for whether or not a legend should be displayed above the chart.

Then, modify the canvas to pass in datasets:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    ...
    [datasets]="chartData"
  >
  </canvas>
</div>

Next, open app.component.ts in a code editor to define the array you referenced in the template:
src/app/app.component.ts

// ...
export class AppComponent {
  // ...

  chartData = [
    {
      data: [330, 600, 260, 700],
      label: 'Account A'
    },
    {
      data: [120, 455, 100, 340],
      label: 'Account B'
    },
    {
      data: [45, 67, 800, 500],
      label: 'Account C'
    }
  ];
}

datasets: This should be an array of objects that contain a data array and a label for each data set.
data: Alternatively, if your chart is simple and has only one data set, you can use data instead of datasets and pass-in an array of data points.

Now, revisit app.component.html and modify the canvas to pass in labels:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    ...
    [labels]="chartLabels"
  >
  </canvas>
</div>

Next, re-open app.component.ts in a code editor to define the array you referenced in the template:
src/app/app.component.ts

// ...
export class AppComponent {
  // ...

  chartLabels = [
    'January',
    'February',
    'March',
    'April'
  ];
}

labels: An array of labels for the X-axis.

Now, revisit app.component.html and modify the canvas to pass in options:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    ...
    [options]="chartOptions"
  >
  </canvas>
</div>

Next, re-open app.component.ts in a code editor to define the object you referenced in the template:
src/app/app.component.ts

// ...
export class AppComponent {
  // ...

  chartOptions = {
    responsive: true
  };
}

options: An object that contains options for the chart. You can refer to the official Chart.js documentation for details on the available options.

Recompile your application:

npm start

When visiting your application in a web browser (typically localhost:4200), you will observe a chart with data plotted out for Account A, Account B, and Account C over the months of April, February, March, April:

There are additional properties and options that are available to Chart.js that are covered in the official documentation.

Step 3 — Handling chartClick and chartHover

Two events are emitted, chartClick and chartHover, and they provide a way to react to the user interacting with the chart. The currently active points and labels are returned as part of the emitted event’s data.
Let’s create an example of adding these to the canvas.
Open app.component.html and add chartHover and chartClick:
src/app/app.component.html

<div style="width: 40%;">
  <canvas
    ...
    (chartHover)="onChartHover(($event)"
    (chartClick)="onChartClick(($event)"
  >
  </canvas>
</div>

Open app.component.ts and add the custom functions you referenced from the template:
src/app/app.component.ts

// ...
export class AppComponent {
  // ...

  onChartHover = ($event: any) => {
    window.console.log('onChartHover', $event);
  };

  onChartClick = ($event: any) => {
    window.console.log('onChartClick', $event);
  };
}

After recompiling your application, you will observe onChartHover and onChartClick logged in your developer tools.

Step 4 — Updating Datasets Dynamically

One of the highlights of using Chart.js is the ability to dynamically update or respond to data received from a backend or from user input.
Let’s continue to build off the previous example with the 3 account values plotted across 4 months and add new data points for the month of May.
Open app.component.ts and defined the custom function:
src/app/app.component.ts

// ...
export class AppComponent {
  // ...

  newDataPoint(dataArr = [100, 100, 100], label) {
    this.chartData.forEach((dataset, index) => {
      this.chartData[index] = Object.assign({}, this.chartData[index], {
        data: [...this.chartData[index].data, dataArr[index]]
      });
    });

    this.chartLabels = [...this.chartLabels, label];
  }
}

[100, 100, 100] is provided as the default value if no array is passed to newDataPoint().
There is also no mutation being performed on the dataset array. Object.assign is used to return new objects containing the previous data with the new data.
Then, open app.component.html and use the custom function in a button after the canvas:
src/app/app.component.html

<div style="width: 40%;">
  ...

  <button (click)="newDataPoint([900, 50, 300], 'May')">
    Add data point
  </button>
</div>

After recompiling your application, you will observe that the chart will plot values for Account A, Account B, Account C for the month of May when you interact with the Add data point button.

Conclusion

In this tutorial, you used Chart.js and ng2-charts to create a sample chart in an Angular application.
Together, these libraries provide you with the power to present data in a way that is modern and dynamic.
If you’d like to learn more about Angular, check out our Angular topic page for exercises and programming projects.