深入学习Vue nextTick的用法及原理


Posted in Javascript onOctober 08, 2019

Vue.nextTick是Vue官方给我们提供的一个API(方法),作用是在下次DOM更新循环结束之后执行延迟回调。在修改数据之后立即使用这个方法,获取更新后的DOM;

那么我们的理解是:当数据发生变化之后,DOM视图并不会立即更新,如果我们在发生变化之后立马去获取某个节点或者某个节点的值,很有可能结果就是undefined;因为Vue实现响应式并不是数据发生变化之后DOM立即变化,而是按一定的策略进行DOM的更新;

来看一个小demo:

App.vue 

<template>
 <div id="app">
    <div ref="message">{{msg}}</div>
    <div v-if="msg1">{{msg1}}</div>
    <button @click="changeMsg">Change the Message</button>
 </div>
</template>

<script>
export default {
 name: 'App',
 data(){
  return {
   msg:"Hello Vue",
   msg1: '',
  }
 },
 methods:{
  changeMsg(){
   this.msg='hello world';
   this.msg1=this.$refs.message.innerHTML;
    console.log("更新DOM之前:"+this.msg1)
  }
 }
}
</script>

<style>
#app {
 font-family: 'Avenir', Helvetica, Arial, sans-serif;
 -webkit-font-smoothing: antialiased;
 -moz-osx-font-smoothing: grayscale;
 text-align: center;
 color: #2c3e50;
 margin-top: 60px;
}
</style>

深入学习Vue nextTick的用法及原理

我们通过运行代码能够看到当我们不在this.$nextTick方法里面进行DOM操作的时候,this.$refs.message.innerHTML的值存储的还是之前的初始值;

修改代码:

App.vue

<template>
 <div id="app">
    <div ref="message">{{msg}}</div>
    <div v-if="msg1">{{msg1}}</div>
    <button @click="changeMsg">Change the Message</button>
 </div>
</template>

<script>
export default {
 name: 'App', 
 data(){
  return {
   msg:"Hello Vue",
   msg1: '',
  }
 },
 methods:{
  changeMsg(){
   this.msg='hello world';
   // this.msg1=this.$refs.message.innerHTML;
   // console.log("更新DOM之前:"+this.msg1)
    this.$nextTick(()=>{
     this.msg1=this.$refs.message.innerHTML;
     console.log("更新DOM之后:"+this.msg1)
    })
  }
 }
}
</script>

<style>
#app {
 font-family: 'Avenir', Helvetica, Arial, sans-serif;
 -webkit-font-smoothing: antialiased;
 -moz-osx-font-smoothing: grayscale;
 text-align: center;
 color: #2c3e50;
 margin-top: 60px;
}
</style>

深入学习Vue nextTick的用法及原理

修改代码之后我们可以发现,使用this.$nextTick很容易的就接收到了更新后的值,正如官网解释:在下次DOM更新循环结束之后执行延迟回调。在修改数据之后立即使用这个方法,获取更新后的DOM;

再来修改代码对比一下:

App.vue

<template>
 <div id="app">
    <div ref="message">{{msg}}</div>
    <div v-if="msg1">{{msg1}}</div>
    <button @click="changeMsg">Change the Message</button>
 </div>
</template>

<script>
export default {
 name: 'App', 
 data(){
  return {
   msg:"Hello Vue",
   msg1: '',
  }
 },
 methods:{
  changeMsg(){
   this.msg='hello world';
   this.msg1=this.$refs.message.innerHTML;
    console.log("更新DOM之前:"+this.msg1)
    this.$nextTick(()=>{
     this.msg1=this.$refs.message.innerHTML;
     console.log("更新DOM之后:"+this.msg1)
    })
  }
 }
}
</script>

<style>
#app {
 font-family: 'Avenir', Helvetica, Arial, sans-serif;
 -webkit-font-smoothing: antialiased;
 -moz-osx-font-smoothing: grayscale;
 text-align: center;
 color: #2c3e50;
 margin-top: 60px;
}
</style>

深入学习Vue nextTick的用法及原理

经过修改代码,我们现在可以很容易看出来this.$nextTick(callback)的作用,callback是回调函数也就是我们要进行操作DOM的事情;

应用场景:

在vue的生命周期钩子函数created()中进行DOM操作的时候一定要把DOM操作放入到this.$nextTick()中;

因为在created钩子函数触发的时候,DOM是没有进行渲染的;DOM没有进行渲染,然后进行DOM操作无疑是徒劳的;

所以我们在created中进行DOM操作的时候,一定要将DOM操作放入到this.$nextTick()中;

