React-lazyLoad、Fragment和Context

1. lazyLoad

  • 当没有使用懒加载时,每次进入页面,都会一次性加载所有组件,如果遇到网络不好的情况,很容易影响用户体验

  • 例如下面的页面在初始化时就一次性加载了所有NaviLink的组件,后续的每次访问具体某一组件时都不用再去发送请求
    React-lazyLoad、Fragment和Context_第1张图片

  • 使用懒加载,可以在只有用户点击或者访问了某一组件时才进行加载,减轻页面压力,给用户良好的使用体验
    React-lazyLoad、Fragment和Context_第2张图片

  • 经过测试发现,使用了懒加载的组件,在跳转时是需要重新请求的

  • 而没有使用懒加载的组件,在访问时,则是不需要发送请求的

  • 使用懒加载必不可少的还需要一个loading组件,用来在网络情况不好时,给予用户更好的体验
    React-lazyLoad、Fragment和Context_第3张图片

  • 使用Suspense组件包裹所有路由组件(一般是包裹在Routes组件外侧),并给Suspensefallback属性传递一个用于在组件不能及时加载时,页面需要展示的组件或者虚拟DOM,统称为Loading组件

  • Loading组件不能设置为懒加载

2. Fragment

  • 在不使用组件时,return 返回的组件必须有一个根组件,一般是一个
    , 否则编译无法通过
  • 当然也可以是一个空标签<>,但是空标签是没有办法指定key的,可以,方便在后续逻辑处理(比如遍历的时候,每一个结构都要有唯一的key)中定位
    React-lazyLoad、Fragment和Context_第4张图片
  • 如果每一个组件内部都有一个多余根组件
    ,当页面组件变多以后,因为多余的根组件的原因,组件层级就会变得越来越复杂
  • 使用包裹,可以避免层级复杂的问题,也可以使结构具其他属性,比如有唯一的key
    React-lazyLoad、Fragment和Context_第5张图片

3. Context

一种组件间通信方式,常用于【祖组件】与【后代组件】间通信
对于类式组件
  • 祖组件要是想给孙组件传递数据,只需要在公共位置创建一个Context,解构出内部的Provider
const MyContext = React.createContext()
  • 在祖组件内部,通过Provider的value属性写明自己要传递的数据(对象或者字符串),包裹想要传递的组件的父组件或者某一上级组件
<Provider value={{username,age}}>
		<B/>
</Provider>
  • 在想要接收数据的组件内声明自己要接收的Context,就可以从自己身上的Context属性上拿到某一上级传输的数据
//声明接收context
	static contextType = MyContext
  • 完整示例:(Context的声明必须在公共位置,即组件可以引用到的地方,可以建立一个专门存放Context的文件夹,然后引入)
import React, { Component } from 'react'
import './index.css'

//创建Context对象
const MyContext = React.createContext()
const {Provider} = MyContext
export default class A extends Component {

	state = {username:'tom',age:18}

	render() {
		const {username,age} = this.state
		return (
			<div className="parent">
				<h3>我是A组件</h3>
				<h4>我的用户名是:{username}</h4>
				<Provider value={{username,age}}>
					<B/>
				</Provider>
			</div>
		)
	}
}

class B extends Component {
	render() {
		return (
			<div className="child">
				<h3>我是B组件</h3>
				<C/>
			</div>
		)
	}
}

class C extends Component {
	//声明接收context
	static contextType = MyContext
	render() {
		const {username,age} = this.context
		return (
			<div className="grand">
				<h3>我是C组件</h3>
				<h4>我从A组件接收到的用户名:{username},年龄是{age}</h4>
			</div>
		)
	}
} 
对于函数式组件
  • 函数式组件没有this,所以无法获取自身的Context,但是函数式组件可以从Context身上解构出一个ConsumerConsumer内部有一个形参是value的方法,可以解析出被传输的数据
import React, { Component } from 'react'
import './index.css'

//创建Context对象
const MyContext = React.createContext()
const {Provider,Consumer} = MyContext
export default class A extends Component {

	state = {username:'tom',age:18}

	render() {
		const {username,age} = this.state
		return (
			<div className="parent">
				<h3>我是A组件</h3>
				<h4>我的用户名是:{username}</h4>
				<Provider value={{username,age}}>
					<B/>
				</Provider>
			</div>
		)
	}
}

class B extends Component {
	render() {
		return (
			<div className="child">
				<h3>我是B组件</h3>
				<C/>
			</div>
		)
	}
}
function C(){
	return (
		<div className="grand">
			<h3>我是C组件</h3>
			<h4>我从A组件接收到的用户名:
			<Consumer>
				{value => `${value.username},年龄是${value.age}`}
			</Consumer>
			</h4>
		</div>
	)
}
注意: 在应用开发中一般不使用Context,一般都使用它的封装react插件

你可能感兴趣的:(React,react.js,前端,前端框架)