React中的context

context出现的缘由:react中,数据都是自顶而下的传递方式,如果在顶层state中存储数据,如果在不借助第三方的状态管理框架的情况下,想要在自组件中过去数据,就必须一层层传递下去,但是有时候传递的某些层级的中用不到这些数据,这时候层级越深越可怕。

正式因为有了上面的这种场景,官方提供了context机制,通过context就可以在自组件里获取祖先组件里的值,而不需层层传递,在react16.3之前context只是官方的实验性API,官方是不推荐开发者使用的,由于有很多开发者使用,所以官方在react16.3版本中发布了最新的context API,新的API,更加易用。

在新的context API中 React提供了一个createContext的方法,该方法返回了一个包含Provider,Consumer对象

举个例子:

// content.jsx
import { createContext } from 'react';
// createContext:用来创建context,有一个参数是默认值,返回值是Provider和Consumer对象
// Provider:用于提供context组件
// Consumer:用于获取context组件
export const { Provider, Consumer } = createContext({ a:1 })

在App.jsx顶层组件中的使用Provider,同时传递一个value进去。

// App.jsx
import React, { Component } from 'react';
import { Provider } from './content'
import Parent from "./parent"

class App extends Component{
    state = { a: 2 };
    
    render() {
        return (
            <div>
                <Provider value={this.state} >
                    <Parent/>
                </Provider>
            </div>
        )
    }
}
export default App;

在child组件中利用Consumer就可以获取到App中传递的数据,Consumer需要使用一个函数作为子元素来接受传递的数据,函数的参数就是上面传递下来的数据。

// child.js
import React, { PureComponent } from 'react';
import { Consumer } from './content'

class Child extends PureComponent{
    render(){
        return (
            <Consumer>
                {context => <p>{context.a}</p>}
            </Comsumer>
        )
    }
}
export default Child

上面的三个文件的数据流传递关系:App -> Parent -> Child 这样我们在顶层的数据,就可以在child这个自组件中获取到。

注意:只有在上层组件没有提供Provider组件的时候,下层组件Consumer才会直接使用createContext函数中的那个初始化参数。但是如果有Consumer组件,但是value没有值或者值是undefind/null也是不会使用初始化参数的

react context 到 React-redux的进化

当我们要传递的数据变多的场景中,都要调用Consumer的话,会显得很冗余,所以我们要将Consumer封装起来。

import React from 'react';
import { Consumer } from './context'

export default mapState => {
    return WrappedComponent => {
        const Component = props => (
           <Consumer>
           {
            value => {
                let mappedProps = mapState(value);
                return <WrappedComponent {...props} {...mappedProps}/>
            }
           }
           </Consumer>
        );
        Component.displayName = `connect(${WrappedComponent.displayName || WrappedComponent.name || "Component"})`;
        return Component
    }
}

connect方法传传入一个mapState方法,mapState是context的value映射方法,当调用connect方法后吗,会返回一个高阶函数工厂,将传入的WrappedComponent组件用Comsumer包裹住,获取到Comsumer中传递过来的value,计算出最终的mappedProps属性,然后把mappedProps传递给组件WrappedComponent。

引用:
  • https://blog.csdn.net/jjx0224/article/details/88242842
  • https://github.com/reduxjs/react-redux
  • https://www.redux.org.cn/docs/react-redux/api.html
  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值