关于Vue.nextTick()的使用

前言:不当心发现线上一个bug,看了下代码,了解到由于用Vue.nextTick的场景不对,在此作个记录。html

1、bug重现

具体场景是,修改文件夹名称时,弹出一个修更名称的弹出框vue

clipboard.png

此时文件名“啦啦啦”会带到编辑文件夹的弹出框中。修改保存后,文件名变成“啦啦啦123”,而后再次修改文件夹名,结果:异步

clipboard.png

此时为何文件名没有带过去?this

2、代码逻辑

经过查看代码了解到 编辑文件夹 弹出框是一个子组件,父组件触发修改文件名的事件时,经过 folderToBeRenamed 传递新的数据spa

this.$nextTick(() => {
   this.folderToBeRenamed = newFolderName
})

子组件再经过props 获取 folderToBeRenamed调试

并用 watch 监听code

watch: {
    folderToBeRenamed () {
      this.folderName = this.folderToBeRenamed.folder_name
    }
 }

folderName就是子组件要获取的数据,看起来好像有道理,但是为何只起到一次监听做用?经过调试发现,只有第一次点击修改文件名,watch里的事件会执行;后续无论folderToBeRenamed是否改变都不会执行watch里的事件了。htm

3、了解Vue.nextTick()

先看下官网的解释事件

clipboard.png

有点难懂o(╯□╰)oip

看到知乎上的解释:

HTML: <div id="testCount" v-html="message"></div>

//改变数据
vm.message = 'changed'

//想要当即使用更新后的DOM。这样不行,由于设置message后DOM尚未更新
console.log(document.getElementById('testCount').innerHTML) // 并不会获得'changed'

//这样能够,nextTick里面的代码会在DOM更新后执行
Vue.nextTick(function(){
    console.log(document.getElementById('testCount').innerHTML) //能够获得'changed'
})

因此 vue的nextTick的做用相似setTimeout,再添加一个新的空的异步事件,执行完异步事件后调用callback。

因此回到咱们前面的bug,能够明白,子组件只感觉到folderToBeRenamed的一次变化,就至关于for循环里的setTimeout

for(var i = 0; i < 3; i++) {
   setTimeout(function() {
       console.log('timeout' + i);
   })
}

最后输出的i都是3,也就是只能感觉到i从0变为3 此次变化。

4、修改bug

这里的逻辑原本是比较简单的,父组件传值,子组件直接获取就能够了。为何须要父组件用Vue.nextTick(),子组件用watch监听,我也不太清楚。由于本身对Vue.nextTick()用法也不太熟,因此在此记录,谨防踩坑_(:з」∠)_

相关文章
相关标签/搜索