5.1 初识State
React 把组件看成是一个状态机(State Machines)。通过与用户交互,实现不同状态,然后渲染 UI,让界面和数据保持一致,只需更新组件的 state,然后根据新的 state 就可以重新渲染用户界面了。
State 与 props 类似,但是 state 是私有的,并且完全受控于当前组件。
下面的例子是通过state获取date参数,将其展示出来
import React from "react"
import ReactDOM from "react-dom"
class Clock extends React.Component {
constructor(props) {
super(props);
this.state = {date: new Date()};
}
render() {
return (
<div>
<h1>时间</h1>
<h2>现在是 {this.state.date.toLocaleTimeString()}.</h2>
</div>
);
}
}
ReactDOM.render(
<Clock />,
document.getElementById('root')
);
结果:
5.2 React生命周期
在许多框架中,都有生命周期的概念,在react中同样如此,需要在销毁时释放组件所占用的资源
先通过一个例子来直观感受一下react的生命周期使用
import React from "react"
import ReactDOM from "react-dom"
class Clock extends React.Component {
constructor(props) {
super(props)
this.state = {date : new Date()}
}
tick() {
this.setState({
date : new Date()
});
}
componentDidMount() {
setInterval(
() => this.tick(),
1000
)
}
componentWillUnmount() {
clearInterval()
}
render() {
return (
<div>
<h1>time0</h1>
<h2>now is {this.state.date.toLocaleTimeString()}</h2>
</div>
)
}
}
ReactDOM.render(
<Clock />,
document.getElementById("root")
)
在react中componentDidMount()与componentWillUnmount()方法被称为生命周期钩子,上述代码执行顺序是:
1. 先执行constructor()构造函数
2. 第二步执行render()方法,渲染输出
3. 当第二步完成渲染后,执行componentDidMount()生命周期钩子,这里设置了一个定时器,来调用tick()
4. 定时器调用tick()后,该函数使用setState()来设置date的值,当设置完成后,React得知状态已经改变,再次调用render()函数来渲染页面
5. 如果Clock组件被从DOM中移除,React会调用componentWillUnmount()这个函数,清除定时器
结果:
5.3 state中的数据流动
父组件或子组件都不能知道某个组件是有状态还是无状态的,并且也不关心某组件是被定义为一个函数还是一个类。状态除了拥有并设置它的组件外,其它组件不可访问。
下面例子中 FormattedDate 组件将在其属性中接收到 date 值,并且不知道它是来自 state、还是来自属性,只要接收到就展示
import React from "react"
import ReactDOM from "react-dom"
function FormattedDate(props) {
return <h2>现在是 {props.date.toLocaleTimeString()}.</h2>;
}
class Clock extends React.Component {
constructor(props) {
super(props);
this.state = {date: new Date()};
}
componentDidMount() {
this.timerID = setInterval(
() => this.tick(),
1000
);
}
componentWillUnmount() {
clearInterval(this.timerID);
}
tick() {
this.setState({
date: new Date()
});
}
render() {
return (
<div>
<h1>Hello, world!</h1>
<FormattedDate date={this.state.date} />
</div>
);
}
}
ReactDOM.render(
<Clock />,
document.getElementById('root')
);
结果:
所有组件的state都是隔离的,相互之间不影响