为什么React会更改我的托管道具?

时间:2016-04-30 07:45:15

标签: javascript reactjs

我尝试使用React编写TODO列表,但是当我更改TodoItem的check属性时,我的结果相反。 {{1也没用。

defaultChecked

简单来说,我设置了每个 var Todo = React.createClass({ getInitialState(){ return{i:0,data:[],allCompleted:false}; }, handleKeyPress(e){ if(e.key === 'Enter' && e.currentTarget.value != ''){ localStorage.setItem(uuid(e.currentTarget.value),JSON.stringify({uuid:uuid(e.currentTarget.value),checked:false,todoContent:e.currentTarget.value})); this.state.data.push({uuid:uuid(e.currentTarget.value),checked:false,todoContent:e.currentTarget.value}); this.setState({i: ++(this.state.i),data:this.state.data}, ()=>{e.target.value = ''}); } }, /* *↓Here I made every item.checked = true when I click the all-completed checkbox; */ handleAllComplete(e){ if(!this.state.allCompleted){ this.state.allCompleted = true; this.state.data.map((item)=>{item.checked?true:item.checked = !item.checked}); return this.setState({data:this.state.data}); } this.state.allCompleted = false; this.state.data.map((item)=>{item.checked = false}); return this.setState({data:this.state.data}); }, handleOneComplete(todoUuid){ console.log('one completed'); this.state.data.map((item)=>{item.uuid==todoUuid?(item.checked = !item.checked):undefined;}); this.setState({data:this.state.data}); }, componentWillMount(){ let data = []; for(var i in localStorage){ if(localStorage.hasOwnProperty(i)){ data.push(JSON.parse(localStorage.getItem(i))); } } this.setState({i:i,data:data}); }, render(){ console.log(this.state.data); return <div> <AddTodoItem handleKeyPress={this.handleKeyPress} handleAllComplete={this.handleAllComplete}/> <TodoItemContainer data={this.state.data} handleOneComplete={this.handleOneComplete}/> <TodoToolBar /> </div> } }); var TodoItemContainer = React.createClass({ render(){ var todoItems = []; for(let i of this.props.data){ todoItems.push(<TodoItem key={i.uuid} uuid={i.uuid} checked={i.checked} content={i.todoContent} style={i.checked?{color:'red'}:undefined} handleOneComplete={this.props.handleOneComplete}/>); console.log(i.checked,'in container'); /* *↑Here's I got the check attribute is true and it meets my expectations; */ } if(todoItems.toString() == ''){ return <div></div>; } return <div>{todoItems}</div>; } }) var TodoItem = React.createClass({ getInitialState(){ return ({checked:this.props.checked,todoContent:this.props.content}); }, componentWillReceiveProps(){ /* *but Here, i got checked = false and that's my question; */ console.log(this.props.checked,'will receive'); this.setState({checked:this.props.checked,todoContent:this.props.content}); }, render(){ console.log(this.state.checked,'render item'); return <div> <input type="checkbox" defaultChecked={this.state.checked} onChange={this.props.handleOneComplete.bind(null,this.props.uuid)}/> <lable style={this.props.style}>{this.state.todoContent}</lable> <button>delete</button> </div> }, }); ,但在TodoItem checked = true TodoItem this.props.checkedfalse

https://jsfiddle.net/20xads1n/1/

1 个答案:

答案 0 :(得分:0)

以下是您的示例的修复版本 https://jsfiddle.net/7s99f2aj/。 有两个问题:

1)您在nextProps方法中错过了componentWillReceiveProps参数(请参阅https://facebook.github.io/react/docs/component-specs.html#updating-componentwillreceiveprops) 2)我在defaultChecked组件

中将checked更改为TodoItem

另外,我建议您在更改状态(即setState而不是this.setState({allCompleted: true}))时随处使用this.state.allCompleted = true;,而不是直接在map内改变状态这样的函数:this.state.data.map((item)=>{item.checked?true:item.checked = !item.checked});。相反,请考虑创建全新的data对象,并使用setState更改您的状态。