与之相反的是mounted,因为当触发mounted的时候,DOM的挂载和渲染都已经完成了,所以在mounted中进行DOM操作是不会有任何问题的;

因为DOM更新是异步的,像v-if指令判断增删DOM元素,我们在方法中给变量赋值的时候,如果不使用this.$nextTick(),我们很有可能拿到的还是初始值,如果想拿到更新后的值,需要使用this.$nextTick()方法

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
jquery关于页面焦点的定位(文本框获取焦点时改变样式 )
Sep 10 Javascript
JS和jquery获取各种屏幕的宽度和高度的代码
Aug 02 Javascript
超简单JS二级、多级联动的简单实例
Feb 18 Javascript
javascript常用函数归纳整理
Oct 31 Javascript
jQuery实现自定义事件的方法
Apr 17 Javascript
关于JS中的apply,call,bind的深入解析
Apr 05 Javascript
基于JavaScript实现跳转提示页面
Sep 24 Javascript
Bootstrap的popover(弹出框)2秒后定时消失的实现代码
Feb 27 Javascript
JS计算两个时间相差分钟数的方法示例
Jan 10 Javascript
Node.js Event Loop各阶段讲解
Mar 08 Javascript
使用Vue实现调用接口加载页面初始数据
Oct 28 Javascript
vue 动态创建组件的两种方法
Dec 31 Vue.js
jQuery 筛选器简单操作示例
Oct 02 #jQuery
jQuery 查找元素操作实例小结
Oct 02 #jQuery
JavaScript 作用域实例分析
Oct 02 #Javascript
JavaScript Dom 绑定事件操作实例详解
Oct 02 #Javascript
JavaScript 面向对象基础简单示例
Oct 02 #Javascript
Nautil 中使用双向数据绑定的实现
Oct 02 #Javascript
详解element-ui级联菜单(城市三级联动菜单)和回显问题
Oct 02 #Javascript
You might like
php 获取select下拉列表框的值
2010/05/08 PHP
PHP 中检查或过滤IP地址的实现代码
2011/11/27 PHP
基于thinkPHP实现的微信自定义分享功能示例
2016/09/23 PHP
CI框架中类的自动加载问题分析
2016/11/21 PHP
PHP chop()函数讲解
2019/02/11 PHP
php libevent 功能与使用方法详解
2020/03/04 PHP
accesskey 提交
2006/06/26 Javascript
用于判断用户注册时,密码强度的JS代码
2009/01/01 Javascript
jquery ready函数源代码研究
2009/12/06 Javascript
Javascript 获取链接(url)参数的方法[正则与截取字符串]
2010/02/09 Javascript
深入理解JavaScript系列(18):面向对象编程之ECMAScript实现
2015/03/05 Javascript
谈谈对JavaScript原生拖放的深入理解
2016/09/20 Javascript
jQuery表单验证简单示例
2016/10/17 Javascript
通过AngularJS实现图片上传及缩略图展示示例
2017/01/03 Javascript
jQuery中ztree 点击文本框弹出下拉框的实例代码
2017/02/05 Javascript
jQuery插件form-validation-engine正则表达式操作示例
2017/02/09 Javascript
简单快速的实现js计算器功能
2017/08/17 Javascript
JS模拟超市简易收银台小程序代码解析
2017/08/18 Javascript
vue 路由嵌套高亮问题的解决方法
2018/05/17 Javascript
angularJS开发注意事项
2018/05/26 Javascript
vue 中基于html5 drag drap的拖放效果案例分析
2018/11/01 Javascript
详解Vue3.0 前的 TypeScript 最佳入门实践
2019/06/18 Javascript
Python3.2模拟实现webqq登录
2016/02/15 Python
讲解Python的Scrapy爬虫框架使用代理进行采集的方法
2016/02/18 Python
Python并发编程协程(Coroutine)之Gevent详解
2017/12/27 Python
python实现nao机器人手臂动作控制
2019/04/29 Python
Python的垃圾回收机制详解
2019/08/28 Python
HTML5的hidden属性兼容老浏览器的方法
2014/04/23 HTML / CSS
UGG雪地靴荷兰官网:UGG荷兰
2016/09/09 全球购物
365 Tickets英国:全球景点门票
2019/07/06 全球购物
农村党员一句话承诺
2014/05/30 职场文书
幼儿生日活动方案
2014/08/27 职场文书
听证通知书
2015/04/24 职场文书
创业计划书之电动车企业
2019/10/11 职场文书
Spring Boot DevTools 全局配置学习指南
2022/03/31 Java/Android
MySQL的存储过程和相关函数
2022/04/26 MySQL