1. 程式人生 > >React.CreateContext

React.CreateContext

跨元件傳遞的內容元件,該元件匯出兩個物件Provider 提供資料, Consumer, 消費資料

簡單的使用

// 建立上下文
let {Provider, Consumer} = React.createContext()

// 假設我們有很多個元件,我們只需要在父元件使用Provider提供資料,然後我們就可以在子元件任何位置使用Consumer拿到資料,不存在跨元件的問題
// 提供資料
import React, {Component} from 'react';
import ReactDOM from 'react-dom';
let {Provider, Consumer} = React.createContext()
// 父元件
function Parent (props) { return ( <div> <div>Parent: </div> <Son></Son> </div> ) } // 子元件 function Son (props) { return ( <div> <div>Son: </div> <Child></Child
>
</div> ) } // 孫子元件 function Child (props) { return ( <Consumer> {value => <div> value: {value} </div>} </Consumer> ) } ReactDOM.render(<Provider value="1"> <Parent /> </Provider
>
, document.getElementById('root'));

簡單理解

思路:

1.自己新建兩個元件Provider,Consumer

2.Provider有一個引數value

3.在Provider元件內遍歷子元件,

4.如果元件是Consumer的話,就返回一個元件,並將value作為值傳遞給新建立的子元件Consumer

import React, {Component} from 'react';
import ReactDOM from 'react-dom';

class Provider extends Component{
    /**
     * 處理渲染子元件Consumer
     * @param {object} obj 需要迴圈的子元件 
     * @param {anything} value 定義的任何值
     */
    initChild (obj, value) {
        if (Array.isArray(obj)) {
            // 這裡應該是遞迴呼叫,實現深度組建的處理
            // 這裡僅作為簡單的理解(其實是我寫不出來,哈哈哈哈)
            obj = obj.map(child => {
                return this.initChild(child, value)
            })
        } else {
            // 如果元件是Consumer 就克隆一個新的元件返回,
            // 因為這裡拿到的Consumer是一個物件,並不能直接使用,所以需要使用 React.cloneElement克隆一個新的物件返回
            if (obj.type.name === 'Consumer') return React.cloneElement(obj, {value})
        }

        return obj
    }
    render () {
        // 拿到子元素
        let {children, value} = this.props
        children = this.initChild(children, value)

        // 先判斷子元件是一個還是陣列,假如是陣列,則遍歷處理
        return (
            <React.Fragment>
                {children}
            </React.Fragment>
        )

    }
}

class Consumer extends Component{
    render () {
        return this.props.children(this.props.value)
    }
}
// 這裡使用自己寫的元件
ReactDOM.render(<Provider value="1">
    <Consumer>
        {
            value => <div>{value}</div>
        }
    </Consumer>
    <div>1-1</div>
    <Consumer>
        {value => `2-${value}`}
    </Consumer>
</Provider>, document.getElementById('root'));

總結

一定要敢寫,雖然不一定寫的出來,但是肯定會有收穫。。。。。。