props校验,默认值
Consumer, Provider
const p = {
name="zhangsan",
age="18"
}
<Provider name="zhangsan" age="18">
<App />
<Provider />
<Consumer>
{(info) => (
// 通过Consumer直接获取父组件的值
<div>
<p>父组件的值:{info}</p>
<GrandSon />
</div>
)}
</Consumer>
组件名.defaultProps = {
age: 1,
str: 'zhangsan'
}
import PropTypes from 'prop-types';
组件名.propTypes = {
optionalArray: PropTypes.array,
optionalBool: PropTypes.bool,
optionalFunc: PropTypes.func,
optionalNumber: PropTypes.number,
optionalObject: PropTypes.object,
optionalString: PropTypes.string,
optionalSymbol: PropTypes.symbol,
optionalObjectWithShape: propTypes.shape({
num: PropTypes.number,
str: PropTypes.string,
})
optionalArray: PropTypes.element,
optionalArray: PropTypes.array,
}
render-props: 共享数据,共享组件
1.
1-1、 将复用的数据this.props.render(state),暴露出去
1-2、 使用props.render()的返回值作为渲染的内容
子组件
state: {数据}
render() {
return this.props.render(this.state)
}
父组件
<子组件 render=((data) => <p>数据: {data}><p />)<子组件 />
2.
2-1、children代替props
2-2、优化,建议添加props校验
子组件名称.ProTypes = {
childlren: PropTypes.func.isRequired
}
2-3、优化,组件卸载时,解除事件绑定,清楚定时器
子组件
state: {数据}
render() {
return this.props.render(this.state)
}
父组件
<子组件>
{(data) => <p>数据: {data}}
<子组件 />
生命周期
创建时:
constructor -> 初始化state,为事件处理程序绑定this
render -> 每次组件渲染时触发(渲染UI,不能调用this.setState)
componentWillMount -> 组件挂载(完成dom渲染后)-> 发送请求,DOM操作
更新时:
render -> 完成UI渲染
componentDidUpdate -> 组件更新完成dom渲染 -> 发送请求,don操作,
卸载时:
componentWillUnmount -> 组件卸载时 -> 执行清理工作如:定时器、、
更新执行渲染时执行:
shoudComponentUpdata -> render
shoudComponentUpdata(nextPrpos, nextState) {
return false/ture
}
高阶组件
1.创建一个函数,名称约定以 with 开头
2.指定函数参数,参数应该以大写字母开头(作为要渲染的组件)
3.在函数内部创建类组件,提供复用的状态逻辑代码,并返回
4.在该组件中,渲染参数组件,同事将状态通过prop传递给参数组件
5.调用该高阶组件,传入要增强的组件,通过返回值拿到增强后的组件,并将其渲染到页面中
6.设置组件的displayName,区分组件,方便调试。
7.传递props,state
function withMouse(WrappedComponent) {
class Mouse extends React.component {
render <WrappedComponent (...this.state) (...this.props)> <WrappedComponent />
}
Mouse.displayName = `Mouse${getDisplayName(WrappedComponent)}`
return Mouse
}
function getDisplayName(WrappedComponent){
return WrappedComponent.displayName || WrappedComponent.name || 'Component'
}
const mouse = withMouse('子组件')
setState方法
1.使用'this.state({})',不能同步获取修改后最新的值,'this.setState()'是异步的
2.推荐使用'this.setState((state, props) => {return {}})',获取的都是最新的值
3.在状态更新完后,立即执行某个操作(页面完成重新渲染),使用'this.setState'第二个参数
'this.setState(
(state, props) => {return {}},
() => {
console.log('状态更新后立即执行')
}
)'
纯组件:PureComponent
纯组件:PureComponent 与 React.Component功能相似
区别:PureComponent内部自动实现了shuldConponentUpdata钩子,不需要手动比较
1.纯组件内部的对比是shallow compare(浅层对比)
2.state和props的值为引用类型时,应该创建新数据,不是直接修改属性中的值
class App extendds React.shuldComponent{
rennder() {
return (
<div>纯组件</div>
)
}
}
路由
npm i react-router-dom
1. 导入import { BrowserRouter as Router, Route, Link } from 'react-router-dom'
import { HashRouter as Router, Route, Link } from 'react-router-dom'
2. 使用Router组件包裹整个组件
3. 指定入口
4. 指定出口
Link: 导航菜单
编程式导航:this.poprs.history.push('/home'),
返回:this.poprs.history.go(n)
默认路由: path="/"
匹配模式:
react默认是模糊匹配,以path开头的都会匹配成功
添加exact属性,让其变成精确匹配:<Router exact path="/first" component={first}></Router>
const first = () => <p>页面一</p>
<Router>
<div className="App">
// 路由入口
<Link to="/first">页面一</Link>
// 路由出口,要展示的组件
<Router path="/first" component={first}></Router>
</div>
</Router>
redux
npm i redux
import { createStore } from 'redux'
const store = createStore(reducer)