先简单的总结一下,后面有一个示例。
父组件:
1. 需要给子组件定义一个引用名
const mychild = ref(null); //名字随意
2 .传递方式是直接使用标签:
<子组件 ref="引用名(mychild)" :数据名="父组件数据名" :方法名="父组件方法名" /?
3. 调用和接收子组件 (子组件需要使用defineExpose):
引用名(mychild).value.子组件数据名
引用名(mychild).value.子组件方法名()
子组件:
1. 接收父组件的数据和方法,需要定义一个defineProps,假设对象名=props:
let props = defineProps({
数据名: {
type: Object, //也可是String等,跟父组件的数据类型一致
default: ()=>{}
},
方法名:{
type: Function
}
});
2. 调用父组件方法,用上一步的defineProps对象直接调用:
props.父组件方法名()
3. 子组件要传值和传方法给父组件,需要使用defineExpose()方法暴露给父组件:
defineExpose({子组件数据名, 子组件方法名})
示例:
父组件,只有一个按钮,用于测试调用子组件的方法,和接收子组件的数据。
子组件,1. 有一个表格显示来自父组件的数据。 2.一个按钮,用于测试调用父组件的方法。
直接贴上完整代码,我已经做了非常详细的注释:
父组件Parent.vue:
<template>
<div style="border: solid 2px black;">
<h2>我是父组件</h2>
<input type="button" value="点我调用子组件方法" @click="testChild" />
<br />
<div style="margin: 10px; background-color: lightgray;">
<child ref="mychild" :dataTochild="dataTochild" :parentFunc="parentFunc"/>
</div>
</div>
</template>
<script lang="ts" setup>
import {reactive,ref} from 'vue'
//region 传给子组件使用的数据和方法 begin
定义子组件的引用 (ref="")
const mychild = ref(null);
定义在父组件的方法和数据
通过下面的方式,分别传递给子组件
<child ref="mychild" :dataTochild="dataTochild" :parentFunc="parentFunc"/>
const parentFunc=()=>{
console.log("我是父组件的方法")
}
const dataTochild = reactive({
time: Date(),
info:{
name:"admin",
sex:"男"
}
})
//region 传给子组件使用的数据和方法 end
//region 定义在父组件,用于测试父组件调用子组件的方法,和接收来自子组件的数据 begin
const testChild=()=>{
console.log("test from child!");
mychild.value.childFunc();
console.log(mychild.value.dataToParent)
}
//region 定义在父组件,用于测试父组件调用子组件的方法,和接收来自子组件的数据 end
</script>
<script lang="ts" >
import child from '../components/child.vue'
</script>
子组件Child.vue:
<template>
<h3>我是子组件</h3>
<table border="1px">
<tr>
<th colspan="2">
<span>下面的数据来自父组件</span>
</th>
</tr>
<tr>
<th>姓名</th>
<th>性别</th>
</tr>
<tr>
<td><span>{{dataTochild.info.name}}</span></td>
<td><span>{{dataTochild.info.sex}}</span></td>
</tr>
<tr>
<td colspan="2"><span>{{dataTochild.time}}</span></td>
</tr>
<tr>
<td colspan="2"><input type="button" value="点我调用父组件方法" @click="testParent" /></td>
</tr>
</table>
</template>
<script setup lang="ts">
import {ref} from 'vue'
//region 给父组件调用的方法和数据 begin
定义完成后,用defineExpose()暴露给父组件
const childFunc = ()=>{
console.log("我是子组件的方法");
};
const dataToParent = ref("我是子组件的数据");
defineExpose({
childFunc,dataToParent
});
//region 给父组件调用的方法和数据 end
//region 接收自父组件的数据 begin
let props = defineProps({
dataTochild : {
type: Object,
default: ()=>{}
},
parentFunc:{
type: Function
}
});
//region 接收自父组件的数据 end
//region 定义在子组件,用于测试子组件调用父组件的方法 begin
const testParent=()=>{
console.log("test from parent!");
props.parentFunc()
}
//region 定义在子组件,用于测试子组件调用父组件的方法 end
</script>
测试结果: