๋ฐ˜์‘ํ˜•

 

๋””๋ฐ”์šด์Šค๋Š” input ์ด๋ฒคํŠธ์—(๋ฆฌ์•กํŠธ์—์„  onChange), ์Šค๋กœํ‹€์€ scroll ์ด๋ฒคํŠธ์— ์ž์ฃผ ์‚ฌ์šฉ๋œ๋‹ค.

 

๋””๋ฐ”์šด์Šค๋Š” ์•„๋ฌด๋ฆฌ ๋งŽ์€ ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•ด๋„ ๋งˆ์ง€๋ง‰ ์ด๋ฒคํŠธ๋งŒ ์‹คํ–‰ํ•˜๋Š” ๋ฐ˜๋ฉด, ์Šค๋กœํ‹€์€ ์ ์–ด๋„ `n` ๋ฐ€๋ฆฌ์ดˆ ๋งˆ๋‹ค ์ •๊ธฐ์ ์œผ๋กœ ๊ธฐ๋Šฅ ์‹คํ–‰์„ ๋ณด์žฅํ•˜๋Š” ์ ์ด ๊ฐ€์žฅ ํฐ ์ฐจ์ด์ . ์ฐธ๊ณ ๋กœ Lodash ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ์— ๋””๋ฐ”์šด์Šค์™€ ์Šค๋กœํ‹€ ๋ฉ”์„œ๋“œ๊ฐ€ ํฌํ•จ๋˜์–ด ์žˆ๋‹ค.

_.debounce(func, wait, [options])
_.throttle(func, wait, [options])   

 

๋””๋ฐ”์šด์Šค | Debounce


์ด๋ฒคํŠธ๊ฐ€ ์—ฐ์†์ ์œผ๋กœ ๋ฐœ์ƒํ•ด๋„ ํ•ญ์ƒ ๋งˆ์ง€๋ง‰ ์ด๋ฒคํŠธ๋งŒ ์ฒ˜๋ฆฌ
์ด๋ฒคํŠธ๋ฅผ ๊ทธ๋ฃนํ™”ํ•˜์—ฌ ํŠน์ • ์‹œ๊ฐ„์ด ์ง€๋‚œ ํ›„ ํ•˜๋‚˜์˜ ์ด๋ฒคํŠธ๋งŒ ๋ฐœ์ƒํ•˜๋„๋ก ํ•˜๋Š” ๊ธฐ์ˆ 

 

๋””๋ฐ”์šด์Šค ์˜ˆ์‹œ ์ฝ”๋“œ โ–ผ

function debounce(callback, ms) {
  let timeout;
  return function (...args) {
    clearTimeout(timeout);
    timeout = setTimeout(() => {
      callback(...args);
    }, ms);
  };
}

// input์— ํƒ€์ดํ•‘์„ ๋ฉˆ์ถ”๊ณ  ms์ดˆ ํ›„์— ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ. ํƒ€์ดํ•‘(์ด๋ฒคํŠธ ๋ฐœ์ƒ) ๋„์ค‘์—” ์•„๋ฌด์ผ๋„ ์ผ์–ด๋‚˜์ง€ ์•Š์Œ
input.addEventListener(
  'input',
  debounce((e) => console.log(e.target.value), 1000),
);
// addEventListener ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•œ ์ˆœ๊ฐ„ debounce ํ•จ์ˆ˜๊ฐ€ ์‹คํ–‰๋˜๊ณ  ๋‚ด๋ถ€ ํ•จ์ˆ˜๋ฅผ ๋ฐ˜ํ™˜ํ•จ
// ์ฆ‰ ์ด๋ฒคํŠธ ํ•ธ๋“ค๋Ÿฌ์—” debounce ํ•จ์ˆ˜๊ฐ€ ๋ฐ˜ํ™˜ํ•œ ๋‚ด๋ถ€ ํ•จ์ˆ˜๊ฐ€ ํ• ๋‹น๋จ
// ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด ๋‚ด๋ถ€ ํ•จ์ˆ˜ ์ธ์ž (...args)์— event ๊ฐ์ฒด๊ฐ€ ์ „๋‹ฌ๋จ

 

