Refresh a doughnut chart in real-time using NG2Charts

Currently, I am in the process of developing a macronutrient calculator as part of a project. The idea is to have a form where users can input values, and a corresponding doughnut chart will display with initial values set at 0. However, upon clicking the submit button, the chart fails to update.

Below is the code snippet:

home.component.html

<form (submit)="addMeal(totalGrams, proteinGrams, fatGrams, carbGrams)">
              <div class="form-group">
                <input
                  class="form-control"
                  type="number"
                  placeholder="Total"
                  #totalGrams
                />
              </div>
              <div class="form-group">
                <input
                  class="form-control"
                  type="number"
                  placeholder="Protein"
                  #proteinGrams
                />
              </div>
              <div class="form-group">
                <input
                  class="form-control"
                  type="number"
                  placeholder="Fat"
                  #fatGrams
                />
              </div>
              <div class="form-group">
                <input
                  class="form-control"
                  type="number"
                  placeholder="Carbs"
                  #carbGrams
                />
              </div>

              <button type="submit" class="btn btn-primary btn-block">
                Submit
              </button>
            </form>

The provided code snippet focuses on the form structure only, excluding irrelevant layout details and Bootstrap components.

home.component.ts

import { Component, ViewChild } from '@angular/core';
import { ChartData, ChartType } from 'chart.js';

@Component({
  selector: 'app-home',
  templateUrl: './home.component.html',
  styleUrls: ['./home.component.css']
})
export class HomeComponent {

  gProtein: number = 0;
  gCarbs: number = 0;
  gFat: number = 0;

  public doughnutChartLabels: string[] = [ 'Protein', 'Carbohydrates', 'Fat' ];
  public doughnutChartData: ChartData<'doughnut'> = {
    labels: this.doughnutChartLabels,
    datasets: [
      { data: [ this.gProtein, this.gCarbs, this.gFat ] },
    ]
  };
  public doughnutChartType: ChartType = 'doughnut';

  addMeal(totalGrams: HTMLInputElement, proteinGrams: HTMLInputElement, fatGrams: HTMLInputElement, carbGrams: HTMLInputElement) {
    this.doughnutChartData.datasets[0].data[0] = parseInt(proteinGrams.value);
    this.doughnutChartData.datasets[0].data[1] = parseInt(carbGrams.value);
    this.doughnutChartData.datasets[0].data[2] = parseInt(fatGrams.value);
    totalGrams.value = ''
    proteinGrams.value = ''
    fatGrams.value = ''
    carbGrams.value = ''
    totalGrams.focus()    
    return false;
  }

}

Although unsure of the last update for this library, following the documentation guide is important for updating the chart effectively, especially if certain sections lack clarity.

Answer №1

I encountered a similar situation where the documentation was well-written but didn't cover every possible scenario for each chart type. To address this, I had to reference another chart for guidance. Specifically, I solved the issue by consulting a bar chart and making the following adjustments.

In your .ts component, add the following imports:

import { BaseChartDirective } from 'ng2-charts';

Next, include the following code snippet:

@ViewChild(BaseChartDirective) chart?: BaseChartDirective;

Finally, modify your addMeal() method as shown below to incorporate the necessary changes:

addMeal(
    totalGrams: HTMLInputElement,
    totalCals: HTMLInputElement,
    proteinGrams: HTMLInputElement,
    fatGrams: HTMLInputElement,
    carbGrams: HTMLInputElement
  ) {
    // Updated calculations here...
    
    this.chart?.chart?.update();
    // Reset input fields and return
    
    return false;
  }

By adding just one line of code before clearing the form fields, you can invoke the update() method to ensure the chart reflects the latest data.

I recommend thoroughly reviewing the complete documentation or relevant sections pertaining to your task before seeking assistance, as detailed explanations like the one provided here can be incredibly helpful.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Using Typescript to establish a connection between ngModel and an object's property

