react 的高阶组件(基础篇)
react 的高阶组件(基础篇)
一、什么是高阶组件?
一个高阶组件只是一个包装了另外一个 React 组件的 React 组件。
这种形式通常实现为一个函数,本质上是一个类工厂(class factory),它下方的函数标签伪代码启发自 Haskell
hocFactory:: W: React.Component => E: React.Component
这里 W(WrappedComponent) 指被包装的 React.Component,E(Enhanced Component) 指返回的新的高阶 React 组件。
定义中的『包装』一词故意被定义的比较模糊,因为它可以指两件事情:
- 属性代理(Props Proxy):高阶组件操控传递给 WrappedComponent 的 props,
- 反向继承(Inheritance Inversion):高阶组件继承(extends)WrappedComponent。
我们将讨论这两种形式的更多细节。
二、我可以使用高阶组件做什么呢?
概括的讲,高阶组件允许你做:
- 代码复用,逻辑抽象,抽离底层准备(bootstrap)代码
- 渲染劫持
- State 抽象和更改
- Props 更改
在探讨这些东西的细节之前,我们先学习如何实现一个高阶组件,因为实现方式『允许/限制』你可以通过高阶组件做哪些事情。
三、代码如下:
1.1 before.js 文件
import React from 'react'
// Before组件
export default class Before extends React.Component {
constructor(props){
super(props);
}
render(){
return (
<p>我是before组件<p/>
)
}
}
1.2 after.js 文件
import React from 'react'
// after 组件
export default class after extends React.Component {
constructor(props){
super(props);
}
render(){
return (
<p>我是after组件<p/>
)
}
}
1.3 componentObj.js 文件
import React from 'react'
import HOC from './HOC'
// componentObj组件
class ComponentObj extends React.Component {
constructor(props){
super(props);
}
render(){
return (
<p> hello 张三 <p/>
)
}
}
export default HOC(ComponentObj) // 引用高阶组件
1.4 高阶组件 HOC.js 文件
import React from 'react'
import Before from './before'
import After from './after'
// 创建一个高阶组件HOC 参数是另一个组件对象
export default function HOC (componentObj){
//获取组件的名称 每个导出的组件都有obj.name属性
const getDisplayName = componentObj.displayName || componentObj.name ;
class HOC extends React.Component {
constructor(props){
super(props);
this.state = {
isDisplay: true // 是否展示
}
}
// 组件渲染之前
componentWillMount(){
// 调用后台的方法
}
// 组件渲染之后
componentDidMount(){
// 调用后台的方法
}
render(){
//return中只能放html标签 不能添加表达式 所以在return外面添加三元运算 实现动态
const commentHtml = {
!!this.state.isDisplay?(
<p>我是commentHtml组件</p>):null
}
// 高阶组件的封装与覆盖
return (
<Before />
<componentObj {...this.state} {...this.props}/>
{commentHtml}
<after />
)
}
}
// 设置组件的显示名称
HOC.displayName = `Pro_(${getDisplayName(componentObj)})`;
return HOC;
}
1.6 返回结果
页面展示效果:
我是before组件
hello 张三
我是commentHtml组件
我是after组件