debounce
export function debounce(callback, delay) {
let timerId;
return (event) => {
if (timerId) clearTimeout(timerId);
timerId = setTimeout(callback, delay, event);
};
}
- 클로저이기 때문에 timerId가 계속해서 보존된다.
- 만약 debounce로 이미 실행되고 있는 timeout이 있다면 끝낸다.
- 없다면 delay 시간 후에 콜백 함수를 실행한다.
- 즉, 이미 setTimeout 안에서 돌아가고 있는 함수가 있다면 취소 처리한다. 이것이 디바운스 핵심.
- 이때 궁금한 점은 만약 위 함수가 유틸 함수라면 debounce를 사용하고 있는 서로 다른 기능들끼리 timerId가 공유되지 않을까? 하는 걱정이 있었음.
- 함수가 호출될 때마다 새롭게 렉시컬 환경이 생성되기 때문에 각각의 id는 겹치지 않는다는 사실을 배우게 됨.
throttle
export function throttle(callback, delay) {
let timerId;
return (event) => {
if (timerId) return;
timerId = setTimeout(() => {
callback(event);
timerId = null;
},
delay,
event
);
};
}
- 마찬가지로 timerId가 계속 저장
- timeId 가 있으면 실행 안함
- delay만큼 지연된 후 콜백함수를 실행, timerId를 초기화한다.
- 즉,
RequestAnimationFrame
function autoSlide() {
const slider = document.querySelector('slider-element').shadowRoot;
let lastTime = null;
function step(timestamp) {
if (!lastTime) lastTime = timestamp;
const now = timestamp;
const elapsed = now - lastTime;
if (elapsed >= 3000) {
slideLeft(slider);
lastTime = now;
}
requestAnimationFrame(step);
}
requestAnimationFrame(step);
}