React不会渲染数组的所有组件

时间:2018-11-03 14:54:47

标签: javascript reactjs

在单击“添加”按钮后,我想动态添加组件。 为此,我创建了一个包含所有组件的数组,然后单击添加它们。

我的问题是,即使它包含多个组件,它也只能呈现一个组件。

我的代码如下:

class QuestionBlock extends React.Component {
    constructor(props) {
        super(props);
        this.state = {answersArray: []};
    }

    addPossibleAnswer() {
        this.state.answersArray.push(
            <PossibleAnswers id={this.state.answersArray.length + 1}/>
        )
        this.forceUpdate();
    }

    componentWillMount() {
        this.state.answersArray.push(
            <PossibleAnswers id={this.state.answersArray.length + 1}/>
        )
    }

    render() {
        console.log(this.state.answersArray) // Grows after adding componenets, but they are not rendered.
        return (
            <div>
                {this.state.answersArray}
                <AddPossibleAnswer addPossibleAnswer={() => this.addPossibleAnswer()} />
            </div>
        );
    }
}

如果您看到我做错了,如果您能帮助我,我将非常高兴!

3 个答案:

答案 0 :(得分:1)

您不会像以前那样与state进行交互。切勿更改状态字段。您需要使用this.setState

this.setState(prevState => ({answersArray: prevState.answersArray.concat([
      <PossibleAnswers id={prevState.answersArray.length + 1}])}));

话虽如此,但您将组件存储在状态中也很奇怪。通常,您将存储数据并根据render方法中的数据创建组件。

答案 1 :(得分:1)

您可以直接在状态中保留原始数据,然后从render方法中派生JSX,而不是直接更改状态并向其中添加JSX。

示例

class QuestionBlock extends React.Component {
  state = { answers: 1 };

  addPossibleAnswer = () => {
    this.setState(({ answers }) => ({ answers: answers + 1 }));
  };

  render() {
    return (
      <div>
        {Array.from({ length: this.state.answers }, (_, index) => (
          <PossibleAnswers key={index} id={index} />
        ))}
        <AddPossibleAnswer addPossibleAnswer={this.addPossibleAnswer} />
      </div>
    );
  }
}

答案 2 :(得分:1)

您直接将元素推送到不带setState的数组中,因此组件不会重新呈现

还应避免在应用程序中尽可能多地使用tthis.forceUpdate(),因为不建议这样做

您需要像下面那样更改代码。在react中处理数组的推荐方法是使用先前状态并推送到数组

addPossibleAnswer() {
       this.setState(prevState => ({
          answersArray: [...prevState.answersArray, <PossibleAnswers id={prevState.answersArray.length + 1}/>]
       }));
    }

componentWillMount() {
    this.setState(prevState => ({
          answersArray: [...prevState.answersArray, <PossibleAnswers id={prevState.answersArray.length + 1}/>]
       }));
}

还要记住,react 16中不建议使用componentWillMount生命周期方法。因此,请将代码移至componentDidMount

这是更正的代码

class QuestionBlock extends React.Component {
    constructor(props) {
        super(props);
        this.state = {answersArray: []};
    }

    addPossibleAnswer() {
       this.setState(prevState => ({
          answersArray: [...prevState.answersArray, <PossibleAnswers id={prevState.answersArray.length + 1}/>]
       }));
    }

  componentDidMount() {
    this.setState(prevState => ({
          answersArray: [...prevState.answersArray, <PossibleAnswers id={prevState.answersArray.length + 1}/>]
       }));
  }

    render() {
        const { answersArray } = this.state;
        return (
            <div>
                {answersArray}
                <AddPossibleAnswer addPossibleAnswer={() => this.addPossibleAnswer()} />
            </div>
        );
    }
}