2015-05-26 80 views
1

我有一个反应组件,它表示单词表中的一行。它在状态更改时重新呈现,但不会更新事件处理程序onClick。我已经将组件剥离到最低限度,并且仍然存在问题。当我点击“编辑”链接时,控制台打印出“onEdit”,并且状态在浏览器中似乎看起来正确,但是当我点击“还原”时,控制台再次打印“onEdit”。为什么在状态更改之后onClick事件没有更新为使用_onRevert函数?为什么它仍然挂在第一个渲染通道的旧事件处理程序上?谢谢。React组件无法更新onClick事件处理程序

var React = require('React/addons'); 

var WordListItem = React.createClass({ 
    getInitialState: function(){ 
     return { 
      isEditing: false, 
      english: this.props.word.english 
     }; 
    }, 
    _onEdit: function(e) { 
     e.preventDefault(); 
     console.log('onEdit'); 
     this.setState({isEditing: true}); 
    }, 
    _onRevert: function(e){ 
     e.preventDefault(); 
     console.log('onRevert'); 
     this.setState({isEditing: false}); 
    }, 
    render: function() { 
     if(this.state.isEditing) { 
      return (
       <div> 
        <span>Editing: {this.state.english} </span> 
        <a href="#" onClick={this._onRevert}>Revert</a> 
       </div> 
      ) 
     } else { 

      return (
       <div> 
        <span>Not Editing: {this.state.english} </span> 
        <a href="#" onClick={this._onEdit}>Edit</a> 
       </div> 
      ) 
     } 

    } 
}) 

module.exports = WordListItem; 

更新下

因此,原来,它的作品,如果我这个组件粘贴到我的主要app.jsx文件,它的工作原理,但如果我有使用它需要的js。这很奇怪,因为browserify正在工作,因为我仍然可以包含其他文件并编写嵌套的反应组件,只是它的事件不会在某些元素上得到更新。也许在这一点上,我应该提出一个新的问题,这个问题更关注。

var React = require('react/addons'); 
//var materialize = require('materialize-css'); 
var word = {id: 4671810846, english: "water", persian: "آب", phonetic: "aab", tags: ["noun","food","drink"]}; 

var WordListItem = require('./components/wordList/WordListItem.jsx'); 

// var WordListItem = React.createClass({ 
//  getInitialState: function(){ 
//   return { 
//    isEditing: false, 
//    english: this.props.word.english 
//   }; 
//  }, 
//  _onEdit: function(e) { 
//   e.preventDefault(); 
//   console.log('onEdit'); 
//   this.setState({isEditing: true}); 
//  }, 
//  _onRevert: function(e){ 
//   e.preventDefault(); 
//   console.log('onRevert'); 
//   this.setState({isEditing: false}); 
//  }, 
//  render: function() { 
//   if(this.state.isEditing) { 
//    return (
//     <div> 
//      <span>Editing: {this.state.english} </span> 
//      <a href="#" onClick={this._onRevert}>Revert</a> 
//     </div> 
//   ) 
//   } else { 
// 
//    return (
//     <div> 
//      <span>Not Editing: {this.state.english} </span> 
//      <a href="#" onClick={this._onEdit}>Edit</a> 
//     </div> 
//   ) 
//   } 
// 
//  } 
// }) 


React.render(<WordListItem word={word}/>, document.getElementById('app')); 
+0

console.log“this”里面的函数调用了_onEdit,然后console.log的状态是isEditing。你确定你的上下文在该函数中是正确的吗? –

+0

那很有趣。当我登录'this'并单击编辑然后单击还原时,_onEdit和_onRevert处理程序都会记录相同的this对象,并且isEditing的状态在此对象内设置为true。但是,this.state.isEditing首先打印false,然后打印为true。 – aherriot

+0

好吧,至少有真正的问题。你的代码工作,但它看起来像inital国家正在重新设置。 –

回答

1

你可以显示你在父级渲染这个子组件的方式吗?我怀疑当你生成一个WordListItem的数组时,你并没有设置一个key属性(或者使用一个简单的索引作为key属性,如果你也删除了WordListItem的话,这是一个灾难处理的秘诀,这个关键字必须是唯一的。

而且我觉得这个组件会更好,如果它没有状态可言,对顶级父组件状态,而不是发送道具到孩子

编辑:

在你word_list_item。 jsx文件,你需要反应为var React = require('React/addons');这只是你在粘贴代码时犯的一个错误吗?它应该是var React = require('react/addons')和小写字母Jus小小的观察,不知道这是否与任何事情有关,但肯定看起来像你有某种浏览问题。

+0

感谢您的建议。我绝对在它们的列表中设置了一个唯一的键。此外,该州是有用的,只是可能不适合这个精简版本。 – aherriot