Let's talk about how we can dynamically bind an input to an undefined property in an object. For example, we have an object named user: let user = {}; How can we bind an input to a property that doesn't exist yet? Like this: <input [(ngMode ...

Angular offers a range of search filters for optimizing search results

The system currently has 3 search fields: 1. Name.... 2. Subject.... 3.Price.... Each of these filters works independently - when searching by name, only results matching that name are displayed; similarly for subject and price. However, the challeng ...

Retrieving component attributes using jQuery or alternate event handlers

In my Angular2 component, I am facing an issue with using vis.js (or jQuery) click events. Despite successfully displaying my graph and catching click events, I encounter a problem where I lose access to my component's properties within the context of ...

What is the best way to include a non-data custom attribute in a TSX template without any value?

Currently, I am working on a React component with Typescript. The initial code looks like this.... const NameFormatter = React.createClass({ render() { return ( <div> <div className="dataset-name"> ...

Creating an interceptor to customize default repository methods in loopback4

Whenever I attempt to access the default repository code, I need to manipulate certain values before triggering the default crud function in the repository. How can I accomplish this? For example: ... @repository.getter('PersonRepository') priva ...

Issues arising from TypeScript error regarding the absence of a property on an object

Having a STEPS_CONFIG object that contains various steps with different properties, including defaultValues, I encountered an issue while trying to access the defaultValues property from the currentStep object in TypeScript. The error message indicated tha ...

What prevents me from employing my nestjs unique decorator within a constructor?

I am looking to develop a personalized decorator that fetches tenant information. This is the current code snippet I have: export type TenantInfo = { token: string id: string } export const TenantInfo = createParamDecorator( (data: unknown, cont ...

Adding optional properties to TypeScript interfaces

As discussed in this post, the optional ? operator is commonly used to indicate that a function parameter can be omitted. But what is the significance of the ? operator when it appears on interface parameters? For instance, consider the following TypeScrip ...

What are the recommended methods for ensuring compatibility of enums in Typescript?

I have a const enum named ComponentId with values A, B, and C. Additionally, there is another const enum called BaseId with values D, E, and F which is used in multiple places. const enum ComponentId { A = 0, B, C } The challenge I am facing ...

The functionality of expandable rows on the material table seems to be malfunctioning once sorting is

After implementing expandable rows and sorting in my table based on the samples provided in Angular Material Table, I encountered an issue. When I try to expand a row after sorting the table, the first click appears to have no effect. The second click brie ...

What is the best way to refresh existing data retrieved by React Query without having to fetch everything again?

My current code structure requires me to refetch all the data after a successful mutation, as the client-side tasks are not updated automatically. Is there a way to update the tasks directly when I create or delete a task? const { data: sessionData } = ...

The navigator.geolocation.watchPosition call did not return any available position information

I offer a service that monitors the position of devices: getLocation(opts): Observable<any> { return Observable.create(observer => { if (window.navigator && window.navigator.geolocation) { window.navigator.geolocat ...

The 'ref' attribute is not found within the 'IntrinsicAttributes' type

I'm currently working on a TypeScript project using React. Although the code is functional, I keep encountering compiler errors with my ref. Here's an example of the code: Firstly, there's a higher-order component that handles errors: expor ...

Why isn't the page showing up on my nextjs site?

I've encountered an issue while developing a web app using nextjs. The sign_up component in the pages directory is not rendering and shows up as a blank page. After investigating with Chrome extension, I found this warning message: Unhandled Runtime ...

Creating a list in an Angular class: A step-by-step guide

In my Angular class, I have set up the username and password fields. Now, I want to include a list of roles as well. How can I go about adding this list of roles? export class User { userid: number; username: string; password: string; ro ...

An issue occurred while loading: Uncaught ReferenceError: module is missing from the http://localhost:9876/_karma_webpack_/scripts.js file on line 1

Error image I encountered an error while performing jasmine karma unit testing with angular. Can anyone provide assistance on this issue? Here is my karma.conf.js file: // Karma configuration file, see link for more information //<br> https://karma ...

What is the proper way to conduct unit testing on a function that is invoked in a service's constructor

Is there a way to verify, within the service's spec file, that a function is invoked in the constructor? Consider the following example: @Injectable({ providedIn: 'root' }) export class myService { constructor() { this.myF ...

The dynamic duo: Formik meets Material-UI

Trying to implement Formik with Material-UI text field in the following code: import TextField from '@material-ui/core/TextField'; import { Field, FieldProps, Form, Formik, FormikErrors, FormikProps } from 'formik'; import ...

How can we dynamically update property values in a ngFor loop by utilizing the click method?

Here is a TypeScript file I am working with: <md-card style="display: inline-block;" *ngFor="let people of peoples"> <p> {{people.name}} </p> <p *ngIf="people.showAge"> {{people.age}} </p> < ...

Declaring variables or fields with specific type restrictions

Imagine we have a generic interface: export interface IKeyValue<K, V> { key: K; value: V; } Now, our goal is to define a variable or field and restrict the types that can be used as K and V: public items: IKeyValue<K extends Type1, V ex ...