【问题标题】:why vue watch only triggered once?为什么 vue watch 只触发一次?
【发布时间】:2019-03-21 08:11:52
【问题描述】:

为什么手表只触发一次?如下代码,当点击'sync'按钮时,id和text同时发生变化,但只触发了id() watch,需要再次点击'sync'按钮才能触发text() watch,为什么?

Vue.component('test-bar', {
  props: ['id', 'text'],
  template: `
      <div>
        <div>child: {{id}} {{text}}</div>
        <button @click="on_click">sync</button>
      </div>
      `,
  watch: {
    id() {
      this.$emit('update:id', this.id)
      // this.$emit('update:text', this.text) // !!! notice here. only when i added this line will trigger text() watch
    },
    text() {
      this.$emit('update:text', this.text)
    }
  },
  methods: {
    on_click() {
      this.id = 1
      this.text = 'child text'
    }
  }
})

new Vue({
  el: "#app",
  data: {
    id: 0,
    text: 'parent text',
  }
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/vue/2.5.17/vue.js"></script>
<div id="app">
  <test-bar :id.sync='id' :text.sync='text'></test-bar>
  <div>parent: {{id}} {{text}}</div>
</div>

【问题讨论】:

    标签: vue.js


    【解决方案1】:

    您不应更新props。当尝试更新一个道具时,Vue 会抛出一个错误并且你的流程会中断。所以在this.id = 1这行之后会抛出异常,下一行不会执行。执行此操作的正确方法是将 computed property 与 getter 和 setter 一起使用。

    类似的东西:

    Vue.component('test-bar', {
      props: ['id', 'text'],
      template: `
      <div>
        <div>child: {{childId}} {{childText}}</div>
        <button @click="on_click">sync</button>
      </div>
      `,
      computed: {
        childId: {
          get () {
            return this.id
          },
          set (value) {
            this.$emit('update:id', value)
          }
        },
        childText: {
          get () {
            return this.text
          },
          set (value) {
            this.$emit('update:text', value)
          }
        }
      },
      methods: {
        on_click() {
          this.childId = 1
          this.childText = 'child text'
        }
      }
    })
    

    这是一个 jsfiddle 工作 example

    一种更简单的方法是只发出事件而不观察变化

    on_click() {
      this.$emit('update:id', 1)
      this.$emit('update:text', 'child text')
    }
    

    JSfiddle example

    【讨论】:

      猜你喜欢
      • 2015-05-20
      • 2015-09-07
      • 2016-06-19
      • 1970-01-01
      • 1970-01-01
      • 2023-03-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多