setState

时间:2019-04-30 18:16:08

标签: reactjs setstate

我正在使用react-d3-graph构建一个React应用。我有这样的状态:

data: {
        nodes: [{"id": "8", "color": "red"}],
      },

通过单击图形的一个节点,我想将其颜色从红色更改为黄色。因此,我对初始化状态的根组件进行了回调。根组件中的回调如下所示:

var color = {...this.state.data}
color.nodes[0].color = 'yellow';
this.setState({color});

如果我用console.log记录状态,则值已更改,但应用程序中的节点仍为红色。 但是,这些更改会在应用程序中执行以下任何操作之后发生。

1 个答案:

答案 0 :(得分:0)

您永远不要直接修改React状态,而必须像下面这样不变地进行修改:

var modifiedData = {...this.state.data}; // shallow copy of data
var modifiedNodes = [...this.state.data.nodes] // shallow copy of nodes array
var modifiedNode = {...this.state.data.nodes[0]} // shallow copy of node you are trying to change the color of
modifiedNode.color = 'yellow'; // changes color of a copy of the original node (not the original node itself, ensuring you aren't modifying the original React state directly)
modifiedNodes[0] = modifiedNode; // modifies the copy, for same reason
modifiedData.nodes = modifiedNodes; // modifies the copy, again for same reason
this.setState({data: modifiedData });

此外,不确定最后一行上为什么有“ this.setState({color});”。如果您的状态为“数据:{         节点:[{“ id”:“ 8”,“ color”:“ red”}],       },” 那么您应该拥有“ this.setState({data:modifiedData});”,就像我上面提到的那样。同样,您不应该像在“ color.nodes [0] .color ='yellow';'”中那样直接修改状态。这是直接修改状态,因为'var color = [... this.state.data]'仅进行浅表复制,这意味着不会深度复制任何嵌套的数组和对象(因为它们在Javascript中是引用类型)。您必须像我上面那样深深地复制它们。

有关为何不应该直接修改状态的更多信息:

https://daveceddia.com/why-not-modify-react-state-directly/

Why can't I directly modify a component's state, really?