1,state(状态)的作用
使用 react 构建应用时,状态的设计和维护应该是思考的重点,状态的数据结构设计的好,页面和逻辑就会好写很多,并且代码也易于维护。
我认为一个组件应该被划分为三个部分,分别是:状态、页面 和 逻辑,状态处于核心位置,它们之间相互的关系如下图所示:
图中的要点总结如下:
- 使用状态构建页面。
- 使用逻辑变更状态,进而间接的控制页面。
- 用户在页面上的操作能够触发执行逻辑。
- 逻辑也可以依据业务进行自执行。
开发功能时,思考顺序如下:
- 依据业务设计状态。
- 写页面,并将状态绑定到页面中,利用状态控制页面。
- 在页面中绑定事件。
- 写逻辑代码。
2,state 的初始化
state 就是类实例中的一个属性,初始化方式有两种。
第一种:在 constructor() 方法中使用 this.state = xxxx。
class Weather extends React.Component{
constructor(){
super()
this.state = {isHot:false,wind:'微风'}
}
}
第二种:在类的底层直接写。
class Weather extends React.Component{
state = { isHot: false, wind: '微风' }
}
这两种方案更推荐第二种写法,更加的简洁清晰。
3,react 中如何绑定事件
class Weather extends React.Component{
state = {isHot:false,wind:'微风'}
render(){
const {isHot,wind} = this.state
return <h1 onClick={this.changeWeather}>今天天气很{isHot ? '炎热' : '凉爽'},{wind}</h1>
}
// 定义方法 changeWeather,并且使用的是箭头函数
changeWeather = () => {
const isHot = this.state.isHot
this.setState({isHot:!isHot})
}
}
小总结:
- react 中绑定事件的语法是 onXxxx = { this.methodName }。
- changeWeather 方法是 h1 元素 click 事件的回调函数,为了使回调函数中的 this 指向类实例,使用了箭头函数。
4,如何变更 state
class Weather extends React.Component{
state = {isHot:false,wind:'微风'}
render(){
const {isHot,wind} = this.state
return <h1 onClick={this.changeWeather}>今天天气很{isHot ? '炎热' : '凉爽'},{wind}</h1>
}
// 定义方法 changeWeather,并且使用的是箭头函数
changeWeather = () => {
const isHot = this.state.isHot
this.setState({isHot:!isHot})
}
}
小总结:
- react 中变更状态必须使用 setState 方法,不能直接变更 this.state 中的数据。
- setState 方法内部除了变更数据,还会触发组件的重新渲染,这是直接变更数据所不具备的。
setState 是 React.component 构造函数原型对象中的方法,源码如下:
/** * Base class helpers for the updating state of a component. */ function Component(props, context, updater) { this.props = props; this.context = context; // If a component has string refs, we will assign a different object later. this.refs = emptyObject; // We initialize the default updater but the real one gets injected by the // renderer. this.updater = updater || ReactNoopUpdateQueue; } Component.prototype.setState = function (partialState, callback) { !(typeof partialState === 'object' || typeof partialState === 'function' || partialState == null) ? invariant(false, 'setState(...): takes an object of state variables to update or a function which returns an object of state variables.') : void 0; this.updater.enqueueSetState(this, partialState, callback, 'setState'); };
5,完整的案例
结合第一小节的内容,思考下面完整代码的 状态、页面 和 逻辑。
<script type="text/babel">
//1.创建组件
class Weather extends React.Component{
//初始化状态
state = {isHot:false,wind:'微风'}
render(){
const {isHot,wind} = this.state
return <h1 onClick={this.changeWeather}>今天天气很{isHot ? '炎热' : '凉爽'},{wind}</h1>
}
//自定义方法————要用赋值语句的形式+箭头函数
changeWeather = () => {
const isHot = this.state.isHot
this.setState({isHot:!isHot})
}
}
console.log(Weather.prototype)
//2.渲染组件到页面
ReactDOM.render(<Weather/>,document.getElementById('test'))
</script>