Home > Article > Web Front-end > JavaScript topic three: anti-shake
Contents
Write at the end
(Related free learning recommendations: javascript video tutorial)
1. Why is anti-shake required
To this end, we give a sample code to understand how the event is triggered frequently:
We write an index.html file:
<meta> <meta> <meta> <title>Document</title> <title>debounce</title> <style> #wrapper { width: 100%; height: 200px; line-height: 200px; text-align: center; color: #fff; background-color: #444; font-size: 30px; } </style> <p></p> <script> var count = 1; var op = document.getElementById("wrapper"); function getUserAction() { op.innerHTML = count++; } op.onmousemove = getUserAction; </script>
It triggers nearly 100 times when sliding from the left to the right getUserAction
Function! Look at the following Gif:
Because this example is very simple, the browser can fully respond, but suppose:
This kind of interaction that puts too much pressure on the browser or server in an instant (a short period of time) needs to be optimized. In order to solve this problem, there are generally two solutions:
Their purpose is: Reduce the triggering frequency of a function to improve performance or avoid Waste of resources.
2. The principle of anti-shake
Today we will focus on the implementation of anti-shake.
The principle of anti-shake is: Even if you trigger an event, I will execute it only after n seconds of inactivity after the event is triggered. For example:
3s as the standard for anti-shake, then:
3. Implement an anti-shake by yourself
3.1 First Editionfunction debounce(func, wait) { var timer; return function () { clearTimeout(timer) timer = setTimeout(func, wait); }}If we want to use it, take the example in the first section as an example:
op.onmousemove = debounce(getUserAction, 2000);At this time You can test it again. When the event continues to occur, the event will only be triggered after 2 seconds of complete stop: Written here, as a requirement for some high-frequency events, it is over. Let’s take a look at its effect: 3.2 Second Edition As we all know, when a dom node triggers an event, this points to itself. In this example, it points to
op, but in this case: Let’s take a look at
var count = 1;var op = document.getElementById("op");function getUserAction() { op.innerHTML = count++; console.log('this', this); // 此时输出 Window...}op.onmousemove = debounce(getUserAction, 2000);function debounce(func, wait) { var timer; return function () { clearTimeout(timer) timer = setTimeout(func, wait); }}. After all, it has been wrapped by a layer of anonymous functions. This already points to window. In order to reduce the impact, we Try to fix it
function debounce(func, wait) { var timer; return function () { var _this = this; // 记录当前this clearTimeout(timer) timer = setTimeout(function(){ func.apply(_this); //将 func的this改为_this }, wait); }}Third EditionThe this pointing problem solved, our function is still not "perfect" enough, in JavaScript, the event processing function will provide the
event object , we call it e for short.
// 使用了 debouce 函数function getUserAction(e) { console.log(e); // undefined op.innerHTML = count++;};In order to ensure its authenticity, we will change the third version:
var count = 1;var op = document.getElementById("op");function getUserAction(e) { op.innerHTML = count++; console.log('e', e); // MouseEvent}op.onmousemove = debounce(getUserAction, 2000);function debounce(func, wait) { var timer; return function () { var _this = this; // 记录当前this var arg = arguments; // 记录参数 clearTimeout(timer) timer = setTimeout(function () { func.apply(_this, arg); //将 func的this改为_this }, wait); }}So far, we have added to the function while retaining the original capabilities of the Dom event as much as possible. With the anti-shake effect, it can solve most of our daily development anti-shake problems, but we need to be more "perfect"
4. Anti-shake advanced
4.1 Immediate executionThis requirement is: seconds blank period
second blank period behind
immediate The parameter determines whether it is executed immediately.
function debounce(func, wait, immediate) { var timer; return function () { var _this = this; var args = arguments; if (timer) clearTimeout(timer); // 常规流程,间隔内触发时清掉重置定时 if (immediate) { // 如果已经执行过,不再执行 var callNow = !timer; // 1. callNow 初始值是 true, 同步立即执行;随后 timer 才开始执行 timer = setTimeout(function(){ timer = null; // wait 期间,timer 是一个 ID 数字,所以 callNow 为 false,func 在此期间永远不会执行 }, wait) // wait 之后,timer 赋值 null,callNow 为 true,func 又开始立即执行。 if (callNow) func.apply(_this, args) } else { timer = setTimeout(function(){ func.apply(_this, args) }, wait); } }}Let’s take a look at its effect at this time: 4.2 Add simple verification
function debounce(func, wait, immediate) { var timer; // 检查函数 if (typeof func !== 'function') { throw new TypeError('Expected a function'); } // 保证wait存在 wait = +wait || 0; const debounced = function () { var _this = this; var args = arguments; if (timer) clearTimeout(timer); // 常规流程,间隔内触发时清掉重置定时 if (immediate) { // 如果已经执行过,不再执行 var callNow = !timer; // 如果不存在定时器,则callNow为true timer = setTimeout(function () { timer = null; // 为了保证之后的时效性,手动添加timer }, wait) // 因为不存在timer,证明是首次执行,所以直接调用 if (callNow) func.apply(_this, args) } else { timer = setTimeout(function () { func.apply(_this, args) }, wait); } } return debounced}
function debounce(func, wait, immediate) { var timer; // 检查函数 if (typeof func !== 'function') { throw new TypeError('Expected a function'); } // 保证wait存在 wait = +wait || 0; const debounced = function () { var _this = this; var args = arguments; if (timer) clearTimeout(timer); // 常规流程,间隔内触发时清掉重置定时 if (immediate) { // 如果已经执行过,不再执行 var callNow = !timer; // 如果不存在定时器,则callNow为true timer = setTimeout(function () { timer = null; // 为了保证之后的时效性,手动添加timer }, wait) // 因为不存在timer,证明是首次执行,所以直接调用 if (callNow) func.apply(_this, args) } else { timer = setTimeout(function () { func.apply(_this, args) }, wait); } } const cancel = function(){ clearTimeout(timer); timer = null; } const pending = function(){ return timer !== undefined; } debounced.cancel = cancel; debounced.pending = pending; return debounced}Let’s take a look at the effect: Write Even if this simple anti-shake method is OK, it is indeed not perfect. If you have any suggestions for improvement, please leave a message in the comment area~
Related free learning recommendations: javascript (Video)
The above is the detailed content of JavaScript topic three: anti-shake. For more information, please follow other related articles on the PHP Chinese website!