JavaScript

IntersectionObserver, MutationObserver, ResizeObserver

presentKey 2024. 6. 16. 22:56

๐Ÿšฉ IntersectionObserver

https://developer.mozilla.org/ko/docs/Web/API/Intersection_Observer_API

ํŠน์ • ์š”์†Œ๊ฐ€ ๋ทฐํฌํŠธ ๋˜๋Š” ๋‹ค๋ฅธ ํŠน์ • ์š”์†Œ์™€ ๊ต์ฐจํ•˜๋Š”์ง€๋ฅผ ๋น„๋™๊ธฐ์ ์œผ๋กœ ๊ฐ์ง€ํ•  ์ˆ˜ ์žˆ๊ฒŒ ํ•ด์ค€๋‹ค. 

 

๊ธฐ์กด์—๋Š” scroll ์ด๋ฒคํŠธ๋ฅผ ํ†ตํ•ด ๋‘ ์š”์†Œ ์‚ฌ์ด์˜ ๊ฐ€์‹œ์„ฑ์„ ๊ฐ์ง€ํ–ˆ์ง€๋งŒ, IntersectionObserver๋Š” ๊ด€์ฐฐ ๋Œ€์ƒ ์š”์†Œ๊ฐ€ ๋ทฐํฌํŠธ์— ๋“ค์–ด์˜ค๊ฑฐ๋‚˜ ๋‚˜๊ฐˆ ๋•Œ๋งŒ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•œ๋‹ค. ์ด ๊ณผ์ •์€ ๋น„๋™๊ธฐ์ ์œผ๋กœ ์ด๋ฃจ์–ด์ง€๋ฏ€๋กœ, ๋ฉ”์ธ ์Šค๋ ˆ๋“œ์˜ ์ž‘์—…์„ ๋ฐฉํ•ดํ•˜์ง€ ์•Š๊ณ  ํ•„์š”ํ•œ ๊ฒฝ์šฐ์—๋งŒ ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•œ๋‹ค.

 

์˜ต์…˜ ์„ค์ •

const options = {
  root: document.querySelector("#scrollArea"),
  rootMargin: "0px",
  threshold: 1.0,
};

const observer = new IntersectionObserver(callback, options);
  • root
    • ๊ต์ฐจ์ ์„ ๊ฐ์‹œํ•˜๋Š”๋ฐ ์‚ฌ์šฉ๋˜๋Š” ์š”์†Œ. ๋ฐ˜๋“œ์‹œ ํƒ€๊ฒŸ์˜ ์ƒ์œ„ ์š”์†Œ์ด์–ด์•ผ ํ•œ๋‹ค.
    • ๊ธฐ๋ณธ๊ฐ’์€ ๋ทฐํฌํŠธ
  • rootMargin
    • root ์š”์†Œ์˜ ๋ฒ”์œ„๋ฅผ ์„ค์ •
    • ๊ธฐ๋ณธ๊ฐ’์€ 0

์ด๋ฏธ์ง€ ์ถœ์ฒ˜
https://wilsotobianco.hashnode.dev/a-graphical-introduction-to-the-intersection-observer-api
https://www.smashingmagazine.com/2021/07/dynamic-header-intersection-observer/
  • threshold
    • ์ฝœ๋ฐฑ์ด ์‹คํ–‰๋˜๋Š” ๊ต์ฐจ ๋น„์œจ
    • ๊ธฐ๋ณธ ๊ฐ’์€ 0 (1px์ด๋ผ๋„ ๋ณด์ด๋ฉด ์ฝœ๋ฐฑ ์‹คํ–‰)
    • 1์€ ํƒ€๊ฒŸ ์š”์†Œ๊ฐ€ 100% ๋ณด์ผ๋•Œ
    • [0, 0.25, 0.5, 1] // 0.25๋Š” 25% ๋ณด์ผ ๋•Œ, 0.5๋Š” 50% ๋ณด์ผ ๋•Œ 

๐Ÿšฉ MutationObserver

https://developer.mozilla.org/ko/docs/Web/API/MutationObserver

DOM ์š”์†Œ์˜ ์†์„ฑ, ์ž์‹ ๋…ธ๋“œ ๋“ฑ์˜ ๋ณ€ํ™”๋ฅผ ๊ฐ์ง€ํ•˜๊ณ  ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•œ๋‹ค.

 