ํƒ€์ดํ•‘์„ ๋ฉˆ์ถ˜ ์‹œ์ (์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜์ง€ ์•Š๋Š” ์‹œ์ )๋ถ€ํ„ฐ ms์ดˆ(์œ„ ์˜ˆ์ œ์—์„  1์ดˆ) ํ›„์— ์ด๋ฒคํŠธ๋ฅผ ์ฒ˜๋ฆฌํ•œ๋‹ค.

 

  • ์ด๋ฒคํŠธ(์ด ์˜ˆ์ œ์—์„  ํƒ€์ดํ•‘)๊ฐ€ ๊ณ„์† ๋ฐœ์ƒํ•˜๋ฉด `clearTimeout`์„ ํ†ตํ•ด ์ด์ „ ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ ๋กœ์ง์„ ์ทจ์†Œํ•œ๋‹ค.
  • ์ด๋ฒคํŠธ๊ฐ€ ์—ฐ์†์ ์œผ๋กœ ๋ฐœ์ƒํ•ด๋„ ํ•ญ์ƒ ๋งˆ์ง€๋ง‰ ์ด๋ฒคํŠธ ๋ฐœ์ƒ ํ›„ `ms`์ดˆ(์œ„ ์˜ˆ์‹œ์—์„  1์ดˆ)๊ฐ€ ์ง€๋‚ฌ์„ ๋•Œ ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ(callback ์‹คํ–‰)๊ฐ€ ์‹œ์ž‘๋œ๋‹ค.
  • ์ž์ฃผ ์‚ฌ์šฉ๋˜๋Š” ๊ณณ: 
    • ๋ฆฌ์‚ฌ์ด์ฆˆ
    • `<input>` ํƒœ๊ทธ์— ์ž…๋ ฅํ•œ API ์š”์ฒญ ์ œํ•œ

 

์Šค๋กœํ‹€ | Throttle


์Šค๋กœํ‹€ : ์ผ์ • (์‹œ๊ฐ„)๊ฐ„๊ฒฉ์œผ๋กœ ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ
์ด๋ฒคํŠธ๋ฅผ ์ผ์ •ํ•œ ์ฃผ๊ธฐ๋งˆ๋‹ค ๋ฐœ์ƒํ•˜๋„๋ก ํ•˜๋Š” ๊ธฐ์ˆ 

 

์Šค๋กœํ‹€ ์˜ˆ์‹œ ์ฝ”๋“œ โ–ผ

function throttle(callback, ms) {
  let timeout;
  return function (...args) {
    if (!timeout) {
      timeout = setTimeout(() => {
        callback(...args);
        timeout = null;
      }, ms);
    }
  };
}

// input์ฐฝ์— ํƒ€์ดํ•‘(์ด๋ฒคํŠธ)์„ ๊ณ„์† ํ•˜๋”๋ผ๋„ ํ•ญ์ƒ ms์ดˆ ๊ฐ„๊ฒฉ์œผ๋กœ ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ
input.addEventListener(
  'input',
  throttle((e) => console.log(e.target.value), 1000),
);
// addEventListener ์ฝ”๋“œ๋ฅผ ์‹คํ–‰ํ•œ ์ˆœ๊ฐ„ throttle ํ•จ์ˆ˜๊ฐ€ ์‹คํ–‰๋˜๊ณ  ๋‚ด๋ถ€ ํ•จ์ˆ˜๋ฅผ ๋ฐ˜ํ™˜ํ•จ
// ์ฆ‰ ์ด๋ฒคํŠธ ํ•ธ๋“ค๋Ÿฌ์—” throttle ํ•จ์ˆ˜๊ฐ€ ๋ฐ˜ํ™˜ํ•œ ๋‚ด๋ถ€ ํ•จ์ˆ˜๊ฐ€ ํ• ๋‹น๋จ
// ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด ๋‚ด๋ถ€ ํ•จ์ˆ˜ ์ธ์ž (...args)์— event๊ฐ์ฒด๊ฐ€ ์ „๋‹ฌ๋จ

 

