1

I am not sure weather the title of the question is right or not. I run into some problem and i have no idea how to solve them.

In my app there is cart page there is list of items. And each item has a field quantity.which can be updated. My problem Here is when i initiate i state quantity and make two function out of it which increase and decrease the quantity.but the problem is when i click on addQuantity it updates all the products quantity at the same time. I have really no idea to solve this i have been trying to figure out from last couple of days . These are the two items.

Item Image

These are my codes

class CartContainer extends React.Component { state = { quantity: 1, };

componentDidMount() { this.props.getItemsAddedToCart(); }

render() {

const addItem = () => {
  this.setState({
    quantity: this.state.quantity + 1,
  });
};

const removeItem = () => {
  this.setState({
    quantity: this.state.quantity - 1,
  });
};

Cart.js

return cartData.map((item, index) => { return (

      <Grid item xs={4} container justify="space-around">
        <CartItemDetails
          quantity={quantity}
          addItem={addItem}
          removeItem={removeItem}
          addQty={addQuantity}
          subQty={subtractQuantity}
          cart={item}
        />
      </Grid>
    </Grid>
  </Grid>
);

CartItemDetail.js

return (
  <Grid container className="cart-item-details">

    <Grid xs={12} md={4}>
      {!this.props.team ? (
        <Grid className="counter" xs={12} container>
          <Grid container justify="center" alignItems="center" xs={4}>
            <button
              onClick={this.props.removeItem}
              className="decrement"
            ></button>
          </Grid>
          <Grid container justify="center" alignItems="center" xs={4}>
            <span>{this.props.quantity}</span>
          </Grid>
          <Grid container justify="center" alignItems="center" xs={4}>

            <button
              onClick={this.props.addItem}
              className="increment"
            ></button>
          </Grid>
        </Grid>
      ) : (
        ""
      )}

Any help would be great I really want to figure this out .

4
  • Can you create a CodeSandbox that allows us to use a working example? Commented Jun 4, 2020 at 8:14
  • yeah give me a minute i will try to. Commented Jun 4, 2020 at 8:15
  • @Titulum It's big app i won't be able to add this to sandbox Commented Jun 4, 2020 at 8:24
  • You should not add your complete app to CodeSandbox, only a small working example that allows us to reproduce your issue. Commented Jun 4, 2020 at 8:33

2 Answers 2

3

Declare your state like the below

state={
quantity:{}
}

use product id or something unique to make the key of quantity

const addItem = (id) => {
  this.setState({
    quantity: {
     ...this.state.quantity,
     [id]:this.state.quantity[id]+1
     }
  });
};

const removeItem = (id) => {
  this.setState({
    quantity: {
     ...this.state.quantity,
     [id]:this.state.quantity[id]-1
     }
  });
};
      <Grid item xs={4} container justify="space-around">
        <CartItemDetails
          quantity={this.state.quantity[id]||0}
          addItem={addItem}
          removeItem={removeItem}
          addQty={addQuantity}
          subQty={subtractQuantity}
          cart={item}
        />
      </Grid>
    </Grid>
  </Grid>
);
Sign up to request clarification or add additional context in comments.

Comments

1

You're only keeping one value for the quantity in your state, so all of your cart items rendered by Cart.js use the same value.

You'll need to track a quantity for each item in your cart, here's an example of the state set for each item:

this.state = {
      items: [
        {
          id: 1,
          name: "Jeans",
          quantity: 1
        },
        {
          id: 2,
          name: "Jacket",
          quantity: 2
        }
      ]
    };

and the functions to increase and decrease an item

increaseItemQuantity(id) {
    return () => {
      const itemIndex = this.state.items.findIndex(item => item.id === id);
      const nextItems = Array.from(this.state.items);
      console.log(itemIndex);
      nextItems[itemIndex].quantity = nextItems[itemIndex].quantity + 1;
      this.setState([...nextItems]);
    };
  }

  decreaseItemQuantity(id) {
    return () => {
      const itemIndex = this.state.items.findIndex(item => item.id === id);
      const nextItems = Array.from(this.state.items);
      console.log(itemIndex);
      nextItems[itemIndex].quantity = Math.max(
        1,
        nextItems[itemIndex].quantity - 1
      );
      this.setState([...nextItems]);
    };
  }

(this can be made much cleaner, but I'm leaving it as it is for the purposes of demonstration)

and then in the render:

render() {
    return (
      <div className="App">
        <div>
          {this.state.items.map((item, index) => (
            <div key={item.id}>
              {item.name} x{item.quantity}
              <br />
              <button
                type="button"
                onClick={this.decreaseItemQuantity(item.id)}
              >
                Decrease
              </button>
              <button
                type="button"
                onClick={this.increaseItemQuantity(item.id)}
              >
                Increase
              </button>
              <br />
              <br />
            </div>
          ))}
        </div>
      </div>
    );
  }

Try it here: https://codesandbox.io/s/solitary-dawn-8gpjl?file=/src/App.js

1 Comment

how will i do this with redux state ?

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.