无法删除数组项目,总是错误的项目被删除。

4

我有一个ingredientsArray数组,它是通过在按下按钮后从下拉菜单中添加项目构建的。然后,当我尝试通过按下项目来使用deleteIngredient从该数组中删除项目时,它会以奇怪的方式行为,并且索引始终返回-1。

import React from 'react';
import { Link } from 'react-router';

export default class Order extends React.Component {

constructor() {
    super()
    this.state = {
      selectedCircle:{},
      cheeseAdd: false,
      ingredient:'',
      ingredientsArray: []
    };
  }

  onSelectIngredient(e){

    this.setState({
      ingredient: e.target.value
    })
  }

addIngredient(){

    this.state.ingredientsArray.push(this.state.ingredient+" ");
    this.forceUpdate();
  }

  deleteIngredient(e) {

  var array = this.state.ingredientsArray;
  var index = array.indexOf(e.target.value);
  console.log(e.target.value);
  array.splice(index, 1);
  this.setState({ingredientsArray: array });
}

  onAddCheese(){

    let add = !this.state.cheeseAdd;
    this.setState({cheeseAdd : add});
  }

  saveAndContinue(e){
    e.preventDefault();
    var pizzaObject = JSON.stringify(this.state.selectedCircle);
    var pizza = pizzaObject.substring(2,4);
    if(this.state.cheeseAdd == true)
    {
        var cheeseChoice = "Yes";
    }
    else{
        var cheeseChoice = "No"
    }
    var data = {
       pizzaSize   : pizza,
       cheese      : cheeseChoice,
       ingredients : [this.state.ingredientsArray]
    }

    this.props.saveValues(data);
    this.props.changeArrowBlack_1();
    this.props.nextCase();
  }

 toggleChoice(name, event) {
     let selected = this.state.selectedCircle;
     selected = {};
     selected[name] = this.state.selectedCircle[name] == "active-circle" ?        "" : "active-circle";
     this.setState({selectedCircle: selected});
  }



  render() {
    const { selected } = this.state;
    const selectedCircle = selected ? "active-circle":"";
    return (
        <div class="container card-layout" id="order-layout">
            <div class="row">

                    <div class="card-panel white">
                      <div class="center">
                        <h5 class="bold">Your Order</h5>
                        <p class="margin-top-30 bold">Choose Pizza size in cm</p>
                        <ul class="margin-top-30">
                            <li ><div onClick={this.toggleChoice.bind(this, "20")} class={"circle-20 hovered-circle " + this.state.selectedCircle["20"]}>20</div></li>
                            <li ><div onClick={this.toggleChoice.bind(this, "30")} class={"circle-30 hovered-circle " + this.state.selectedCircle["30"]}>30</div></li>
                            <li ><div onClick={this.toggleChoice.bind(this, "40")} class={"circle-40 hovered-circle " + this.state.selectedCircle["40"]}>40</div></li>
                          </ul> 
                           <p class="bold margin-top-20">Ingredients:</p>
                        <div class="row">
                            <select class="browser-default col s5 offset-s3" defaultValue="0" onChange={this.onSelectIngredient.bind(this)}>
                              <option value="0" disabled>Choose Ingredients</option>
                              <option value="Tomato sauce">Tomato sauce</option>
                              <option value="Mozarella">Mozarella</option>
                              <option value="Mushrooms">Mushrooms</option>
                      <option value="Cheese">Cheese</option>
                      <option value="Salami">Salami</option>
                            </select>
                            <i onClick={this.addIngredient.bind(this)} class="material-icons medium col s1 add-ingredient">add_box</i>
                          </div>
                  <div class="row ingredients-row">
                    {this.state.ingredientsArray.map((item, index) => <span class="col s3" key={index} >{item}<img src="/img/icons/cancel_small.png" onClick={this.deleteIngredient.bind(this)} /></span> )}
                  </div>  
                            <p class="bold margin-top-30">Cheese rand ?</p>
                            <div class="switch margin-top-20">
                                <label>no
                                <input ref="cheeseRand" type="checkbox" checked={this.state.cheeseAdd} onChange={this.onAddCheese.bind(this)}  />
                                <span class="lever"></span>
                                yes</label>
                            </div>
                            <div class="divider margin-top-30"></div>
                            <button onClick={this.saveAndContinue.bind(this)} class="waves-effect waves-light btn red-button margin-top-20"><i class="material-icons right">arrow_forward</i>Next</button>
                     </div>
                   </div>
            </div>
        </div>
    );
  }
}

你能展示一个数组的样例吗? - Rajesh
@Rajesh 一个示例数组可能是ingredientsArray["蘑菇", "番茄", "奶酪"],我从下拉列表中获取值,如代码所示,并将它们推送到数组中,每个数组项都作为span填充到dom中,我在该span上有一个onclick函数,应该删除该数组项,但它没有正常工作。 - user3209048
你尝试过使用.trim()吗?e.target.value.trim() - Rajesh
@Rajesh 是的,如果你使用 trim,那么它会完全停止工作,不使用 trim 它会删除,但是删除错误的项,并且索引始终返回 -1。 - user3209048
请提供 [mcve]。 - user663031
1个回答

3

你没有将项目的索引传递给deleteIngredient()。在你的map方法中,你可以这样操作:

onClick={this.deleteIngredient.bind(this, index)}

然后在deleteIngredient()函数中:

你可以这样访问它:

deleteIngredient(index) {
   console.log(index)
   ...
 }

此外,您正在错误地更新状态,以下是一个快速修复方法:

  deleteIngredient(index) {
    console.log(index);
    var array = this.state.ingredientsArray.slice();
    array.splice(index, 1);
    this.setState({ingredientsArray: array });
  }

或者,使用过滤器方法:
  deleteIngredient(index) {
    this.setState({
      ingredientsArray: this.state.ingredientsArray.filter((item, i) => i !== index)
    });
  }

或者,使用ES6扩展运算符:

 deleteIngredient(index) {
    this.setState({
      ingredientsArray: [
        ...this.state.ingredientsArray.slice(0, index),
        ...this.state.ingredientsArray.slice(index + 1)
      ]
    });
  }

这里有一个演示样例:http://codepen.io/PiotrBerebecki/pen/bwLyOJ

1
非常感谢,工作完美无缺。我仍然是JavaScript和React的新手,感谢您的分享,让我变得更好! - user3209048
1
很高兴能够帮助,我还添加了使用扩展运算符从数组中删除项的方法。 - Piotr Berebecki
在JSX中,您不应该使用.bind语法,而是创建一个组件,在其中传递deleteIngredient回调和索引,然后从该组件内部调用它。 - kudlajz
很好的提示@kudlajz。这里有一个我们可以实现它的例子:https://dev59.com/QF0a5IYBdhLWcg3w6sVk#38908620 - Piotr Berebecki

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接