setState
- setState是批量操作的,第一次是批量更新,后续将是每次更新。
- 使用pendingState来保存修改的状态,最终渲染的时候使用state
- update里面setState外面没有添加定时器等的时候,isBatchingUpdate为true,将所有的状态合并之后,在进行render。
- 存在定时器,transcation先执行将isBatchingUpdate变为false,接下来的setState将不是批量更新的,而是每次修改状态每次都更新一次。
let isBatchingUpdate = true; // 默认是批量更新
let transcation = (component) => {
component.state = component.pendingState;
component.render();
isBatchingUpdate = false;
}
class My {
constructor() {
this.state = { number: 0 }; // 自己的状态
this.pendingState = { ...this.state };
}
setState(obj) {
if (isBatchingUpdate) {
this.pendingState = { ... this.pendingState, ...obj };
} else {
this.pendingState = { ... this.pendingState, ...obj };
transcation(this);
}
}
update() {
setTimeout(() => {
this.setState({ number: this.state.number + 1 });
this.setState({ number: this.state.number + 3 });
this.setState({ number: this.state.number + 2 });
}, 0);
transcation(this);
}
render() {
console.log(this.state.number);
}
}
let my = new My();
// 内部会先调用更新方法
my.update();
复制代码
类组件和函数组件
- 函数组件(一个函数就是一个组件),函数名必须大写。
- 没有this指向
- 没有生命周期
- 没有状态
- 类组件(继承React.Component父类),使用父类提供的setState设置状态
- constructor构造函数中调用super
- 使用一些生命周期函数
- 绑定this方式:1、执行事件的时候bind。2、执行事件的时候箭头函数。3、组件定义的方法中使用箭头函数。
- setState有三种方式:1、传递对象。2、传递一个函数,函数参数为prevState。3、传递对象带回调函数。
Props
传递给组件的属性
- 默认props
// 默认属性 必须名字叫defaultProps 属于类上的属性 es7
static defaultProps = {
name:'xxx',
}
复制代码
- 属性校验
static propTypes = { // propTypes 就是专门校验类型的
age: PropTypes.number.isRequired,
gender:PropTypes.oneOf(['男','女']),
postion:PropTypes.shape({
x:PropTypes.number,
y: PropTypes.number
}),
hobby: PropTypes.arrayOf(PropTypes.string),
salary(props, propName, componentNam){
if (props[propName] <= 100000){
throw new Error('收益太低')
}
}
}
复制代码
受控和非受控组件
- 受控组件就是和状态相关联的组件,双向绑定。
- 非受控组件是直接通import React, { Component } from 'react';
import ReactDOM from 'react-dom';
// 如果使用非受控组件好处就是 可以和第三方库使用
// 如果只是点击按钮获取 输入框的内容 更推荐 非受控组件
class Control extends Component {
password = React.createRef();
handleSubmit = (e) => {
e.preventDefault();
console.log(this.username.value);
console.log(this.password.current.value);
}
render() {
return (<div>
<form onSubmit={this.handleSubmit}>
<input required type="text" name="username" ref={(dom) => this.username = dom} />
<input type="email" name="password" ref={this.password} />
<button type="submit">提交</button>
</form>
</div>)
}
}
ReactDOM.render(<Control></Control>, window.root);过dom元素来获取其内部的值(ref)。
复制代码