Mic*_*sky 3 vue.js vuejs3 vue-composition-api
我有一个Component A和一个嵌套的Component B。组件 A加载一个字符串列表,组件 B有一个元素,当组件 A完成加载SELECT时会填充该元素。此时应选择第一个选项。此后,当选择其他选项时,组件 B应发出带有选择数据的事件,以便组件 A “知道”选择了哪个选项。由于A应该控制B,因此该选项通过 props 传递回B。SELECTupdate
在我下面的实现中,组件 B 只接收选择的初始值,并且在加载列表时,它会成功填充,但控制属性不会更改 selectedOption 值。所以,这是行不通的。
实施这个的正确方法是什么?
组分A:
<template>
<component-b :list="list" :selected="selected" @update="onUpdate">
</template>
<script lang="ts">
import { defineComponent, ref } from 'vue';
export default defineComponent({
setup: () => {
const list = ref<string[]>([]);
const selected = ref('');
load().then(data => { // some load function returning a promise
selected.value = data[0]; // data is never empty
list.value = data;
});
const onUpdate = (data: string) => selected.value = data;
return { list, selected, onUpdate };
}
})
</script>
Run Code Online (Sandbox Code Playgroud)
组分B:
<template>
<select v-model="selectedOption" @change="onChange">
<option v-for="item of props.list" />{{item}</option>
</select>
</template>
<script lang="ts">
import { defineComponent, ref, PropType } from 'vue';
export default defineComponent({
emits: ['update'],
props: {
selected: {
type: String
},
list: {
type: Object as PropType<String[]>
}
}
setup: (props, { emit }) => {
const selectedOption = ref(props.selected); // this doesn't work when loading is finished and props are updated
const onChange = () => emit('update', selectedOption.value);
return { selectedOption, onChange, props }
}
});
</script>
Run Code Online (Sandbox Code Playgroud)
谢谢。
在 中ComponentB.vue,selectedOption'sref仅初始化为 的值props.selected,但它本身不是反应性的(即,ref不会props.selected自动跟踪):
const selectedOption = ref(props.selected); // not reactive to props.selected
Run Code Online (Sandbox Code Playgroud)
您可以通过watchEffect将任何新值复制到selectedOption(每当props.selected更改时自动发生)来解决此问题:
watchEffect(() => selectedOption.value = props.selected);
Run Code Online (Sandbox Code Playgroud)
旁注: setup()不需要显式返回,props因为它们已经可按名称用于模板。您的模板可以更改为:
<!-- <option v-for="item of props.list">{{ item }}</option> -->
reference props directly by name
<option v-for="item of list">{{ item }}</option>
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
8393 次 |
| 最近记录: |