diff --git "a/docs/39_DOM/\353\254\270\354\206\214\355\235\254.md" "b/docs/39_DOM/\353\254\270\354\206\214\355\235\254.md" index 5e44ba74..d6d74b67 100644 --- "a/docs/39_DOM/\353\254\270\354\206\214\355\235\254.md" +++ "b/docs/39_DOM/\353\254\270\354\206\214\355\235\254.md" @@ -647,6 +647,243 @@ DOMPurify.sanitize(''); ``` +### πŸ’¬ 3. λ…Έλ“œ 생성과 μΆ”κ°€ + +#### ✨ μš”μ†Œ λ…Έλ“œ 생성 + +> `Document.prototype.createElement(tagName)` λ©”μ„œλ“œλŠ” μš”μ†Œ λ…Έλ“œλ₯Ό 생성해 λ°˜ν™˜ν•œλ‹€. 이떄 μƒμ„±λœ μš”μ†Œ λ…Έλ“œλŠ” μ•„λ¬΄λŸ° μžμ‹ λ…Έλ“œλ₯Ό 가지고 μžˆμ§€ μ•ŠκΈ° λ•Œλ¬Έμ— μš”μ†Œ λ…Έλ“œμ˜ μžμ‹ λ…Έλ“œμΈ ν…μŠ€νŠΈ λ…Έλ“œλ„ μ—†λŠ” μƒνƒœλ‹€. + +```javascript +const $li = document.createElement('li'); +console.log($li.childNodes); // NodeList [] +``` + +![](https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbhbrH6%2FbtrAYtFCU9e%2FCmbKmC81nM6ojw8s3IhXVK%2Fimg.png) + +#### ✨ ν…μŠ€νŠΈ λ…Έλ“œ 생성 + +> `Document.prototype.createTextNode(text)` λ©”μ„œλ“œλŠ” ν…μŠ€νŠΈ λ…Έλ“œλ₯Ό 생성해 λ°˜ν™˜ν•œλ‹€. ν…μŠ€νŠΈ λ…Έλ“œλ₯Ό 생성할 뿐 μš”μ†Œ λ…Έλ“œμ— μΆ”κ°€ν•˜μ§€λŠ” μ•ŠκΈ° λ•Œλ¬Έμ— 이후에 μš”μ†Œ λ…Έλ“œμ— ν…μŠ€νŠΈ λ…Έλ“œλ₯Ό μΆ”κ°€ν•˜λŠ” 별도 μ²˜λ¦¬κ°€ ν•„μš”ν•˜λ‹€. + +```javascript +const textNode = document.createTextNode('Banana'); +``` + +![](https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcgtlKq%2FbtrAVsOGiDz%2FTom3PpiPkPksdt2rUTzwa1%2Fimg.png) + +#### ✨ ν…μŠ€νŠΈ λ…Έλ“œλ₯Ό μš”μ†Œ λ…Έλ“œμ˜ μžμ‹ λ…Έλ“œλ‘œ μΆ”κ°€ + +> `Node.prototype.appendChild(childNode)` λ©”μ„œλ“œλŠ” λ§€κ°œλ³€μˆ˜ `childNode`μ—κ²Œ 인수둜 μ „λ‹¬ν•œ λ…Έλ“œλ₯Ό `appendChild` λ©”μ„œλ“œλ₯Ό ν˜ΈμΆœν•œ λ…Έλ“œμ˜ λ§ˆμ§€λ§‰ μžμ‹ λ…Έλ“œλ‘œ μΆ”κ°€ν•œλ‹€. μ΄λ•Œ κΈ°μ‘΄ DOMμ—λŠ” μΆ”κ°€λ˜μ§€ μ•ŠλŠ”λ‹€. + +μš”μ†Œ λ…Έλ“œμ— μžμ‹ λ…Έλ“œκ°€ ν•˜λ‚˜λ„ μ—†λŠ” κ²½μš°μ—λŠ” `textContext` ν”„λ‘œνΌν‹°λ₯Ό μ‚¬μš©ν•˜λŠ” 것이 더 κ°„νŽΈν•˜λ‹€. 단, μš”μ†Œ λ…Έλ“œμ— μžμ‹ λ…Έλ“œκ°€ μžˆλŠ” 경우 μš”μ†Œ λ…Έλ“œμ˜ `textContent` ν”„λ‘œνΌν‹°μ— λ¬Έμžμ—΄μ„ ν• λ‹Ήν•˜λ©΄ μš”μ†Œ λ…Έλ“œμ˜ λͺ¨λ“  μžμ‹ λ…Έλ“œκ°€ 제거되고 ν• λ‹Ήν•œ λ¬Έμžμ—΄μ΄ ν…μŠ€νŠΈλ‘œ μΆ”κ°€λ˜λ―€λ‘œ μ£Όμ˜ν•΄μ•Ό ν•œλ‹€. 🚨 + +```javascript +$li.appendChild(document.createTextNode('Banana')); + +// μœ„ μ½”λ“œμ™€ λ™μΌν•˜κ²Œ λ™μž‘ +$li.textContent = 'Banana'; +``` + +![](https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fee7Vxs%2FbtrASCch6fG%2FpwOuWO0289sDzigfOtxVaK%2Fimg.png) + +#### ✨ μš”μ†Œ λ…Έλ“œλ₯Ό DOM에 μΆ”κ°€ + +> `Node.prototype.appendChild` λ©”μ„œλ“œλ₯Ό μ‚¬μš©ν•΄ ν…μŠ€νŠΈ λ…Έλ“œμ™€ λΆ€μž κ΄€κ³„λ‘œ μ—°κ²°ν•œ μš”μ†Œ λ…Έλ“œλ₯Ό #fruits μš”μ†Œ λ…Έλ“œμ˜ λ§ˆμ§€λ§‰ μžμ‹ μš”μ†Œλ‘œ μΆ”κ°€ν•œλ‹€. 이 κ³Όμ •μ—μ„œ μƒˆλ‘­κ²Œ μƒμ„±ν•œ μš”μ†Œ λ…Έλ“œκ°€ DOM에 μΆ”κ°€λœλ‹€. + +기쑴의 DOM에 μš”μ†Œ λ…Έλ“œλ₯Ό μΆ”κ°€ν•˜λŠ” μ²˜λ¦¬λŠ” 이 과정뿐이며 μœ„ μ˜ˆμ œλŠ” 단 ν•˜λ‚˜μ˜ μš”μ†Œ λ…Έλ“œλ₯Ό 생성해 DOM에 ν•œ 번 μΆ”κ°€ν•˜λ―€λ‘œ DOM은 ν•œ 번 λ³€κ²½λœλ‹€. μ΄λ•Œ λ¦¬ν”Œλ‘œμš°μ™€ λ¦¬νŽ˜μΈνŠΈκ°€ μ‹€ν–‰λœλ‹€. + +```javascript +$fruits.appendChild($li); +``` + +![](https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbUsuIa%2FbtrARFHlsRe%2FrxAS601yGvQqk9pVZkotxk%2Fimg.png) + +### πŸ’¬ 4. 볡수의 λ…Έλ“œ 생성과 μΆ”κ°€ + +> `DocumentFragment` λ…Έλ“œλŠ” λ…Έλ“œ 객체의 μΌμ’…μœΌλ‘œ, λΆ€λͺ¨ λ…Έλ“œκ°€ μ—†μ–΄ κΈ°μ‘΄ DOMκ³ΌλŠ” λ³„λ„λ‘œ μ‘΄μž¬ν•œλ‹€λŠ” νŠΉμ§•μ΄ μžˆλ‹€. μžμ‹ λ…Έλ“œλ“€μ˜ λΆ€λͺ¨ λ…Έλ“œλ‘œμ„œ λ³„λ„μ˜ μ„œλΈŒ DOM을 κ΅¬μ„±ν•˜μ—¬ κΈ°μ‘΄ DOM에 μΆ”κ°€ν•˜κΈ° μœ„ν•œ μš©λ„λ‘œ μ‚¬μš©ν•œλ‹€. + +`DocumentFragment` λ…Έλ“œλŠ” κΈ°μ‘΄ DOMκ³ΌλŠ” λ³„λ„λ‘œ μ‘΄μž¬ν•˜λ―€λ‘œ μžμ‹ λ…Έλ“œλ₯Ό 좔가해도 κΈ°μ‘΄ DOMμ—λŠ” μ–΄λ– ν•œ 변경도 λ°œμƒν•˜μ§€ μ•ŠμœΌλ©°, DOM에 μΆ”κ°€ν•˜λ©΄ μžμ‹ μ€ 제거되고 μžμ‹ μ˜ μžμ‹ λ…Έλ“œλ§Œ DOM에 μΆ”κ°€λœλ‹€. λ¦¬ν”Œλ‘œμš°μ™€ 리페인트 λ˜ν•œ ν•œ 번만 μ‹€ν–‰λœλ‹€. + +![](https://blog.kakaocdn.net/dn/cduCw4/btrABLuYwLy/rFA4dBOA0DWAVJmj2DXceK/img.png) + +```html + + + + + + + +``` + +### πŸ’¬ 5. λ…Έλ“œ μ‚½μž… + +#### ✨ λ§ˆμ§€λ§‰ λ…Έλ“œλ‘œ μΆ”κ°€ + +> `Node.prototype.appendChild` λ©”μ„œλ“œλŠ” 인수둜 전달받은 λ…Έλ“œλ₯Ό μžμ‹ μ„ ν˜ΈμΆœν•œ λ…Έλ“œμ˜ λ§ˆμ§€λ§‰ μžμ‹ λ…Έλ“œλ‘œ DOM에 μΆ”κ°€ν•œλ‹€. λ…Έλ“œλ₯Ό μΆ”κ°€ν•  μœ„μΉ˜λŠ” μ •ν•  수 μ—†κ³  μ–Έμ œλ‚˜ λ§ˆμ§€λ§‰ μžμ‹ λ…Έλ“œλ‘œ μΆ”κ°€ν•œλ‹€. + +```html + + + + + + + +``` + +#### ✨ μ§€μ •ν•œ μœ„μΉ˜μ— λ…Έλ“œ μ‚½μž… + +> `Node.prototype.insertBefore(newNode, childNode)` λ©”μ„œλ“œλŠ” 첫 번째 인수둜 전달받은 λ…Έλ“œλ₯Ό 두 번째 인수둜 전달받은 λ…Έλ“œ μ•žμ— μ‚½μž…ν•œλ‹€. + +μ΄λ•Œ 두 번째 인수둜 전달받은 λ…Έλ“œλŠ” λ°˜λ“œμ‹œ `insertBefore` λ©”μ„œλ“œλ₯Ό ν˜ΈμΆœν•œ λ…Έλ“œμ˜ μžμ‹ λ…Έλ“œμ—¬μ•Ό ν•˜λ©°, μ•„λ‹Œ 경우 `DOMException` μ—λŸ¬κ°€ λ°œμƒν•œλ‹€. 전달받은 두 번째 μΈμˆ˜κ°€ null인 κ²½μš°μ—λŠ” `appendChild` λ©”μ„œλ“œμ²˜λŸΌ λ™μž‘ν•œλ‹€. + +```html + + + + + + + +``` + +### πŸ’¬ 6. λ…Έλ“œ 이동 + +> DOM에 이미 μ‘΄μž¬ν•˜λŠ” λ…Έλ“œλ₯Ό `appendChild` λ˜λŠ” `insertBefore` λ©”μ„œλ“œλ₯Ό μ‚¬μš©ν•΄ DOM에 λ‹€μ‹œ μΆ”κ°€ν•˜λ©΄ ν˜„μž¬ μœ„μΉ˜μ—μ„œ λ…Έλ“œλ₯Ό μ œκ±°ν•˜κ³  μƒˆλ‘œμš΄ μœ„μΉ˜μ— λ…Έλ“œλ₯Ό μΆ”κ°€ν•˜λ©° μ΄λ™ν•œλ‹€. + +```html + + + + + + + +``` + +### πŸ’¬ 7. λ…Έλ“œ 볡사 + +> `Node.prototype.cloneNode([deep: true | false])` λ©”μ„œλ“œλŠ” λ…Έλ“œμ˜ 사본을 생성해 λ°˜ν™˜ν•œλ‹€. falseλ₯Ό 인수둜 μ „λ‹¬ν•˜κ±°λ‚˜ μƒλž΅ν•˜λ©΄ λ…Έλ“œλ₯Ό 얕은 볡사shallow copyν•˜μ—¬ λ…Έλ“œ μžμ‹ λ§Œμ˜ 사본을 μƒμ„±ν•œλ‹€. 얕은 λ³΅μ‚¬λ‘œ μƒμ„±λœ μš”μ†Œ λ…Έλ“œλŠ” μžμ† λ…Έλ“œλ₯Ό λ³΅μ‚¬ν•˜μ§€ μ•ŠμœΌλ―€λ‘œ ν…μŠ€νŠΈ λ…Έλ“œλ„ μ—†λ‹€. + +```html + + + + + + + +``` + +### πŸ’¬ 8. λ…Έλ“œ ꡐ체 + +> `Node.prototype.replaceChild(newChild, oldChild)` λ©”μ„œλ“œλŠ” μžμ‹ μ„ ν˜ΈμΆœν•œ λ…Έλ“œμ˜ μžμ‹ λ…Έλ“œλ₯Ό λ‹€λ₯Έ λ…Έλ“œλ‘œ κ΅μ²΄ν•œλ‹€. 즉, μžμ‹ μ„ ν˜ΈμΆœν•œ λ…Έλ“œμ˜ μžμ‹ λ…Έλ“œμΈ `oldChild` λ…Έλ“œλ₯Ό `newChild` λ…Έλ“œλ‘œ κ΅μ²΄ν•œλ‹€. μ΄λ•Œ `oldChild` λ…Έλ“œλŠ” DOMμ—μ„œ μ œκ±°λœλ‹€. + +```html + + + + + + + +``` + +### πŸ’¬ 9. λ…Έλ“œ μ‚­μ œ + +> `Node.prototype.removeChild(child)` λ©”μ„œλ“œλŠ” child λ§€κ°œλ³€μˆ˜μ— 인수둜 μ „λ‹¬ν•œ λ…Έλ“œλ₯Ό DOMμ—μ„œ μ‚­μ œν•œλ‹€. + +```html + + + + + + + +``` + ## πŸ‘€ REFERENCE λͺ¨λ˜ μžλ°”μŠ€ν¬λ¦½νŠΈ Deep Dive 39μž₯ DOM