1.父子组件数据传递
1.1父子组件传值概念
父子组件传值是指:数据从父组件流向子组件,或者从子组件反馈给父组件的过程。这是组件间通信的一种基本方式,对于构建可复用和模块化的界面至关重要。通过这个思想,Vue应用程序中的组件可以高效地共享和交换数据,实现复杂的交互逻辑。
1.2子传父 ComponentA组件
为了实现子组件向父系传值,这里我们要创建一个ComponentA子组件。子组件中,script逻辑部分创建三部分内容,一个数组以及两个方法,template展示部分主要用循环输出渲染,展示数组绑定的按钮(下文会详细讲)。
在script部分,首先我们声明一段数组对象categories用于展示,每个对象包含id和name两个值;其次声明一个defineEmits宏函数,目的是在子组件的setup中,暴露自定义的点击事件itemClick;最后声明一个触发方法btnClick,包含一个形参item,方法调用前面的defineEmits的函数,触发itemClick事件并向其传递item对象。
在template部分,首先这里我们主要用了v-for循环控制渲染,渲染categories数组中的每个对象;其次我们用动态绑定实现,渲染的值是categories对象中的name属性;最后用事件绑定前面的触发方法btnClick,实现点击触发并传值的效果。
<!-- 子组件 触发自定义事件 -->
<!-- 子传父 -->
<script setup>
import { ref ,reactive, defineEmits} from 'vue'
const info = ref('子组件A 的信息')
const categories = reactive ([
{id:1,name:'手机'},
{id:2,name:'电脑'},
{id:3,name:'电脑配件'},
{id:4,name:'手机配件'},
{id:5,name:'衣帽'}
])
// defineEmits方法,自定义事件(可定义多个,事件名用逗号分隔,放到数组中)
const myEmits = defineEmits(['itemClick'])
const btnClick = (item)=>{
// 触发自定义事件,附带上一个分类对象
myEmits('itemClick',item)
}
</script>
<template>
<h2>{{ info }}</h2>
<!-- 生成按钮 动态绑定 categories的name属性 -->
<input type="button" v-for="item in categories" :value="item.name" @click="btnClick(item)">
</template>
1.3父传子 ComponentB组件
实现父系组件向子系组件传值,我们创建一个ComponentB子组件。子组件中,script逻辑部分创建一个方法,template展示部分主要从父系组件渲染。
在script部分,首先我们声明一个defineProps函数,其中声明了形参postTitle和otherInfo两部分内容,这两部分都是从父系组件中传递过来的。
在template部分,只渲染输出postTitle和otherInfo两部分的标签即可,其中的数据由父系组件传递。
<script setup>
import {ref,defineProps} from 'vue'
// 父传子
const info = ref('子组件B的信息')
// 调用defineProps函数 传进来一个数组 数组中的字符串 就是用来接收父组件的传值
defineProps(['postTitle','otherInfo'])
</script>
<template>
<h1>{{ info }}</h1>
<ul>
<li>{{ postTitle }}</li>
<li>{{ otherInfo }}</li>
</ul>
</template>
<style scoped>
</style>
1.4父系组件HomeView
最后一部分,我们来实现父系组件HomeView,首先在script逻辑部分针对非全局组件进行引入;其次我们声明ComponentA中打印输出的方法callback;最后声明ComponentB中所需要的两个常量,一个是字符串postTitle,一个是对象otherInfo。
template渲染部分,我们直接写已经引入的两个组件标签名ComponentA与ComponentB。其中,组件A事件绑定方法itemClick打印输出,组件B动态绑定前面声明的两个常量。
<script setup>
// 非全局组件 要在 script setup 中导入
import ComponentB from '@/components/ComponentB.vue';
import ComponentA from '@/components/ComponentA.vue';
import {ref} from 'vue'
const postTitle = ref('hello world')
const otherInfo = ref({
name: 'zhangsan',
age: 18
})
const callback = (data)=>{
console.log('out->data',data)
}
</script>
<template>
<main>
<!-- <TheWelcome /> -->
<!-- 使用组件 类似html标签<标签名></> -->
<ComponentA @itemClick="callback"></ComponentA>
<ComponentB :postTitle="postTitle" :otherInfo="otherInfo"></ComponentB>
</main>
</template>
2.展示效果
这样当我们点击组件A的按钮时,控制台可以打印从itemClick事件传递的数据,组件B的数据也由父系组件传递给子组件渲染,简化重复的代码。
这次先讲到这里,下次讲计算属性的相关知识。(本人水平有限,希望大家多多指正!)