在 Vue 3 中,Composition API
是一种新的编写组件逻辑的方式,它通过 setup
函数提供了一种更灵活的方式来组织和复用代码。与传统的 Options API
相比,Composition API
更适合处理复杂的逻辑场景,尤其是在需要跨组件复用逻辑时。
以下是基于 Composition API
的父子组件传值的实现方式。
1. 父组件向子组件传递数据(Props)
示例代码
父组件(ParentComponent.vue)
<template><div><h1>父组件</h1><ChildComponent :message="parentMessage" /></div>
</template><script setup>
import { ref } from 'vue';
import ChildComponent from './ChildComponent.vue';// 定义父组件的数据
const parentMessage = ref('Hello from Parent!');
</script>
子组件(ChildComponent.vue)
<template><div><h2>子组件</h2><p>从父组件接收到的消息:{{ message }}</p></div>
</template><script setup>
// 接收父组件传递的 props
defineProps({message: {type: String,required: true,},
});
</script>
解析
- 父组件通过
ref
定义响应式数据,并通过v-bind
将其传递给子组件。 - 子组件使用
defineProps
来接收父组件传递的props
。
2. 子组件向父组件传递数据(Events)
示例代码
父组件(ParentComponent.vue)
<template><div><h1>父组件</h1><p>从子组件接收到的消息:{{ childMessage }}</p><ChildComponent @send-message="receiveMessage" /></div>
</template><script setup>
import { ref } from 'vue';
import ChildComponent from './ChildComponent.vue';// 定义父组件的数据
const childMessage = ref('');// 接收子组件传递的数据
const receiveMessage = (message) => {childMessage.value = message;
};
</script>
子组件(ChildComponent.vue)
<template><div><h2>子组件</h2><button @click="sendMessageToParent">发送消息给父组件</button></div>
</template><script setup>
import { defineEmits } from 'vue';// 定义触发事件的方法
const emit = defineEmits(['send-message']);const sendMessageToParent = () => {const message = 'Hello from Child!';emit('send-message', message); // 触发事件并传递数据
};
</script>
解析
- 子组件通过
defineEmits
定义可以触发的事件。 - 使用
emit
方法触发事件,并将数据传递给父组件。 - 父组件通过监听子组件的事件来接收数据。
3. 双向绑定(v-model)
示例代码
父组件(ParentComponent.vue)
<template><div><h1>父组件</h1><p>当前值:{{ inputValue }}</p><ChildComponent v-model="inputValue" /></div>
</template><script setup>
import { ref } from 'vue';
import ChildComponent from './ChildComponent.vue';// 定义父组件的数据
const inputValue = ref('');
</script>
子组件(ChildComponent.vue)
<template><div><h2>子组件</h2><input :value="modelValue" @input="updateValue" /></div>
</template><script setup>
import { defineProps, defineEmits } from 'vue';// 接收父组件传递的 props
const props = defineProps({modelValue: {type: String,required: true,},
});// 定义触发事件的方法
const emit = defineEmits(['update:modelValue']);// 更新父组件的值
const updateValue = (event) => {emit('update:modelValue', event.target.value);
};
</script>
解析
- 父组件通过
v-model
将inputValue
绑定到子组件。 - 子组件通过
defineProps
接收modelValue
,并通过$emit('update:modelValue', value)
更新父组件的值。
4. 跨层级组件传值(Provide/Inject)
示例代码
祖父组件(GrandParentComponent.vue)
<template><div><h1>祖父组件</h1><ParentComponent /></div>
</template><script setup>
import { provide, ref } from 'vue';
import ParentComponent from './ParentComponent.vue';// 提供共享数据
const sharedMessage = ref('Hello from GrandParent!');
provide('sharedMessage', sharedMessage);
</script>
父组件(ParentComponent.vue)
<template><div><h2>父组件</h2><ChildComponent /></div>
</template><script setup>
import ChildComponent from './ChildComponent.vue';
</script>
子组件(ChildComponent.vue)
<template><div><h3>子组件</h3><p>从祖父组件接收到的消息:{{ sharedMessage }}</p></div>
</template><script setup>
import { inject } from 'vue';// 注入共享数据
const sharedMessage = inject('sharedMessage');
</script>
解析
- 祖父组件通过
provide
提供数据。 - 子组件通过
inject
接收数据,无需经过中间层级。
总结
- 父传子 :使用
defineProps
。 - 子传父 :使用
defineEmits
和emit
。 - 双向绑定 :使用
v-model
和update:modelValue
。 - 跨层级传值 :使用
provide
和inject
。
Composition API
提供了更灵活和强大的方式来组织组件逻辑,特别是在复杂场景下。如果还有其他问题或需要更详细的示例,请随时补充说明!