์ด๋ฒคํŠธ(์œ„ ์˜ˆ์ œ์—์„  ํƒ€์ดํ•‘)๊ฐ€ ์ง€์†์ ์œผ๋กœ ๋ฐœ์ƒํ•ด๋„ ํ•ญ์ƒ ์ง€์ •ํ•œ ms์ดˆ ๋งˆ๋‹ค ์ด๋ฒคํŠธ์— ๋Œ€ํ•œ ์ฒ˜๋ฆฌ๊ฐ€ ์ด๋ค„์ง„๋‹ค.

 

  • ์ฒซ ๋ฒˆ์งธ ์ด๋ฒคํŠธ ์ดํ›„ ๋‹ค๋ฅธ ์ด๋ฒคํŠธ๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด, ํ•ด๋‹น ์ด๋ฒคํŠธ๋Š” ํƒ€์ž„์•„์›ƒ ID๊ฐ€ ์—†๋Š” ๊ฒฝ์šฐ์—๋งŒ ์ฒ˜๋ฆฌ๋œ๋‹ค.
  • `ms`์ดˆ๊ฐ€ ์ง€๋‚œ ํ›„ ์ด์ „ ์ด๋ฒคํŠธ ์ฒ˜๋ฆฌ๋ฅผ ์™„๋ฃŒํ•˜๋ฉด, ํƒ€์ž„์•„์›ƒ ID๊ฐ€ `null`๋กœ ๋ณ€๊ฒฝ๋˜๊ณ  ์ด ์‹œ์ ๋ถ€ํ„ฐ ์ƒˆ๋กœ์šด ์ด๋ฒคํŠธ๋ฅผ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ๋Š” ์ƒํƒœ๊ฐ€ ๋œ๋‹ค.
  • ์ด๋ฒคํŠธ๊ฐ€ ์—ฐ์†์ ์œผ๋กœ ๋ฐœ์ƒํ•˜๋Š” ๊ฒฝ์šฐ, ๊ฐ ์ด๋ฒคํŠธ๋Š” `ms`์ดˆ ๊ฐ„๊ฒฉ์œผ๋กœ ์ฒ˜๋ฆฌ๋œ๋‹ค.
  • ์ž์ฃผ ์‚ฌ์šฉ๋˜๋Š” ๊ณณ: 
    • ๋ฌดํ•œ ์Šคํฌ๋กค
    • ์• ๋‹ˆ๋ฉ”์ด์…˜ ํ”„๋ ˆ์ž„

 

์ฝ”๋“œํŽœ


์ฝ”๋“œํŽœ ํ•˜๋‹จ ์ฝ˜์†” ์ฐฝ์—์„œ ์–ด๋–ป๊ฒŒ ์ถœ๋ ฅ๋˜๋Š”์ง€ ์ง์ ‘ ํ™•์ธํ•ด๋ณผ ์ˆ˜ ์žˆ๋‹ค. 

See the Pen debounce & throttle by ColorFilter (@colorfilter) on CodePen.

 

 

๋ ˆํผ๋Ÿฐ์Šค


 


๊ธ€ ์ˆ˜์ •์‚ฌํ•ญ์€ ๋…ธ์…˜ ํŽ˜์ด์ง€์— ๊ฐ€์žฅ ๋น ๋ฅด๊ฒŒ ๋ฐ˜์˜๋ฉ๋‹ˆ๋‹ค. ๋งํฌ๋ฅผ ์ฐธ๊ณ ํ•ด ์ฃผ์„ธ์š”
๋ฐ˜์‘ํ˜•