使用ReactJS显示新的列表项onclick

时间:2018-12-19 06:57:37

标签: javascript arrays reactjs events state

单击按钮,将数组更新并显示为列表项时出现问题。从下面的代码中,我收到错误消息:

  

list.map不是函数

import React from "react";


export default class InputPushToList extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      ActiveText: "",
      li: ["First Item"]
    };

    this.handleOnClick = this.handleOnClick.bind(this);
    this.handleChange = this.handleChange.bind(this);
  }

  handleChange(e) {
    this.setState({
      ActiveText: e.target.value
    });
  }

  handleOnClick(e) {
    e.preventDefault();

    const newListItem = [this.state.ActiveText];

    this.setState({
      li: this.state.li.push(newListItem)
    });
  }

  render() {
    const list = this.state.li;
    return (
      <React.Fragment>
        <h2>{this.props.inputTitle}</h2>
        <input type="text" onChange={this.handleChange} />
        <h2>{this.state.ActiveText}</h2>
        <br />
        <button onClick={this.handleOnClick}>Add to list</button>

        <ul>
          {list.map(e => (
            <li>{e}</li>
          ))}
        </ul>
      </React.Fragment>
    );
  }
}

在我看来list.map是一个函数,但显然不是,所以为什么呢?当单击按钮时,如何显示一个列表项(输入的活动状态this.state.ActiveText)?感谢您的帮助。

3 个答案:

答案 0 :(得分:1)

首先,您不要在this.setState中使用this.state,而应使用函数来更新状态。检查以供参考:https://reactjs.org/docs/state-and-lifecycle.html#state-updates-may-be-asynchronous

您的代码应如下:

this.setState((state) => ({
  li: state.li.concat([newListItem])
}));

第二,为什么要通过执行const newListItem = [this.state.ActiveText];将数组分配给newlistitem?

应为const newListItem = this.state.ActiveText;

答案 1 :(得分:1)

问题是这一行:

this.setState({
      li: this.state.li.push(newListItem)
    });

示例:

var arr = [];
console.log(arr.push({}))// it will print 1.

在您的情况下:

this.setState({
      li: this.state.li.push(newListItem)// here you assigned `li`1.
    });

修复以上问题。

答案 2 :(得分:1)

1。不要变异this.state

handleOnClick()中,不要写this.state.li.push(newListItem)

相反,制作一个this.state.li的克隆,将newListItem添加到该克隆中,并将li的状态设置为新的克隆:

handleOnClick(e) {
  e.preventDefault();
  this.setState({
    li: [
      ...this.state.li, // spread out the existing li
      this.state.ActiveText // append this newListItem at the end of this array
    ]
  });
}

2。考虑销毁

在您的render()中,您可以解构 this.state.li

render() {
  const { li } = this.state
  return (
    <React.Fragment>
      ...other stuffs
      <ul>
        {li.map(e => (
          <li>{e}</li>
        ))}
      </ul>
    </React.Fragment>
  );
}