vue3使用provide/inject实现全局变量功能,部分摆脱vuex

vue3新的provide/inject功能可以穿透多层组件,实现数据从父组件传递到子组件。

这时将所有需要使用的全局变量在根组件就provide,这样,所有的组件都能使用到这个变量。

如果需要变量是响应式的,就需要在provide的时候使用ref或者reactive包装变量。

for (let key in store) {
    let type = typeof store[key]
    if (type == 'function') {//这里是粗略的写法,目前当类型是函数时,直接provide
        app.provide(key, store[key])//这里的app是install函数中提供的app,其中包含了provide
    } else if (type == 'object') {//是对象时,使用reactive包装
        app.provide(key, reactive(store[key]))
    } else {//是其他值时,使用ref包装,这时调用需要使用.value
        app.provide(key, ref(store[key]))
    }
}

把上面的代码整和为vue3插件。这里定义一个createStore函数用来指示需要进行管理的全局变量。

/*
*  ./plug.js
*/
function createStore(store) {
    return {
        install: (app, options) => {//返回的对象中需要包含install函数。
            for (let key in store) {
                let type = typeof store[key]
                if (type == 'function') {
                    app.provide(key, store[key])
                } else if (type == 'object') {
                    app.provide(key, reactive(store[key]))
                } else {
                    app.provide(key, ref(store[key]))
                }
            }
        }
    }
}
export {
    createStore
}

在store文件夹中,我们可以像vuex一样调用createStore函数,然后导出这个函数返回的结果,这个结果需要在main.js中use。

import {createStore} from "./plug"
export default createStore({
    //这里是全局变量
    key1:'value1',
    key2:{
    	a:53,
    }
})

之后再main.js中像vuex一样use引用就行

import { createApp } from 'vue'
import App from './App.vue'
import store from  './store/index'
createApp(App).use(store).mount('#app')

使用时,只需要inject变量名就行。

let global_events = inject("global_events");

为什么这里不使用原先vue2那种this写法呢?因为在vue3中setup中的组合式API写法,已经不提倡继续使用this了。而且由于在执行 setup 时尚未创建组件实例,因此在 setup 选项中没有 this。

我们还可以借此实现全局的event系统,实现eventbus。下期将在此基础上实现event系统

你可能感兴趣的:(vue,前端,es6,javascript,vue.js)