MutationObserver๋Š” ๊ธฐ์กด์˜ Mutation Event๋ฅผ ๋Œ€์ฒดํ•˜๋ฉฐ ๋น„๋™๊ธฐ์ ์œผ๋กœ ๋™์ž‘ํ•œ๋‹ค. ๋ณ€ํ™”๋ฅผ ๊ฐ์ง€ํ•œ ํ›„, ์ฝœ๋ฐฑ์„ ๋งˆ์ดํฌ๋กœํƒœ์Šคํฌํ์— ์ถ”๊ฐ€ํ•˜๋ฏ€๋กœ  ๋ฉ”์ธ ์Šค๋ ˆ๋“œ์˜ ์ž‘์—…์„ ๋ฐฉํ•ดํ•˜์ง€ ์•Š๋Š”๋‹ค.

 

์˜ต์…˜ ์„ค์ •

// ๋ณ€๊ฒฝ์„ ๊ฐ์ง€ํ•  ๋…ธ๋“œ ์„ ํƒ
const targetNode = document.getElementById("some-id");

// ๊ฐ์ง€ ์˜ต์…˜ (๊ฐ์ง€ํ•  ๋ณ€๊ฒฝ)
const config = { attributes: true, childList: true, subtree: true };

const observer = new MutationObserver(callback);

// ์„ค์ •ํ•œ ๋ณ€๊ฒฝ์˜ ๊ฐ์ง€ ์‹œ์ž‘
observer.observe(targetNode, config);
  • attributes
    • ์š”์†Œ์˜ ์†์„ฑ(attribute) ๋ณ€ํ™”๋ฅผ ๊ฐ์ง€
  • childList
    • ์ž์‹ ๋…ธ๋“œ์˜ ์ถ”๊ฐ€ ๋ฐ ์ œ๊ฑฐ๋ฅผ ๊ฐ์ง€
  • subtree
    • ๋ชจ๋“  ํ•˜์œ„ ๋…ธ๋“œ์˜ ์ถ”๊ฐ€, ์ œ๊ฑฐ ๋ฐ ๋ณ€๊ฒฝ์„ ๊ฐ์ง€
  • attributeOldValue
    • ์†์„ฑ์˜ ์ด์ „ ๊ฐ’์„ ๊ธฐ๋ก
  • characterData
    • ํ…์ŠคํŠธ ๋…ธ๋“œ์˜ ๋ณ€๊ฒฝ์„ ๊ฐ์ง€
  • characterDataOldValue
    • ํ…์ŠคํŠธ ๋…ธ๋“œ์˜ ์ด์ „ ๊ฐ’์„ ๊ธฐ๋ก
  • attributeFilter
    • ๊ฐ์ง€ํ•  ์†์„ฑ์˜ ์ด๋ฆ„์ผ ์ง€์ •, ์ง€์ •๋œ ์†์„ฑ๋งŒ ๋ณ€ํ™”๊ฐ€ ๊ฐ์ง€๋œ๋‹ค.
    • attribute๊ฐ€ true ์„ค์ •๋œ ๊ฒฝ์šฐ๋งŒ ์œ ํšจ
    • ['class', 'id', 'style', ...] 

 

๐Ÿšฉ ResizeObserver

https://developer.mozilla.org/en-US/docs/Web/API/ResizeObserver

์š”์†Œ์˜ ํฌ๊ธฐ ๋ณ€ํ™”๋ฅผ ๊ฐ์ง€ํ•˜๊ณ  ์ฝœ๋ฐฑ ํ•จ์ˆ˜๋ฅผ ์‹คํ–‰ํ•œ๋‹ค.

 

๊ธฐ์กด์˜ resize ์ด๋ฒคํŠธ๋Š” ๋ธŒ๋ผ์šฐ์ € ์ฐฝ ํฌ๊ธฐ ๋ณ€ํ™”๋ฅผ ๊ฐ์ง€ํ•˜๋ฉฐ ๋™๊ธฐ์ ์œผ๋กœ ์ž‘๋™ํ•œ๋‹ค. ๋ฐ˜๋ฉด, ResizeObserver๋Š” ํŠน์ • ์š”์†Œ์˜ ํฌ๊ธฐ ๋ณ€ํ™”๋งŒ ๊ฐ์ง€ํ•˜๊ณ , ๋น„๋™๊ธฐ์  ์ฒ˜๋ฆฌํ•˜์—ฌ ๋ฉ”์ธ ์Šค๋ ˆ๋“œ์˜ ์ž‘์—…์„ ๋ฐฉํ•ดํ•˜์ง€ ์•Š๋Š”๋‹ค.

const divElem = document.querySelector("body > div");

const resizeObserver = new ResizeObserver(callback);

resizeObserver.observe(divElem);