首页 > 解决方案 > 基于文本搜索创建/销毁 Vue 组件

问题描述

我有以下内容App.vue

<template>
    <div id="app">
        <input type="text" v-model="term">
        <hello-world text="Button 1" v-if="term === ''"></hello-world>
        <hello-world v-else text="Button 2"></hello-world>
    </div>
</template>

<script>
import HelloWorld from '@/components/HelloWorld'

export default {
    name: 'app',
    data() {
        return {
            term: ''
        }
    },
    components: {
        HelloWorld
    }
}
</script>

这是HelloWorld.vue

<template>
    <div>
        <button>{{ text }}</button>
    </div>
</template>

<script>
export default {
    props: {
        text: String
    },
    created() {
        console.log('Created')
    },
    destroyed() {
        console.log('Destroyed')
    }
}
</script>

所以,当我输入一些东西时,第一个组件应该被销毁,第二个组件应该被创建。但是,不会发生这样的事情。组件既不会被销毁也不会被创建。

好像v-if没有触发created()&destroyed()功能。请帮我解决一下这个。

标签: javascriptvue.jscomponents

解决方案


Vue 使用虚拟 dom 方法。因此,它是在比较虚拟树,而不是识别结构的变化(oldNode.type === newNode.type)。当它发生时,Vue 会更新相同的组件,而不是销毁旧节点并创建一个新节点。

尝试强制 Vue 检测虚拟树更改,避免使用具有相同标签名称并由v-if指令控制的兄弟姐妹。

参考:

https://medium.com/@deathmood/how-to-write-your-own-virtual-dom-ee74acc13060

Vue.component('hello-world', {
  props: {
    text: String
  },
  created() {
    console.log('Created')
  },
  destroyed() {
    console.log('Destroyed')
  },
  template: "<button>{{ text }}</button>"
});

var app = new Vue({
  el: "#app",
  data() {
    return {
      term: ''
    }
  }
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>

<div id="app">
  <input type="text" v-model="term">
  <span><hello-world v-if="!term" text="Button 1"></hello-world></span>
  <span><hello-world v-if="term" text="Button 2"></hello-world></span>
</div>


推荐阅读