我在父组件中有一个数组,在从api中读取一些JSON之后,我需要动态更新它。 我正在使用React Router,并且能够将数组传递给子组件并基于数组值添加一个CSS类,但是我似乎无法弄清楚如何正确地更新数组并将panelone的数组值更改为关闭。
父组件:
import React, { Component } from 'react';
import { Route, NavLink, HashRouter } from "react-router-dom";
import Child from './components/Child';
class App extends Component {
arr = {
panelone : 'on',
paneltwo: 'off'
};
componentDidMount() {
// Some function to get JSON...
this.arr.panelone = 'off'; // ???
//...
}
render() {
return (
<div className="App">
<TopBar />
<HashRouter>
<div>
<nav>
<ul className="header">
<li><NavLink exact to="/">Overview</NavLink></li>
</ul>
</nav>
<div className="main-container">
<Route
exact path="/"
render={(props) => <Child arr = {this.arr} />}
/>
</div>
</div>
</HashRouter>
</div>
);
}
}
子组件:
import React, { Component } from 'react';
import { Link } from "react-router-dom";
class Child extends Component {
render() {
return (
<div>
//This is working OK and css class "on" is added from panelone val
<div className={'item ' + this.props.arr.panelone}>
<p>Some Title</p>
</div>
</div>
);
}
}
export default Child;
使用React Router时动态更新arr和更新子组件的正确方法是什么?
答案 0 :(得分:1)
我将为此使用状态,然后调用setState()
进行更新。您阅读过以下内容:https://reactjs.org/docs/state-and-lifecycle.html#adding-local-state-to-a-class吗?
您不能直接设置或更新道具。我会做这样的事情:
class App extends Component {
constructor(props) {
super(props);
this.state = {
arr = {
panelone : 'on',
paneltwo: 'off'
}
};
}
componentDidMount() {
this.setState({
arr: {
...this.state.arr,
panelone: 'off'
}
});
}
答案 1 :(得分:1)
该arr
实际上是一个实例字段对象,因此访问和更新它的正确方法是通过this
关键字:
componentDidMount() {
// Some function to get JSON...
this.arr = {panelone: 'off', paneltwo: 'on'}
//...
}
但这会给您带来一个问题,即在更新自定义实例字段时React不会更新子组件。
因此正确的方法将是使用组件的状态。在App
的类的开头,用arr
定义状态:
constructor(props) {
super(props);
this.state = {
arr: {
panelone: 'off', paneltwo: 'on'
}
};
}
然后应该使用arr
方法,而不是将setState
更新为实例字段:
componentDidMount() {
// Some function to get JSON...
this.setState({
arr: {
panelone: 'off',
paneltwo: 'on'
}
});
//...
}
在App
的呈现方法中,使用this.state.arr
代替this.arr
:
render() {
return (
<div className="App">
<TopBar />
<HashRouter>
<div>
<nav>
<ul className="header">
<li><NavLink exact to="/">Overview</NavLink></li>
</ul>
</nav>
<div className="main-container">
<Route
exact path="/"
render={(props) => <Child arr = {this.state.arr} />}
/>
</div>
</div>
</HashRouter>
</div>
);
}
这将与您目前使用Child
组件的方式一样工作,您应该检查state documentation