解决vue自定义指令导致的内存泄漏问题


Posted in Javascript onAugust 04, 2020

vue的自定义指令是一个比较容易引起内存泄漏的地方,原因就在于指令通常给元素绑定了事件,但是如果忘记了解绑,就会产生内存泄漏的问题。

看下面代码:

directives: {
  scroll: {
  inserted (el, cb) {
   // 不是元素节点 || 未设置回调函数
   if (el.nodeType !== 1 || !cb) return
   let direct = 'down'
   let rollHeight = 0

   let getScrollEventTarget = (target) => {
   while (target.nodeType === 1 && target.tagName !== 'BODY' && el.tagName !== 'HTML') {
    var overflowY = getComputedStyle(target).overflowY
    if (overflowY === 'scroll' || overflowY === 'auto') {
    return target
    }
    target = target.parentNode
   }
   return window
   }

   let targetNode = getScrollEventTarget(el)

   let scrollListener = () => {
   if (targetNode.scrollTop > rollHeight) {
    direct = 'down'
   } else {
    direct = 'up'
   }
   rollHeight = targetNode.scrollTop
   cb.value(rollHeight, direct)
   }

   el.unbindEventListener = () => {
   targetNode.removeEventListener('scroll', scrollListener)
   }
   targetNode.addEventListener('scroll', scrollListener)
  },
   // unbind (el) {
   // if (el.unbindEventListener) {
   // el.unbindEventListener()
   // }
  // }
  }
 }

起初,我忘记了些注释的unbind方法,导致出现了内存泄漏,给元素绑定的scroll方法,会一直存在内存里。

导致出的情况,就是比如我进了页面滚动到第3页,出去,再点一个页面,当滚动到第4页时,将会请求2次,一次是上个页面的第4页,一次是本次页面的第4页,当你退出,再进一个页面,当滚动到第5页时,将会请求3次(上上页,上页和本页),这就是典型的事件未解绑导致的内存泄漏。

所以需要给元素解绑,好在vue指令提供了unbind钩子函数,

但是这里依然有个技术巧点就是:

1、我们scroll的元素可能是绑定的元素的父级等等,需要一层一层往上找

2、就是解绑的时候我们也需要找到那个父级元素等等,然后还需要remove对应的方法,那么肯定不可能在unbind里再写一次,所以就可以在insert钩子函数里,给el绑定一个解绑事件el.unbindEventListener,在unbind钩子函数里直接调用即可。

以上这篇解决vue自定义指令导致的内存泄漏问题就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
浏览器无法运行JAVA脚本的解决方法
Jan 09 Javascript
解决AJAX中跨域访问出现'没有权限'的错误
Aug 20 Javascript
修复IE9&safari 的sort方法
Oct 21 Javascript
jquery中获得元素尺寸和坐标的方法整理
May 18 Javascript
用JS实现轮播图效果(二)
Jun 26 Javascript
js中数组的常用方法小结
Dec 30 Javascript
javascript 日期相减-在线教程(附代码)
Aug 17 Javascript
Vue 实现一个命令式弹窗组件功能
Sep 25 Javascript
layer弹出层倒计时关闭的实现方法
Sep 27 Javascript
浅探express路由和中间件的实现
Sep 30 Javascript
24行JavaScript代码实现Redux的方法实例
Nov 17 Javascript
如何让vue长列表快速加载
Mar 29 Vue.js
vue中的v-model原理,与组件自定义v-model详解
Aug 04 #Javascript
详解JS深拷贝与浅拷贝
Aug 04 #Javascript
vue addRoutes路由动态加载操作
Aug 04 #Javascript
vue+element使用动态加载路由方式实现三级菜单页面显示的操作
Aug 04 #Javascript
Vue登录拦截 登录后继续跳转指定页面的操作
Aug 04 #Javascript
vue 解决uglifyjs-webpack-plugin打包出现报错的问题
Aug 04 #Javascript
浅谈在vue-cli3项目中解决动态引入图片img404的问题
Aug 04 #Javascript
You might like
JAVA/JSP学习系列之七
2006/10/09 PHP
php将会员数据导入到ucenter的代码
2010/07/18 PHP
ThinkPHP框架实现的MySQL数据库备份功能示例
2018/05/24 PHP
PHP实现的DES加密解密类定义与用法示例
2020/11/02 PHP
利用PHP内置SERVER开启web服务(本地开发使用)
2021/03/09 PHP
跨浏览器的设置innerHTML方法
2006/09/18 Javascript
javascript web对话框与弹出窗口
2009/02/22 Javascript
jquery插件 autoComboBox 下拉框
2010/12/22 Javascript
jQuery动态设置form表单的enctype值(实现代码)
2013/07/04 Javascript
jquery将一个表单序列化为一个对象的方法
2014/01/03 Javascript
jQuery使用fadein方法实现渐出效果实例
2015/03/27 Javascript
javascript实现根据汉字获取简拼
2016/09/25 Javascript
vuejs+element-ui+laravel5.4上传文件的示例代码
2017/08/12 Javascript
详解element-ui中form验证杂记
2019/03/04 Javascript
使用Vue.observable()进行状态管理的实例代码详解
2019/05/26 Javascript
解决Vue打包后访问图片/图标不显示的问题
2019/07/25 Javascript
写一个Vue loading 插件
2020/11/09 Javascript
[42:20]Winstrike vs VGJ.S 2018国际邀请赛淘汰赛BO3 第二场 8.23
2018/08/24 DOTA
python网络编程学习笔记(四):域名系统
2014/06/09 Python
python通过BF算法实现关键词匹配的方法
2015/03/13 Python
python实现黑客字幕雨效果
2018/06/21 Python
python3.7.0的安装步骤
2018/08/27 Python
python ftplib模块使用代码实例
2019/12/31 Python
PyCharm取消波浪线、下划线和中划线的实现
2020/03/03 Python
pymysql之cur.fetchall() 和cur.fetchone()用法详解
2020/05/15 Python
如何基于Python代码实现高精度免费OCR工具
2020/06/18 Python
Python 利用OpenCV给照片换底色的示例代码
2020/08/03 Python
解决Pymongo insert时会自动添加_id的问题
2020/12/05 Python
CSS3实现精美横向滚动菜单按钮
2017/04/14 HTML / CSS
英国儿童家具专卖店:GLTC
2016/09/24 全球购物
美国购买和销售礼品卡平台:Raise
2017/01/13 全球购物
公司财务工作总结的自我评价
2013/11/23 职场文书
室内设计专业毕业生求职信
2014/05/02 职场文书
关于倡议书的范文
2015/04/29 职场文书
水浒传读书笔记
2015/06/25 职场文书
什么是clearfix (一文搞清楚css清除浮动clearfix)
2023/05/21 HTML / CSS