从JSX调用方法时如何对更新做出反应?

时间:2018-02-20 16:37:55

标签: javascript reactjs jsx

我的jsx中有一张桌子可以呈现一张排行榜。我想现在展示每个团队的“形式”。即最近5场比赛。

我有一种方法可以解决这个问题(称为表格)

 const LeagueTable = ({ teams, form }) => (
  <table className="leagueTable">
    <thead>
      <tr className="tableRow">
        <th>#</th>
        <th>Name</th>
        <th>P</th>
        <th>W</th>
        <th>D</th>
        <th>L</th>
        <th>F</th>
        <th>A</th>
        <th>GD</th>
        <th>Pts</th>
        <th>Form</th>
      </tr>
    </thead>
    <tbody>
      {teams.sort((a, b) => (
          (b.points) - (a.points)
      )).map((team, index) => (
        <tr key={index} className="tableRow">
         <td className="stats">{index + 1}</td>
         <td className="stats">{team.name}</td>
         <td className="stats">{team.won + team.lost + team.drawn}</td>
         <td className="stats">{team.won}</td>
         <td className="stats">{team.drawn}</td>
         <td className="stats">{team.lost}</td>
         <td className="stats">{team.goalsScored}</td>
         <td className="stats">{team.goalsAgainst}</td>
         <td className="stats">{team.goalsScored - team.goalsAgainst}</td>
         <td className="stats">{team.points}</td>
         <td className="stats">{form(team)}</td>
       </tr>
     ))}
    </tbody>
 </table>
);

这是方法:

 form = (team) => {
    let lastFiveMatches;
    return team && team.matches ?
      lastFiveMatches = Object.values(this.props.teams.find(t => t.name === team.name).matches).sort(this.compare).reverse().slice(0, 5).map((match) => {
        if(match.winner === team.name){
          return 'W ';
        }
        else if(match.winner !== team.name){
          return 'L ';
        }
        else {
          return 'D ';
        }
      })
    :
    '---'
  }

基本上它一切正常但是自从将这个方法添加到我的表后,它只在刷新而不是立即更新我的表(这是它之前做的)

任何人都能解释为什么会这样做以及如何将其改回来?

当我摆脱<td className="stats">{form(team)}</td>时,它立即再次起作用,所以我知道这个方法调用是问题

我尝试添加this.forceUpdate()this.setState(this.state)来强制重新渲染,但看起来这会导致反应爆炸,我收到cannot update during an existing state transition错误。

1 个答案:

答案 0 :(得分:0)

添加此form函数的方式会给您带来很多痛苦。

即使您说它有效,但函数内的this.props...无效。

如果你想让它发挥作用,我会做的是:

您需要在函数

中定义compare而不是this
const compare = ()=>{'whatever'}

表单代码:

const form = (team, teams) => {
    let lastFiveMatches;
    return team && team.matches ?
      lastFiveMatches = Object.values(teams.find(t => t.name === team.name).matches).sort(compare).reverse().slice(0, 5).map((match) => {
        if(match.winner === team.name){
          return 'W ';
        }
        else if(match.winner !== team.name){
          return 'L ';
        }
        else {
          return 'D ';
        }
      })
    :
    '---'
  }

现在如何在你的表中使用它:

<td className="stats">{form(team, teams)}</td>

使您的功能干净,不依赖于特定的this或范围。 您可以绑定特定范围,但这不是您想要做的事情。

更新: 在审查代码之后,我认为这是范围问题

请将构造函数添加到包含'form'方法的组件中并在其中

 this.form = this.form.bind(this)

或者您可以使用ES6代替 桌上道具:

 <Table
          teams={teams}
          form={team=> this.form(team)}
        />