์์ง ์์ฑ ์ค์ธ ๋ฏธํกํ ๊ธ์ ๋๋ค.. ๋น ๋ฅธ ์์ผ ๋ด์ ์์ ํ๊ฒ ์ต๋๋ค. ๐ซ
requestAnimationFrame()
์ ๋ํด ์์๋ณด๊ธฐ ์ํด...
Event Loop
, Task Queue
, Micro Task Queue
์์ ๋ ๋์๊ฐ rAF๊น์ง ์์๋ณด์.
๋จผ์ ์ด ์ฝ๋ ์คํ ์์๋ฅผ ๋ง์ถฐ๋ณด์
console.log("script start");
setTimeout(function() {
console.log("setTimeout");
}, 0);
Promise.resolve().then(function() {
console.log("promise1");
}).then(function() {
console.log("promise2");
});
requestAnimationFrame(function {
console.log("requestAnimationFrame");
})
console.log("script end");
์คํ ์์๋ ๋ค์๊ณผ ๊ฐ๋ค. ๋ง์ถ์ง ๋ชปํ๋ค๋ฉด ์๋ ๊ธ์ ์ฝ์ด๋ณด๋ฉด์ ์์๋ณด์.
script start
script end
promise1
promise2
requestAnimationFrame
setTimeout
ํ์ง๋ง ์ค์ ๋ก ์๋ฐ์คํฌ๋ฆฝํธ๊ฐ ์ฌ์ฉ๋๋ ํ๊ฒฝ์ ์๊ฐํด๋ณด๋ฉด ํ๋์ ์์ ๋ง์ด ์๋ ๋ ๋ง์ ์์ ๋ค์ด ๋์์ ์ฒ๋ฆฌ๋๋ ๊ฒ์ ํ์ธํ ์ ์๋ค.
ex)
์ ๋๋ฉ์ด์
ํจ๊ณผ๋ฅผ ๋ณด์ฌ์ฃผ๋ฉด์ ๋์์ ๋ง์ฐ์ค ์
๋ ฅ์ ๋ฐ์ ์ฒ๋ฆฌex)
Node.js ๊ธฐ๋ฐ์ ์น์๋ฒ์์๋ ๋์์ ์ฌ๋ฌ ๊ฐ์ HTTP ์์ฒญ์ ์ฒ๋ฆฌ๋จ์ผ ์ค๋ ๋์ธ ์๋ฐ์คํฌ๋ฆฝํธ์์๋ ๋์์ฑ์ ์ง์ํ ์ ์๋ ๋น๊ฒฐ์๋ ์ด๋ฒคํธ ๋ฃจํ๊ฐ ์กด์ฌํ์ฌ ๋น๋๊ธฐ์ ์ธ ์ผ ์ฒ๋ฆฌ๋ฅผ ๊ฐ๋ฅ์ผ ํ๊ธฐ ๋๋ฌธ์ด๋ค.
๋น๋๊ธฐ ์์ฒญ์ ์๋ฐ์คํฌ๋ฆฝํธ ์์ง์ ๊ตฌ๋ํ๋ ํ๊ฒฝ,
์ฆ๋ธ๋ผ์ฐ์
๋NodeJS
๊ฐ ๋ด๋นํ๋ค.
์๋ ์ฌ์ง์์ ๊ทธ ํ๊ฒฝ์ ํ์ธํ ์ ์๋ค.
๋ธ๋ผ์ฐ์ ํ๊ฒฝ | Web API |
---|---|
๋น๋๊ธฐ์ ์ผ๋ก ์ฒ๋ฆฌ๋๋ Task๋ ํฌ๊ฒ ๋ ๊ฐ์ง ์ข ๋ฅ๋ก ๋๋๊ฒ ๋๋ค.
Task Queue
: setTimeout(), setInterval(), setImmediate() ๋ฑMicrotask Queue
: Promise์ ์ฝ๋ฐฑํจ์, async/await, process.nextTick, Object.observe, MutationObserver ๋ฑ์ฐ์ ์์๋ Microtask Queue
> Task Queue
Call stack์์ ๋ ์ด์ ์ฒ๋ฆฌํ task๊ฐ ์์ ๋ ์ฐ์ ์์๊ฐ ๋ ๋์ Microtask Queue์ ์๋ ๋น๋๊ธฐ task๊ฐ ๋จผ์ ์ฒ๋ฆฌ๋ ์ดํ์, Task Queue์ ์๋ task๊ฐ ์คํ๋๋ค.
์ฝ๋ ์์์ ๊ทธ ์คํ ์์๋ ๋ค์๊ณผ ๊ฐ๋ค.
console.log('Start!');
setTimeout(() => {
console.log('Timeout!');
}, 0);
Promise.resolve('Promise!').then(res => console.log(res));
console.log('End!');
rAF(requestAnimationFrame)
: ์์คํ ์ด ํ๋ ์์ ๊ทธ๋ฆด ์ค๋น๊ฐ ๋๋ฉด ์ ๋๋ฉ์ด์ ํ๋ ์์ ํธ์ถํ์ฌ ์ ๋๋ฉ์ด์ ์นํ์ด์ง๋ฅผ ๋ณด๋ค ์ํํ๊ณ ํจ์จ์ ์ผ๋ก ์์ฑํ ์ ์๋๋ก ํด์ค๋ค. ์ค์ ํ๋ฉด์ด ๊ฐฑ์ ๋์ด ํ์๋๋ ์ฃผ๊ธฐ์ ๋ฐ๋ผ ํจ์๋ฅผ ํธ์ถํด์ฃผ๊ธฐ ๋๋ฌธ์ ์๋ฐ์คํฌ๋ฆฝํธ๊ฐ ํ๋ ์ ์์ ์ ์คํ๋๋๋ก ๋ณด์ฅํด์ฃผ์ด ๋ฐ๋ฆผ ํ์์ ๋ฐฉ์งํด์ค๋ค.
setInterval
: ๋ธ๋ผ์ฐ์ ์ ๋ค๋ฅธ ํญ ํ๋ฉด์ ๋ณด๊ฑฐ๋ ๋ธ๋ผ์ฐ์ ๊ฐ ์ต์ํ๋์ด ์์ ๋ ๊ณ์ ํ์ด๋จธ๊ฐ ๋์ ์ฝ๋ฐฑ์ ํธ์ถํ๊ธฐ ๋๋ฌธ์ ์์คํ
๋ฆฌ์์ค ๋ญ๋น O & ๋ถํ์ํ ์ ๋ ฅ์ ์๋ชจ OrequestAnimationFrame
: ํ์ด์ง๊ฐ ๋นํ์ฑํ ๋ ์ํ์ด๋ฉด ํ์ด์ง ํ๋ฉด ๊ทธ๋ฆฌ๊ธฐ ์์
๋ ๋ธ๋ผ์ฐ์ ์ ์ํด ์ผ์ ์ค์ง๋จ์ผ๋ก CPU ๋ฆฌ์์ค/๋ฐฐํฐ๋ฆฌ ๋ญ๋น XAnimation Frames
: ๋ธ๋ผ์ฐ์ ์ ๋ ๋๋ง ์์ง์ด ๋ค์ ํ๋ ์์ ๊ทธ๋ฆฌ๊ธฐ ์ ์ ์คํํด์ผ ํ๋ rAF์ ๋ฑ๋กํ ์ฝ๋ฐฑ ํจ์๋ค์ ๋ด๋ Queueconst rocket = document.querySelector('.rocket');
const value = document.querySelector('.value');
let yPos = 0;
let rafId;
// ์ฝ๋ฐฑ ํจ์
const render = () => {
yPos += 2; // y ์ขํ ์ฆ๊ฐ
rocket.style.transform = `translateY(${-yPos}px)`; // ๋ก์ผ์ ์๋ก ์ฌ๋ฆฌ๊ธฐ
value.innerHTML = yPos; // ์นด์ดํฐ ํ์
// ๋ง์ฝ ๋ก์ผ ์์น๊ฐ ์ผ์ y์ขํ๊ฐ์ผ ๊ฒฝ์ฐ requestAnimationFrame ์ข
๋ฃ
if (yPos >= 500) {
cancelAnimationFrame(rafId);
return;
}
rafId = requestAnimationFrame(render); // rAF ๋ฐ๋ณต ํธ์ถ
}
requestAnimationFrame(render); // ์ ๋๋ฉ์ด์
์์