解决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 相关文章推荐
pjblog中的UBBCode.js
Apr 25 Javascript
jquery.artwl.thickbox.js  一个非常简单好用的jQuery弹出层插件
Mar 01 Javascript
jquery隐藏标签和显示标签的实例
Nov 11 Javascript
javascript按位非运算符的使用方法
Nov 14 Javascript
js 自动播放的实例代码
Nov 19 Javascript
浅谈JavaScript 浏览器对象
Jun 03 Javascript
js变量提升深入理解
Sep 16 Javascript
Jquery EasyUI Datagrid右键菜单实现方法
Dec 30 Javascript
Easyui使用Dialog行内按钮布局的实例
Jul 27 Javascript
BootStrap TreeView使用实例详解
Nov 01 Javascript
select获取下拉框的值 下拉框默认选中方法
Feb 28 Javascript
vue、react等单页面项目部署到服务器的方法及vue和react的区别
Sep 29 Javascript
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
php 获取客户端的真实ip
2009/11/30 PHP
php设计模式 Command(命令模式)
2011/06/26 PHP
php函数serialize()与unserialize()用法实例
2014/11/06 PHP
用PHP去掉文件头的Unicode签名(BOM)方法
2017/06/22 PHP
jQuery maxlength文本字数限制插件
2010/04/16 Javascript
导航跟随滚动条置顶移动示例代码
2013/09/11 Javascript
Backbone.js 0.9.2 源码注释中文翻译版
2015/06/25 Javascript
理解JavaScript事件对象
2016/01/25 Javascript
深入理解JS addLoadEvent函数
2016/05/20 Javascript
JS控制页面跳转时未请求要跳转的地址怎么回事
2016/10/14 Javascript
SpringMVC简单整合Angular2的示例
2017/07/31 Javascript
详解Node.js模板引擎Jade入门
2018/01/19 Javascript
vue实例中data使用return包裹的方法
2018/08/27 Javascript
Vue中UI组件库之Vuex与虚拟服务器初识
2019/05/07 Javascript
JavaScript将数组转换为链表的方法
2020/02/16 Javascript
[58:00]DOTA2-DPC中国联赛 正赛 PSG.LGD vs Elephant BO3 第二场 2月7日
2021/03/11 DOTA
复习Python中的字符串知识点
2015/04/14 Python
python连接MySQL数据库实例分析
2015/05/12 Python
利用Python中SocketServer 实现客户端与服务器间非阻塞通信
2016/12/15 Python
python递归删除指定目录及其所有内容的方法
2017/01/13 Python
python os.listdir按文件存取时间顺序列出目录的实例
2018/10/21 Python
使用python进行拆分大文件的方法
2018/12/10 Python
解决python3 HTMLTestRunner测试报告中文乱码的问题
2018/12/17 Python
Python实现微信小程序支付功能
2019/07/25 Python
python 实现在无序数组中找到中位数方法
2020/03/03 Python
Python ini文件常用操作方法解析
2020/04/26 Python
Python实现LR1文法的完整实例代码
2020/10/25 Python
新秀丽拉杆箱美国官方网站:Samsonite美国
2016/07/25 全球购物
英格兰橄榄球商店:England Rugby Store
2016/12/17 全球购物
学用政策心得体会
2014/09/10 职场文书
2014年统战工作总结
2014/12/09 职场文书
孙振耀退休感言
2015/08/01 职场文书
寒假致家长的一封信
2015/10/10 职场文书
小学大队长竞选稿
2015/11/20 职场文书
2019年教师节祝福语精选,给老师送上真诚的祝福
2019/09/09 职场文书
python Polars库的使用简介
2021/04/21 Python