最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Using data from API with Chart JS - Stack Overflow

programmeradmin2浏览0评论

I am getting data from an api and then reformatting part of it into an array using .map(), I am successfully able to do this, but when it es time to pass it into Chart JS as data it does work. I am able to pass in a normal, hard coded, array but not my own data...

I tried using an Angular directive (NG2-Charts) to help out thinking maybe that was the problem, but that doesn't work either...

Component.ts: ... Other variable and stuff up here...

getStockData() {
    this.stocksService.getStockData()
      .subscribe(
        (response) => {
          for(var i = 0; i < response.length; i++) {
            this.stockOpen.push(response[i]['open']);
          }
          console.log('after loop: ', this.stockOpen);
        },
        (error) => console.error(error)
      );
      console.log('real: ', this.stockOpen);
      console.log('test: ', this.testData);
  }

  // Chart JS version
  buildStockChart() {
    var ctx = document.querySelector("#chart");
    this.chart = new Chart(ctx, {
      type: 'bar',
      data: {
        labels: [1,2,3,4,5],
        datasets: [
          { 
            data: this.stockOpen,
            borderColor: "#3cba9f",
            fill: false
          }
        ]
      },
      options: {
        legend: {
          display: false
        },
        scales: {
          xAxes: [{
            display: true
          }],
          yAxes: [{
            display: true
          }],
        }
      }
    });
  }

  // NG2-Charts version
  public lineChartData:Array<any> = [
    {data: this.testData},
  ];
  public lineChartLabels:Array<any> = ['January', 'February', 'March', 'April', 'May', 'June', 'July'];
  public lineChartOptions:any = {
    responsive: true
  };

Result from console.log():

I am getting data from an api and then reformatting part of it into an array using .map(), I am successfully able to do this, but when it es time to pass it into Chart JS as data it does work. I am able to pass in a normal, hard coded, array but not my own data...

I tried using an Angular directive (NG2-Charts) to help out thinking maybe that was the problem, but that doesn't work either...

Component.ts: ... Other variable and stuff up here...

getStockData() {
    this.stocksService.getStockData()
      .subscribe(
        (response) => {
          for(var i = 0; i < response.length; i++) {
            this.stockOpen.push(response[i]['open']);
          }
          console.log('after loop: ', this.stockOpen);
        },
        (error) => console.error(error)
      );
      console.log('real: ', this.stockOpen);
      console.log('test: ', this.testData);
  }

  // Chart JS version
  buildStockChart() {
    var ctx = document.querySelector("#chart");
    this.chart = new Chart(ctx, {
      type: 'bar',
      data: {
        labels: [1,2,3,4,5],
        datasets: [
          { 
            data: this.stockOpen,
            borderColor: "#3cba9f",
            fill: false
          }
        ]
      },
      options: {
        legend: {
          display: false
        },
        scales: {
          xAxes: [{
            display: true
          }],
          yAxes: [{
            display: true
          }],
        }
      }
    });
  }

  // NG2-Charts version
  public lineChartData:Array<any> = [
    {data: this.testData},
  ];
  public lineChartLabels:Array<any> = ['January', 'February', 'March', 'April', 'May', 'June', 'July'];
  public lineChartOptions:any = {
    responsive: true
  };

Result from console.log():

Share Improve this question edited Jul 25, 2018 at 0:21 2pha 10.2k2 gold badges31 silver badges47 bronze badges asked Jul 24, 2018 at 22:58 GarrettGarrett 1,8086 gold badges30 silver badges59 bronze badges 3
  • Have you tried logging after the for loop (inside of the subscribe closure)? – Hodrobond Commented Jul 24, 2018 at 23:05
  • @Hodrobond I just tried it and updated the post. It is different but I'm still not totally sure what the issue is – Garrett Commented Jul 24, 2018 at 23:09
  • In the first set of console.logs, the 'real' was empty because it wasn't populated yet. Now it looks like you have populated data, and I'm not sure what else is wrong. My guess would be you're trying to use stockOpen before it gets set. When do you call buildStockChart in relation to getStockData, and can you ensure it waits to build until you've gotten your data? – Hodrobond Commented Jul 24, 2018 at 23:16
Add a ment  | 

3 Answers 3

Reset to default 3

i also have same problem with chart JS on angular so i force to use another chart. im now using angular 2 chart js.

i think the problem here is the delay of data fetch by API, the CHART ponent is already render on html view but the data is still not fetch by the API service.

try to add this code on your code block. This will handle the data if API service data is available. ()=>{this.buildStockChart();}


 this.stocksService.getStockData()
      .subscribe(
        (response) => {
          for(var i = 0; i < response.length; i++) {
            this.stockOpen.push(response[i]['open']);
          }
          console.log('after loop: ', this.stockOpen);
        },
        ()=>{
        this.buildStockChart();
        }
      );
      console.log('real: ', this.stockOpen);
      console.log('test: ', this.testData);
  }

This chart is easy to manage for dynamic instances.

Hope this chart will work on you.

https://www.npmjs./package/angular2-chartjs

When are you calling the buildStockChart() method?

You should call it right after the for loop into the callback you pass to the subscribe method, since that's the moment when this.stockOpen is populated (before that moment it will be empty as you are seeing in the console).

As @Joseph Agbing, I was unable to get it work with angular 7. I'm now using chart.js only

npm install chart.js --save

with into my someChart.ponent.html

<div style="display: block"><!--Mandatory div including chart--> <canvas id="canvas">{{chart}}</canvas> </div>

into my someChart.ponent.ts

called from my httpClient.post(...).subscribe(lData => (setChartDataFromEntities(lDataProcessed), ...)

import { Chart } from 'chart.js';

export class someClass {

/**
* 
* @param aDate 
* @param aChargeUnitArray 
*/
setChartDataFromEntities( aDate: Date, aChargeUnitArray: ChargeUnit[] ){
    console.debug('setChartDataFromEntities->', aChargeUnitArray)
    let lChartDataArray = []
    let lChartDataLineDataArray: Array<Number> = []
    let lChartLabelsArray: string[] = []
    let l_s: string
    aChargeUnitArray.forEach(element => {
        lChartDataLineDataArray.push(element.charge)
        lChartLabelsArray.push(MiscHelper.dateTimeHMSForChart(element.timestamp))
    });
    lChartDataArray.push(
        {
            data: lChartDataLineDataArray,
            label: MiscHelper.dateForGui(aDate),
        }
    )

    this.chart = new Chart('canvas', {
    type: 'line',
    data: {
        labels: lChartLabelsArray,
        datasets: lChartDataArray
    },
    options: {
        legend: {
            display: false
        },
        scales: {
        xAxes: [{
            display: true
        }],
        yAxes: [{
            display: true
        }],
        }
    }
    });    

    this.statusMessage = 'Chart loaded'
}

hope it helps somebody more than the day I wasted trying to get it work...

发布评论

评论列表(0)

  1. 暂无评论