react使用Context方法实现组件通信(案例说明嵌套传值+详细用法总结)

前言

之前的文章我们介绍了在react中使用props实现组件通信,比如父子,祖孙通信,但是使用props一层层传递的时候还是很麻烦的,那么今天这篇文章就来介绍新的用法——使用Context实现组建通信

Context

在react官方文档中是这样解释的:Context 提供了一个无需为每层组件手动添加 props,就能在组件树间进行数据传递的方法。此处附上传送门Context-react
Context 设计目的是为了共享那些对于一个组件树而言是“全局”的数据,例如当前认证的用户、主题或首选语言。下面一起来看看如何使用Context实现组件通信

祖孙传值

最外层组件(祖组件):

  1. 引入父组件(hello.js),引入context中的MainContext
  2. 使用<MainContext.Provider value={this.state.arr}>提供服务进行传值,value就是要传的值
import React, {
    
     Component } from 'react'
import Hello from './hello'
import MainContext from './context'

export class Main extends Component {
    
    
    state = {
    
    
        // arr: [1, 2, 3],
        arr: 'hello',
        obj: {
    
    name: 'chaochao'}
    }
  render() {
    
    
    return (
      <div>
          <MainContext.Provider value={
    
    this.state.arr}>
                Main Page
                <Hello/>
          </MainContext.Provider>
      </div>
    )
  }
}

export default Main

孙组件:
上面祖组件已经使用MainContext.Provider进行传值了,那么在这里就不需要一层层传值,在孙组件中可以直接使用MainContext.Consumer组件进行接收
1.从context.js中引入MainContext
2.使用MainContext.Consumer进行取值
这样就可以成功在孙组件中拿到祖组件的值

import React, {
    
     Component } from 'react'
import MainContext from './context'

export class World extends Component {
    
    
  render() {
    
    
    return (
        <MainContext.Consumer>
        	{
    
    
				context => {
    
    
					return (
						<div>World Page --- {
    
    context}</div
					)
				}
			}
        </MainContext.Consumer>
    )
  }
}

export default World

除了使用MainContext.Consumer进行取值,这里还有一种方法:
可以使用static contextType = MainContext 或者 Hello.contextType = MainContext,这样就能直接是使用this.context获取到传入的值

export class Hello extends Component {
    
    
    // static contextType = MainContext
    render() {
    
    
        return (
            <div>Hello Page==={
    
    this.context}
                <World />
            </div>
        )
    }
}

Hello.contextType = MainContext // 等同于第二行代码的作用

嵌套传值

上面的例子是祖组件传值给孙组件组,孙组件中使用了MainContext.Consumer接收值,但是如果孙组件还要接收别的组件传过来的值,那么我们就要嵌套MainContext.Consumer进行接收
这里来举例说明一下:
新建一个userContext.js:

import React from 'react'
const UserContext = React.createContext()
export default UserContext

在祖组件中进行嵌套传值:

  1. 同时引入两个context的文件
  2. 注意看MainContext.Provider和UserContext.Provider进行嵌套传值
import React, {
    
     Component } from 'react'
import Hello from './hello'
import MainContext from './context'
import UserContext from './userContext'

export class Main extends Component {
    
    
    state = {
    
    
        // arr: [1, 2, 3],
        arr: 'hello',
        obj: {
    
    name: 'chaochao'}
    }
  render() {
    
    
    return (
      <div>
          <MainContext.Provider value={
    
    this.state.arr}>
              <UserContext.Provider value={
    
    this.state.obj}>
                Main Page
                <Hello/>
              </UserContext.Provider>
          </MainContext.Provider>
      </div>
    )
  }
}

export default Main

孙组件中:
1.也是要同时引入两个context
2. 接收值也需要进行嵌套,注意观察写法
这样就能就收到两个不同的值

import React, {
    
     Component } from 'react'
import MainContext from './context'
import UserContext from './userContext'

export class World extends Component {
    
    
  render() {
    
    
    return (
        // 函数式组件中比较推荐使用Consumer进行取值消费
        <MainContext.Consumer>
            {
    
    context => {
    
    
                return <UserContext.Consumer>
                    {
    
    user => {
    
    
                        console.log(context, user)
                        return (
                            <div>World Page --- {
    
    context} --- {
    
    user.name}</div>
                        )
                    }}
                </UserContext.Consumer>
            }}
        </MainContext.Consumer>
    )
  }
}

export default World

Context使用步骤总结

还是和之前一样,通过小案例来实现用法,祖组件传值给孙组件
新建context.js文件,用来使用context
context.js中内容:

import React from 'react'
// 创建一个 Context 对象,组件会从组件树中离自身最近的那个匹配的 Provider 中读取到当前的 context 值。
const MainContext = React.createContext('这里面可以设置默认值')

export default MainContext
// 传值使用Provider接收value属性,传递给消费组件
<MainContext.Provider value={
    
    /* 某个值 */}>

接收值的两种方法:

  1. 使用Context.Consumer(多用于函数式组件)
<MainContext.Consumer>
  {
    
    value => /* 基于 context 值进行渲染*/}
</MainContext.Consumer>
  1. 用Class.contextType挂载在class上,然后使用 this.context 来消费最近 Context 上的那个值。可以在任何生命周期中访问到它,包括 render 函数中。(多用于类组件)
static contextType = MainContext
// 或者
Hello.contextType = MainContext 
// 就可以直接用this.context访问了

本篇文章就到这里结束啦,如果对你有帮助的话,点赞关注支持一下谢谢~
后续还会给大家继续带来优质的前端内容~ 持续更新!!!

猜你喜欢

转载自blog.csdn.net/weixin_45745641/article/details/123489191