• react-高阶组件


    一、什么是高阶组件

    高阶组件( Higher-Order Component,HOC )是一个以组件作为参数,返回一个新组件函数

    • 高阶组件最大的特点就是复用组件逻辑
    • 高阶组件本身并不是 React 的 API,而是React组件的一种设计模式,一种组件重用的高级技巧
    • 高阶组件是一个函数,接收要包装的组件,返回增强后的组件

    二、如何实现一个高阶组件

    高阶组件内部创建一个组件,在这个组件中提供复用的状态逻辑代码,通过props将复用状态传递给被包装组件 WrappedComponent

    • 创建一个函数,命名以 with 开头
    • 指定函数参数,参数为组件,所以参数应该以大写字母开头
    • 在函数内部创建一个组件,提供复用的状态逻辑代码,并返回
    • 在该组件中,渲染参数组件,同时将状态通过props传递给参数组件
    • 调用该高阶组件,传入要增强的组件,通过返回值拿到增强后的组件,并将其渲染到页面中
    function withMouse(WrappedComponent) {
    	class Mouse extends React.Component {
    		state = {
    		    x: 0,
    			y: 0,
    		}
    		render() {
    			return (
    				<WrappedComponent {...this.state}></WrappedComponent>
    			)
    		}
    	}
    	return Mouse
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    const Position = props => (
    	<div>
    	    鼠标位置: {props.x}, {props.y}
    	</div>
    )
    
    const MousePosition = withMouse(Position)
    
    <MousePosition />
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    三、高阶组件demo

    • 代码
    import React from 'react'
    
    /**
     * 高阶组件
     */
    
    // 获取组件名
    // function getDisplayName(WrappedComponent) {
    // 	return WrappedComponent.displayName || WrappedComponent.name || 'Component'
    // }
    
    // 创建高阶组件
    function withMouse(WrappedComponent) {
    	// 该组件提供复用的状态逻辑
    	class Mouse extends React.Component {
    		// 初始化state
    		state = {
    			x: 0,
    			y: 0,
    		}
    
    		// 渲染UI,可以将state和props 一起传递给组件
    		render() {
    			return (
    				<WrappedComponent {...this.state} {...this.props}></WrappedComponent>
    			)
    		}
    
    		// 组件挂载,监听鼠标移动
    		componentDidMount() {
    			window.addEventListener('mousemove', this.handleMouseMove)
    		}
    
    		// 组件卸载,移除监听
    		componentWillUnmount() {
    			window.removeEventListener('mousemove', this.handleMouseMove)
    		}
    
    		// 鼠标移动事件处理程序
    		handleMouseMove = e => {
    			this.setState({
    				x: e.clientX,
    				y: e.clientY,
    			})
    		}
    	}
    
    	// 设置displayName  这个为了调试区分用,可以不设置
    	// Mouse.displayName = `WithMouse${getDisplayName(WrappedComponent)}`
    
    	// 返回增强后的组件
    	return Mouse
    }
    
    // 位置组件,用来测试高阶组件
    const Position = props => (
    	<div>
    		<h2>
    			鼠标位置: {props.x}, {props.y}
    		</h2>
    		MousePosition组件: 接收的参数 a == {props.a}
    	</div>
    )
    
    // 猫抓老鼠组件,用来测试高阶组件
    const Cat = props => (
    	<div>
    		<img
    			src={require('../../assets/images/cat.png')}
    			alt="猫"
    			height="22px"
    			style={{
    				position: 'absolute',
    				top: props.y - 10,
    				left: props.x - 10,
    			}}
    		/>
    		MouseCat组件: 接收的参数 a == {props.a}
    	</div>
    )
    
    // 获取增强后的组件
    const MousePosition = withMouse(Position)
    const MouseCat = withMouse(Cat)
    
    // 使用
    class MouseHigher extends React.Component {
    	// 渲染增强后的组件
    	render() {
    		return (
    			<div>
    				<MousePosition a="111"></MousePosition>
    				<MouseCat a="222"></MouseCat>
    			</div>
    		)
    	}
    }
    
    export default MouseHigher
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67
    • 68
    • 69
    • 70
    • 71
    • 72
    • 73
    • 74
    • 75
    • 76
    • 77
    • 78
    • 79
    • 80
    • 81
    • 82
    • 83
    • 84
    • 85
    • 86
    • 87
    • 88
    • 89
    • 90
    • 91
    • 92
    • 93
    • 94
    • 95
    • 96
    • 97
    • 98
    • 99
    • 100
    • 效果

    在这里插入图片描述

  • 相关阅读:
    两进两出热电阻信号隔离变送器
    【音视频】FLV封装格式
    requests库中解决字典值中列表在URL编码时的问题
    C++第二学期期末考试选择题题库(qlu题库,自用)
    ArcGIS Pro中的回归分析浅析(上)回归的概念&探索性回归工具使用
    windows 可以禁用的服务盘点
    LeetCode 盛最多水的容器 双指针
    c语言从入门到实战——分支和循环
    【Redis笔记】发布与订阅
    leetcode两数之和使用JavaScript解题
  • 原文地址:https://blog.csdn.net/Miss_Y0/article/details/134070316