Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/393.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 对要从状态数组中删除的其他组件作出反应_Javascript_Reactjs_State - Fatal编程技术网

Javascript 对要从状态数组中删除的其他组件作出反应

Javascript 对要从状态数组中删除的其他组件作出反应,javascript,reactjs,state,Javascript,Reactjs,State,我正在开发一个todo应用程序,以了解react的威力。我创建了3个组件,我将在下面向您展示。因此,我想从位于其他组件中的数组状态中删除todo 看看下面我的组件 这是我的TodoAppComponent: import AddTodoComponent from '../AddTodoComponent/AddTodoComponent'; class TodoAppComponent extends Component { render() { return (

我正在开发一个todo应用程序,以了解react的威力。我创建了3个组件,我将在下面向您展示。因此,我想从位于其他组件中的数组状态中删除todo

看看下面我的组件

这是我的TodoAppComponent:

import AddTodoComponent from '../AddTodoComponent/AddTodoComponent';

class TodoAppComponent extends Component {
  render() {
    return (
        <div id="page-content-wrapper">
            <div className="container">
                <div className="row">
                    <div className="col-lg-6 col-lg-offset-3">
                        <h1 className="m-b-md">What needs to be done?</h1>

                        <AddTodoComponent></AddTodoComponent>
                    </div>                         
                </div>
            </div>
        </div>
    );
  }
}

export default TodoAppComponent;
class TodoItemComponent extends Component {
  deleteTodo(todo){
      console.log('deleteTodo', todo);
      this.props.onDelete(this.props.todo);
  }



  render() {
      console.log('this.props.todo', this.props.todo);

return (
    <div>            
        <li className="list-group-item todo-item">
            <button className="btn btn-xs btn-react btn-circle m-r-md">
                <span className="fa fa-check"></span>
            </button>
            {this.props.todo}
            <span className="pull-right">
                <button className="btn btn-xs btn-react btn-circle m-r-xs">
                    <span className="fa fa-pencil-square-o"></span>
                </button>

                <button className="btn btn-xs btn-react btn-circle" onClick={this.deleteTodo.bind(this.props.todo)}>
                    <span className="fa fa-trash-o"></span>
                </button>
            </span>
        </li>
    </div>
);
import TodoItemComponent from '../TodoItemComponent/TodoItemComponent';

class AddTodoComponent extends Component {
    constructor(props) {
        super(props);

        this.state = {
            todo: '',
            todoArray: []
        };
    }

    addTodo(e){
        this.setState({ todo: e.target.value });
        this.state.todoArray.push(<TodoItemComponent todo={this.state.todo} onDelete={this.delete}></TodoItemComponent>);
    }

    delete(index){
    //     this.setState({
    //         todoArray: update(this.state.todoArray, {$splice: [[index, 1]]})
    //     });

        console.log('testDelete', this.state.todoArray);
    }

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

    render() {
        return (            
            <div>
                <div className="input-group m-b-md">
                    <input type="text" className="form-control add-todo" placeholder="Todo..." value={this.state.todo} onChange={this.handleChange.bind(this)} />
                    <span className="input-group-btn">
                        <button className="btn btn-react" type="button" onClick={this.addTodo.bind(this)}>Add</button>
                    </span>
                </div>
                <ul className="list-group">
                    {this.state.todoArray}
                </ul>
            </div>
        );
    }
}

export default AddTodoComponent;
以下是AddTodoComponent:

import AddTodoComponent from '../AddTodoComponent/AddTodoComponent';

class TodoAppComponent extends Component {
  render() {
    return (
        <div id="page-content-wrapper">
            <div className="container">
                <div className="row">
                    <div className="col-lg-6 col-lg-offset-3">
                        <h1 className="m-b-md">What needs to be done?</h1>

                        <AddTodoComponent></AddTodoComponent>
                    </div>                         
                </div>
            </div>
        </div>
    );
  }
}

export default TodoAppComponent;
class TodoItemComponent extends Component {
  deleteTodo(todo){
      console.log('deleteTodo', todo);
      this.props.onDelete(this.props.todo);
  }



  render() {
      console.log('this.props.todo', this.props.todo);

return (
    <div>            
        <li className="list-group-item todo-item">
            <button className="btn btn-xs btn-react btn-circle m-r-md">
                <span className="fa fa-check"></span>
            </button>
            {this.props.todo}
            <span className="pull-right">
                <button className="btn btn-xs btn-react btn-circle m-r-xs">
                    <span className="fa fa-pencil-square-o"></span>
                </button>

                <button className="btn btn-xs btn-react btn-circle" onClick={this.deleteTodo.bind(this.props.todo)}>
                    <span className="fa fa-trash-o"></span>
                </button>
            </span>
        </li>
    </div>
);
import TodoItemComponent from '../TodoItemComponent/TodoItemComponent';

class AddTodoComponent extends Component {
    constructor(props) {
        super(props);

        this.state = {
            todo: '',
            todoArray: []
        };
    }

    addTodo(e){
        this.setState({ todo: e.target.value });
        this.state.todoArray.push(<TodoItemComponent todo={this.state.todo} onDelete={this.delete}></TodoItemComponent>);
    }

    delete(index){
    //     this.setState({
    //         todoArray: update(this.state.todoArray, {$splice: [[index, 1]]})
    //     });

        console.log('testDelete', this.state.todoArray);
    }

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

    render() {
        return (            
            <div>
                <div className="input-group m-b-md">
                    <input type="text" className="form-control add-todo" placeholder="Todo..." value={this.state.todo} onChange={this.handleChange.bind(this)} />
                    <span className="input-group-btn">
                        <button className="btn btn-react" type="button" onClick={this.addTodo.bind(this)}>Add</button>
                    </span>
                </div>
                <ul className="list-group">
                    {this.state.todoArray}
                </ul>
            </div>
        );
    }
}

export default AddTodoComponent;
所以函数是这样的:

deleteTodo(todo){
      console.log('deleteTodo', todo);
      this.props.onDelete(this.props.todo);
  }

有人能帮我解决这个问题吗?

你的问题是滥用了here:

第一个参数应该是绑定函数的上下文,即
this
,而不是todo

onClick={this.deleteTodo.bind(this)}
您应该在
deleteTodo
函数中使用
this.props.todo
(该函数现在具有适当的上下文)

或者,您可以(维护其外部上下文)传递
todo

onClick={() => this.deleteTodo(this.props.todo)}

并且您的
deleteTodo
方法将接收
todo
作为其第一个参数。

将数据存储在
中。状态
,并且仅在
渲染
中创建React元素,如下所示:

class AddTodoComponent extends Component {
    constructor(props) {
        super(props);

        this.state = {
            todo: '',
            todoArray: []
        };
    }

    addTodo(e){
        this.state.todoArray.push(e.target.value);
        this.setState({ todo: '' });
    }

    delete(index){
        console.log('testDelete', this.state.todoArray);
    }

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

    render() {
        return (            
            <div>
                <div className="input-group m-b-md">
                    <input type="text" className="form-control add-todo" placeholder="Todo..." value={this.state.todo} onChange={this.handleChange.bind(this)} />
                    <span className="input-group-btn">
                        <button className="btn btn-react" type="button" onClick={this.addTodo.bind(this)}>Add</button>
                    </span>
                </div>
                <ul className="list-group">
                    {this.state.todoArray.map((todo, index) => (
                      <TodoItemComponent todo={todo} onDelete={this.delete.bind(this, index)}></TodoItemComponent>
                    ))}
                </ul>
            </div>
        );
    }
}
类AddTodoComponent扩展组件{
建造师(道具){
超级(道具);
此.state={
待办事项:'',
todoArray:[]
};
}
addTodo(e){
this.state.todoArray.push(e.target.value);
this.setState({todo:''});
}
删除(索引){
log('testDelete',this.state.todoArray);
}
手变(e){
this.setState({todo:e.target.value});
}
render(){
报税表(
添加
    {this.state.todoArray.map((todo,index)=>( ))}
); } }
您是否尝试过
onDelete={()=>this.delete(1)}
或其他索引?您无法在
delete
方法中访问
this.props.todo
的值。因此,您必须像这样为它提供一个上下文
onClick={this.delete.bind(this,this.props.todo)}
。通过此操作,您可以访问
delete
自定义方法中的todo项。您不应该将呈现的组件存储在状态中。在状态中存储普通的旧JavaScript对象和数组,并且仅在
render
中呈现React组件。
addTodo
方法将导致渲染组件被推入在
render
生命周期之外更新的数组时出现问题。@RossAllen谢谢,您是怎么做的?@RossAllen这就是您的意思吗?我无法访问
delete()
中的
this.state.todoArray
。它返回给我以下信息:
uncaughttypeerror:cannotreadproperty'todoArray'of undefine
感谢您的解释,现在我将该道具记录在两个组件中。但是,当我尝试更新AddTodoComponent中的状态时,它抛出了一个错误:
uncaught TypeError:无法在每个其他函数
this.state中读取未定义的
的属性“todoArray”。除了
delete()
之外,todoArray
是可识别的,它甚至无法记录状态。感谢您的回答,但是todo道具没有正确显示,这是输入字段的值。这仅在触发
onChange
方法时才会显示。我不太明白您希望它做什么。
todo道具
工作不正常,它必须在
TodoItemComponent
中显示,因为您可以看到它是输入值。但是现在它只在
onChange
方法上被触发。因此,首先我使用
this.state.todo
给出了
todo prop
this,这样它就可以在
TodoItemComponent
中呈现,但是当我使用你的代码时,我无法访问
todo prop
,所以todoItem返回空。