【Vue2/3】使用Provide/Inject 依赖注入跨组件通信

历史小剧场

什么东西,都有使用年限,比如大米、王朝。
不同的是,大米的年限看得见,王朝的年限看不见。看不见,却依然存在。对于气数,崇祯是不信的,开始不信。等到崇祯十四年,怕什么来什么,后院起火,前院也起火,卢象昇死了,辽东白了,中原乱了,信了。

前言

  • 在组件嵌套多层情况下,不论组件嵌套多深,父组件都可以通过provide来提供数据,子组件或孙组件或曾孙组件使用inject注入数据。
  • 还有,在兄弟组件之间传值也很方便。

Vue2-OptionsAPI使用

什么是optionsAPI?

我的理解就是,像一个对象里面的属性方法都算是optionsAPI,所以,在Vue2中都是以这样的格式来编写代码的。

案例

App.vue

export default {
  provide: {
    // 丧失响应式
    name: '李四'
  },
  ...
}

Father.vue

<template>
    <div>
        <TestProvideOptionsAPIChild />
    </div>
</template>

<script lang="ts">
import TestProvideOptionsAPIChild from './TestProvideOptionsAPIChild.vue';

export default {
    name: "TestProvideOptionsAPIFather",
    components: {
        TestProvideOptionsAPIChild
    },
}
</script>

<style lang="scss" scoped>

</style>

TestProvideOptionsAPIChild.vue

<!--  -->
<template>
    <div>
        <h1>{{ name }}</h1>
    </div>
</template>

<script lang="ts">
export default {
    name: "TestProvideOptionsAPIChild",
    inject: ["name"],
}
</script>

<style lang="scss" scoped>

</style>

Vue3-CompositionAPI使用

在组合式API中,我们需要在setup()函数期间调用,或者在setup 语法糖里使用,必须从vue显示导入provide/inject方法

案例

App.vue

export default {
  setup() {
    const name = ref<string>("张三")

    const changeName = () => {
      name.value = '王五'
    }

    // 使用readonly包裹,使其不可在子组件被修改
    provide('name', readonly(name))
    provide('age', 20)
    provide('sex', '男')
    provide('hobby', '跑步')
    provide("changeName", changeName)
  }
  ...
}

Father.vue

<!--  -->
<template>
    <div>
        <TestProvideChild />
    </div>
</template>

<script setup lang="ts">
import TestProvideChild from './TestProvideChild.vue'
</script>

<style lang="scss" scoped>

</style>

TestProvideChild.vue

<!-- TestProvideChild.vue -->
<template>
    <div>
        <h1>{{ name }}</h1>
        <h1>{{ age }}</h1>
        <h1>{{ sex }}</h1>
        <h1>{{ hobby }}</h1>
        <button @click="changeName">修改姓名</button><br>
        <button @click="injectChangeName">子组件修改姓名</button><br>
    </div>
</template>

<script setup lang="ts">
import { inject } from 'vue';

// inject() 方法第二个参数为默认值
let name = inject('name', ''),
      age = inject('age', 0),
      sex = inject('sex', 'unknown'),
      hobby = inject('hobby', ""),
      changeName = inject('changeName', () => {});

const injectChangeName = () => {
    name.value = '心潮'
}
</script>

<style lang="scss" scoped>

</style>

【默认规则】当我们使用provide/inject来实现组件通信的时候,必须在父组件中去修改数据,在子组件不可以自行去修改数据,所以,我们可以在父组件中使用provide传递数据时可以将数据使用readonly()方法去包裹。如此,在子组件中去修改就修改不了了,否则的话,是可以修改的。这样,对以后项目的数据维护不友好

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值