2017-01-09 6 views
0

Ich konnte nicht erkennen, was mit dem Code falsch ist. Ich übergebe Zustand über Requisiten, das NewItem ging durch, aber ich konnte den Zustand in Todos Komponente nicht aktualisieren.Fehler beim Hinzufügen von Element und Update-Status ist react.js

class AddTodo extends React.Component { 
    constructor(){ 
    super(); 
    this.state = {text: ''}; 
    } 
    onTextChanged(e){ 
    this.setState({text:e.target.value}); 
    } 
    addHandler(){ 
    this.props.addTodo(this.state.text); 
    } 
    render() { 
    return(
     <div> 
     <input type="text" onChange={(e)=>this.onTextChanged(e)} /> 
     <button onClick={()=>this.addHandler()}>Add</button> 
     </div> 
    ) 
    } 
} 

class Todos extends React.Component { 
    constructor(){ 
    super(); 
    this.state = {data: ['write book','wash clothes','jogging']}; 
    } 
    addTodo(item){ 
    const newData = [...this.state.data, item]; //problem is here 
    this.setState({ data: newData }); //problem is here 
    console.log(this.state.data) 
    } 
    render() { 
    return (  
     <div> 
     <AddTodo addTodo={(item)=>this.addTodo(item)}/> 
     <ul> 
     {this.state.data.map((item)=><TodoItems key={item} item={item}/>)} 
     </ul> 
     </div> 
    ); 
    } 
} 

http://jsbin.com/nitibinale/1/edit?html,js,console,output

+0

Wie binden Sie AddTodo-Funktionen an die Instanz? Ich sehe anonyme Funktionen, aber "das" ist der falsche Wert in ihnen. Alles in der Konsole? Welche Schritte haben Sie zum Debuggen unternommen? –

+0

@DaveNewton warum muss ich binden? pfeilfunktion von es6 macht hier nicht die arbeit? –

+0

@DaveNewton http://jsbin.com/pajoliboqi/1/edit funktioniert auch nicht, wenn ich es6 nicht verwende –

Antwort

1

Ihr Code korrekt ist, Dies ist wahrscheinlich ein Fehler mit JSBin, und wie es behandelt transpilation mit Babel

class AddTodo extends React.Component { 
 
    constructor(){ 
 
    super(); 
 
    this.state = {text: ''}; 
 
    } 
 
    onTextChanged(e){ 
 
    this.setState({text:e.target.value}); 
 
    } 
 
    addHandler(){ 
 
    this.props.addTodo(this.state.text); 
 
    } 
 
    render() { 
 
    return(
 
     <div> 
 
     <input type="text" onChange={(e)=>this.onTextChanged(e)} /> 
 
     <button onClick={()=>this.addHandler()}>Add</button> 
 
     </div> 
 
    ) 
 
    } 
 
} 
 

 
class Todos extends React.Component { 
 
    constructor(){ 
 
    super(); 
 
    this.state = {data: ['write book','wash clothes','jogging']}; 
 
    } 
 
    addTodo(item){ 
 
    const newData = [...this.state.data, item]; //problem is here 
 
    this.setState({ data: newData }); //problem is here 
 
    console.log(this.state.data) 
 
    } 
 
    render() { 
 
    return (  
 
     <div> 
 
     <AddTodo addTodo={(item)=>this.addTodo(item)}/> 
 
     <ul> 
 
     {this.state.data.map((item)=><TodoItems key={item} item={item}/>)} 
 
     </ul> 
 
     </div> 
 
    ); 
 
    } 
 
} 
 

 
class TodoItems extends React.Component { 
 
    constructor(props){ 
 
    super() 
 
    this.state = { 
 
     text: props.item, 
 
     isEditing: false 
 
    }; 
 
    } 
 
    onClickEdit(){ 
 
    this.setState({isEditing: !this.state.isEditing}); 
 
    } 
 
    onSaveEdit(e){ 
 
    this.setState({ 
 
     isEditing: false, 
 
     text: this.state.text 
 
     }); 
 
    } 
 
    onTextChanged(e){ 
 
    this.setState({text: e.target.value}); 
 
    } 
 
    onEnter(e){ 
 
    if(e.charCode === 13){ 
 
     this.setState({ 
 
     isEditing: false, 
 
     text: this.state.text 
 
     }); 
 
    } 
 
    } 
 
