1

I am new to angular programming so bear with me if my question is not well structured.I m trying to create a simple food ordering app, So i have a service while take mock data from a json file and it also have some methods which manipulates the data.

import { Injectable, FactoryProvider } from '@angular/core';
import { groupBy, remove, find } from "lodash";
import { foodItems } from "./food-items.constants"
import { Router } from '@angular/router';
@Injectable({
  providedIn: 'root'
})
export class DataService {
      private foodz = foodItems;
      private cart = [];
      private CartObject = {};
      private totalAmount: number = 0;
      constructor(private router: Router) {

      }
      getTotal() {
        return this.totalAmount;
      }
      getCart() {
        return this.cart;
      }

      getFoodItems() {
        let items = groupBy(this.foodz, function (food) {
          return food.cuisine;
        });
        return items;
      }
      addItemToCart(item) {
        let cartItem = find(this.cart, function (cartObject) {
          if (cartObject.itemName === item.itemName) {
            cartObject.quantity++;
            cartObject.Amount = cartObject.quantity * item.pricePerUnit;
            return true;
          }
        });
        if (cartItem) {
          this.totalAmount += Number(item.pricePerUnit);
          alert(this.totalAmount);

        }
        if (!cartItem) {
          this.cart.push({
            'itemName': item.itemName,
            'quantity': 1,
            'Amount': item.pricePerUnit
          });
          this.totalAmount += item.pricePerUnit;
          alert(this.totalAmount);

        }
        return true;
      }
      removeItemFromCart(item) {
        let cartItem = find(this.cart, (cartObject) => {

          if (cartObject.itemName === item.itemName) {
            if (cartObject.quantity == 1) {
              this.totalAmount -= item.pricePerUnit;
              alert(this.totalAmount);
              remove(this.cart, function (cObject) {
                if (cObject.itemName == item.itemName) {
                  return true;
                }
              });
            }
            else {
              cartObject.quantity--;
              cartObject.Amount = cartObject.quantity * item.pricePerUnit;
              this.totalAmount -= item.pricePerUnit;
              alert(this.totalAmount);
              return true;
            }
          }
        });
        if (!cartItem) {

        }
        return true;
      }
}

Next i have a component which has an instance of this service through DI and through users actions i am trying to add and remove foods in my cart. Issue While my cart is updating right but the total variable is not being updated on the fly as soon as i add or remove items from the cart. Here is my component.ts file contents.

      import { Component, OnInit } from '@angular/core';
  import { DataService } from '../data.service';

  @Component({
    selector: 'app-add-card',
    templateUrl: './add-card.component.html',
    styleUrls: ['./add-card.component.css']
  })
  export class AddCardComponent implements OnInit {
    private cart = [];
    private total: number;

    constructor(private foodService: DataService) {

    }

    ngOnInit() {
      this.cart = this.foodService.getCart();
      this.total = this.foodService.getTotal();

    }
  }

and here is my view component.html file to display cart summary.

<div class="menu text-center" > <br>
 <h1><span>{{ total | currency: "INR" }}</span></h1 > <br>
</div>
< br >

<div class="menu" style = "margin-bottom: 30px" >
  <div class="heading text-center" >
    <span>Order Details < /span>
  </div>


  < div class="item" * ngFor="let item of cart" >
        <span style="width:50%;display:inline-block" > {{ item.itemName }}</span>
        <span style = "width:20%;display:inline-block" > Qua.{ { item.quantity } } </span>
         <span > {{ item.Amount | currency: "INR" }} { { cart.total } } </span>
    </div>
</div>
3

1 Answer 1

3

It will not update because you are not listening to the changes done in the total value in the service.

Add a Subject for the total value in your service, components can subscribe to the changes in the subject and accordingly update their variables.

In your service, have something like:

public totalObs = new Subject()

Wherever you update your total in the service do this:

this.totalObs.next(this.total)

In your component have something like:

totalSub: Subscription
ngOnInit() {
   this.cart = this.foodService.getCart();
   this.totalSub = this.foodService.totalObs.subscribe((total) => {this.total = total}); 
}

ngOnDestroy() {
    if (this.totalSub) {
        this.totalSub.unsubscribe()
    }
}
Sign up to request clarification or add additional context in comments.

6 Comments

Thank you for your solution, i will try this and get back to you. just a supplementary question: how is my cart updating then on the fly as soon as i add or remove items from the cart. i haven't written anything for that but it seems to update without me writing anything.
@GaganDeep Please show the component code you have written for updating the cart, (both HTMl and ts)
that component simply just calls the service method like this.foodService.addItemToCart(item); thats it. i send the item to it from the html. and it adds it to cart and my view is updated instantaneously.
@GaganDeep cart is an Array, its reference is shared between the component and the service Whenever you do things on the browsers (clicks for add/remove), a change detection will run and will check for existing data. Same should happen for total but total is a primitive type, its reference is not shared between the component and the service so the changes done in the service will not affect the changes in the component.
ok. Thank you @xyz i will try this when i have my laptop with me and get back to you on this. Thank you for your efforts.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.