当前页面 A.vue
<template>
<div>
<a @click="funA()">点击</a>
<B ref="componentB"></B>
</div>
</template>
<script>
import B from "./B.vue"; //引入组件B
export default {
components:{
B
},
methods:{
funA(){
this.$refs.componentB.funB() //调用B.vue里面的funB方法
}
}
}
</script>
组件B.vue
<template>
<div>
<basic-modal ref="modalA" :show="isShow">
<div slot="modal-body">
<p v-for="item in options">{{item}}</p>
</div>
</basic-modal>
</div>
</template>
<script>
import BasicModal from "./BasicModal.vue"; //引入BasicModal组件
export default {
components:{
BasicModal
},
data () {
return {
options:[],
isShow: false,
}
},
methods:{
funB(){
this.options = ['a','b','c','d'],
this.isShow=true
}
}
}
</script>
带slot的组件 BasicModal.vue
<template>
<div>
<template v-if="show">
<div>
<slot name="modal-body">
</slot>
</div>
</template>
</div>
</template>
<script>
export default {
props:{
show:{
type: Boolean,
default: false
}
},
}
</script>
问题描述: A.vue页面引用B.vue组件,B.vue组件页面引用BasicModal.vue组件页面,BasicModal.vue里面用了slot。B.vue插入到插槽里面的dom是动态的,导致A.vue页面首次渲染完成(或F5重新刷新A.vue页面)后,首次手动触发<a>标签的点击事件会出现B.vue里面的options变量没有被渲染出来的bug,但options变量也被赋值不为空。往后再触发点击事件就不会再复现这个bug。
解决方案:触发A.vue页面的点击事件后调用vm.$forceUpdate(), 迫使 Vue 实例重新渲染。注意它仅仅影响实例本身和插入插槽内容的子组件,而不是所有子组件。
最终B.vue
<template>
<div>
<basic-modal ref="modalA" :show="isShow">
<div slot="modal-body">
<p v-for="item in options">{{item}}</p>
</div>
</basic-modal>
</div>
</template>
<script>
import BasicModal from "./BasicModal.vue"; //引入BasicModal组件
export default {
components:{
BasicModal
},
data () {
return {
options:[],
isShow: false,
}
},
methods:{
funB(){
this.options = ['a','b','c','d'],
this.isShow=true
this.$nextTick(() => { //强制vue重新渲染
this.$forceUpdate();
});
}
}
}
</script>