Open yizihan opened 6 years ago
在浏览器DOM事件里面,有一些事件会随着用户的操作不间断触发。比如:重新调整浏览器窗口大小(resize)、浏览器页面滚动(scroll)、鼠标移动(mousemove)。也就是说用户在触发这些浏览器操作时,脚本里绑定的对应的事件处理方法,这个方法就会不停的触发。
有的时候如果事件处理方法比较庞大,DOM操作比较复杂,还不断的触发此类事件就会造成性能上的损失,导致用户体验下降(UI反应慢、浏览器卡死等)。所以通常我们会给相应事件添加延迟执行的逻辑。
延迟调用onresize的回调函数
let Count = 0; let timer = null function addCount() { console.log(Count++)} window.onresize = function () { clearTimeout(timer); timer = setTimeout(function() { addCount(); }, 100) }
改善建议:产生了一个全局变量timer;为了解决这个问题,需要使用闭包。
使用一个闭包函数throttle,把timer放在内部并且返回延时处理函数,这样timer变量对外是不可见的,但是内部延时函数触发时还可以访问到timer变量。
let Count = 0; function addCount() { console.log(Count++)} function throttle(fn, delay) { var timer = null; // 返回匿名函数,产生闭包 return function () { clearTimeout(timer); timer = setTimeout(function() { fn(); }, delay) } } window.onresize = throttle(addCount, 100)
throttle被调用后返回的回调函数才是真正的onresize触发时需要调用到的函数。
改善建议:如果用户不断的resize浏览器窗口大小,这时延迟处理函数一次都不会执行。 新功能:当用户触发resize的时候应该在某段时间内至少触发一次;判断条件是取当前的时间毫秒数,每次调用把当前的时间和上一次调用时间相减,然后判断差值如果大于某段时间就直接触发,否则还是走timeout的延迟逻辑。
添加固定时间执行回调函数的逻辑
let Count = 0; function addCount() { console.log(Count++)} function throttle(fn, delay, atlest) { var timer = null; // 记录上一次延时事件的标识 var previous = null; // 记录上一次执行时间的标识 return function () { var now = +new Date(); // 毫秒字符串 if(!previous) previous = now; // 将previous重置到当前时间 if (atlest && (now - previous) > atlest) { // 当时间差大于设定的时间段时 fn(); // 强制执行一次 previous = now; // 再次将previous重置到当前时间 } else { clearTimeout(timer); // 清除上次的延时事件 timer = setTimeout(function() { // 重新设定延时事件 fn(); }, delay) } } } window.onresize = throttle(addCount, 500, 1000)
参考文章: JavaScript 节流函数 Throttle 详解
在浏览器DOM事件里面,有一些事件会随着用户的操作不间断触发。比如:重新调整浏览器窗口大小(resize)、浏览器页面滚动(scroll)、鼠标移动(mousemove)。也就是说用户在触发这些浏览器操作时,脚本里绑定的对应的事件处理方法,这个方法就会不停的触发。
有的时候如果事件处理方法比较庞大,DOM操作比较复杂,还不断的触发此类事件就会造成性能上的损失,导致用户体验下降(UI反应慢、浏览器卡死等)。所以通常我们会给相应事件添加延迟执行的逻辑。
方案一
延迟调用onresize的回调函数
方案二
使用一个闭包函数throttle,把timer放在内部并且返回延时处理函数,这样timer变量对外是不可见的,但是内部延时函数触发时还可以访问到timer变量。
throttle被调用后返回的回调函数才是真正的onresize触发时需要调用到的函数。
方案三
添加固定时间执行回调函数的逻辑
参考文章: JavaScript 节流函数 Throttle 详解