    render(){ 
 
    return(
 
     <div> 
 
     
 
     <li> 
 
     {this.state.isEditing ? '' : <span>{this.state.text}</span>} 
 

 
     {this.state.isEditing ? <span><input value={this.state.text} onKeyPress={(e)=>this.onEnter(e)} 
 
    type="text" onChange={(e)=>this.onTextChanged(e)}/></span> :''} 
 
    &nbsp;&nbsp; 
 
     {this.state.isEditing ? '' : <button onClick={()=>this.onClickEdit()}>Edit</button>} 
 

 
     {this.state.isEditing ? <button onClick={()=>this.onSaveEdit()}>Save</button> : ''} 
 
     </li> 
 
     </div> 
 
    ) 
 
    } 
 
} 
 

 
React.render(
 
    <Todos />, 
 
    document.getElementById('react_example') 
 
);
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.8/react.min.js"></script> 
 
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/0.14.8/react-dom.min.js"></script> 
 
<div id="react_example"></div>

0

Blick auf diese: https://jsfiddle.net/0mhvbnhx/

class AddTodo extends React.Component { 
    constructor(){ 
    super(); 
    this.state = {text: ''}; 
    } 
    onTextChanged(e){ 
    this.setState({text:e.target.value}); 
    } 
    addHandler() { 
    this.props.addTodo(this.state.text); 
    this.setState({ text: '' }); 
    } 
    render() { 
    return(
     <div> 
     <input type="text" value={this.state.text} onChange={(e)=>this.onTextChanged(e)} /> 
     <button onClick={()=>this.addHandler()}>Add</button> 
     </div> 
    ) 
    } 
} 

class Todos extends React.Component { 
    constructor(){ 
    super(); 
    this.state = { 
     data: ['write book','wash clothes','jogging'] 
    }; 
    } 
    addTodo = (item) => { 
    const data = [...this.state.data, item]; 
    this.setState({ data }); 
    } 
    changeTodo = (i, text) => { 
    const data = [...this.state.data]; 
    data[i] = text; 
    this.setState({ data }); 
    } 
    render() { 
    return (  
     <div> 
     <AddTodo addTodo={this.addTodo}/> 
     <ul> 
     {this.state.data.map((item, i)=> 
      <TodoItems key={i} index={i} item={item} changeTodo={this.changeTodo}/> 
     )} 
     </ul> 
     </div> 
    ); 
    } 
} 

class TodoItems extends React.Component { 
    constructor(props){ 
    super() 
    this.state = { 
     isEditing: false, 
     text: '', 
    }; 
    } 
    onClickEdit(){ 
    this.setState({isEditing: !this.state.isEditing, text: this.props.item}); 
    } 
    onSaveEdit(){ 
    this.props.changeTodo(this.props.index, this.state.text); 
    this.setState({ 
     isEditing: false, 
    }); 
    } 
    onTextChanged(e){ 
    this.setState({text: e.target.value}); 
    } 
    onEnter(e) { 
    if(e.charCode === 13){ 
     this.onSaveEdit(); 
    } 
    } 
    render(){ 
    return(
     <div> 

     <li> 
     {this.state.isEditing ? '' : <span>{this.props.item}</span>} 

     {this.state.isEditing ? <span><input value={this.state.text} onKeyPress={(e)=>this.onEnter(e)} 
    type="text" onChange={(e)=>this.onTextChanged(e)}/></span> :''} 
    &nbsp;&nbsp; 
     {this.state.isEditing ? '' : <button onClick={()=>this.onClickEdit()}>Edit</button>} 

     {this.state.isEditing ? <button onClick={()=>this.onSaveEdit()}>Save</button> : ''} 
     </li> 
     </div> 
    ) 
    } 
} 

React.render(
    <Todos />, 
    document.getElementById('react_example') 
); 
+0

das funktionierte, aber Sie haben eine Funktion hinzugefügt, die ich denke nicht benötigt wird. –

+0

@JennyMok Welcher? –

+0

changeTodo, warum brauchst du das? –

0

Ich glaube, Shubham hat in seiner Antwort Recht. Wenn Sie sich die answer aus einer verwandten Frage ansehen, werden Sie sehen, dass Sie wahrscheinlich das // noprotect Pragma oben hinzufügen müssen, damit JS Bin funktioniert. Dein Code funktioniert einwandfrei.

Abgesehen: Sie können die Callback-Version von setState (link) zu prüfen, verwenden, da es asynchron ist, und this.state nicht immer konsistent sein, wenn Sie es die Art und Weise Zugang sind Sie zur Zeit.

Verwandte Themen