[ ᴊᴀᴠᴀꜱᴄʀɪᴘᴛ ] DOM(Document Object Model)

NewHa·2023년 11월 4일

DOM(문서 객체 모델)

DOM(Document Object Model)은 Document 즉, HTML요소를 객체(Object)처럼 조작할 수 있는 모델(Model)입니다. DOM이 없으면 자바스크립트는 HTML과 엑세스할 수 없습니다. DOM을 이용하면 HTML의 부분들에 접근하여 동적으로 움직이게 만들 수 있습니다.

  1. DOM이란 무엇인가?
    정의: DOM(Document Object Model)은 HTML 문서를 구조화하고 이를 프로그래밍적으로 다룰 수 있도록 하는 API입니다.
    비유: 웹페이지를 '집'이라고 생각한다면, DOM은 그 집의 설계도와 같습니다. 설계도를 통해 집의 구조를 확인하고, 원하는 부분을 변경할 수 있듯이 DOM도 HTML 요소를 확인하고 조작할 수 있게 합니다.

💚 DOM에 접근하기

  • script태그를 이용해 HTML파일에 자바스크립트 파일을 불러옵니다. 웹 브라우저가 <script>요소를 만나면, HTML 해석을 잠시 멈추고 <script>요소를 먼저 실행합니다. (script요소는 등장과 함께 실행됩니다.) (HTML파싱 문서 참고)

  • HTML 문서를 읽어들이고 스타일을 입히고 페이지로 만들어 뷰포트에 표시하는 과정을 critical Rendering Path라고 합니다.

  • document객체에 구현됩니다. 브라우저에서 작동되는 자바스크립트 코드에서는 어디에서나 조회할 수 있다.

💚 DOM생성

  • 원본 HTML 문서의 객체 기반 표현 방식입니다. 단순 텍스트로 구성된 HTML 문서의 내용과 구조가 객체 모델로 변환되어 다양한 프로그램에서 사용될 수 있습니다. 이러한 DOM의 개체구조는 노드트리로 표현됩니다.

  • DOM 은 항상 유효한 HTML 형식이고, 자바스크립트에 수정될 수 있는 동적모델이어야 합니다.

🎀 DOM이 아닌 것

  • HTML : HTML 문서로부터 생성되지만 항상 동일하진 않습니다.
    • 작성된 HTML문서가 유효하지 않을 떄 DOM을 생성하는 동안 브라우저는 올바르게 교정합니다.
    • 자바스크립트에 의해 DOM이 수정될 수 있습니다. DOM을 업데이트 하지만 HTML 문서의 내용을 변경하진 않습니다.
  • DOM은 브라우저에 보이는 것이 아닙니다.
    • 브라우저 뷰 포트에 보이는 것은 렌더트리로 DOM + CSSOM의 조합입니다. 렌더트리는 오직 스크린에 그려지는 것으로 DOM과 다릅니다. 즉, 렌더링 요소만 관련있으므로 시각적으로 보이지 않는 요소는 제외됩니다.
  • DOM은 개발도구에서 보이지 않습니다.
    • 개발도구의 요소검사기는 DOM과 가장 가까운 근사치를 제공하지만, DOM에 없는 추가적인 정보를 포함합니다. 예컨대 CSS의 ::before::after 선택자를 사용해 생성된 가상 요소는 CSSOM과 렌더트리의 일부를 구성하지만 기술적으로 DOM의 요소는 아닙니다. DOM은 오직 원본 HTML 문서로 빌드되고, 요소에 적용되는 스타일을 포함하지 않기 때문입니다.
    • DOM 은 HTML 문서에 대한 인터페이스로, 뷰 포트에 무엇을 렌더링할지 결정하기 위해 사용되고, 페이지의 콘텐츠 및 구조, 스타일이 자바스크립트 프로그램에 의해 수정되기 위해 사용됩니다.

💚 DOM과 자바스크립트

  • DOM은 프로그래밍 언어는 아니지만 없으면 자바스크립트 언어는 웹페이지 또는 XML페이지 및 요소들과 관련된 모델이나 개념들에 대한 정보를 갖지 못하게 됩니다.
  • 페이지의 콘텐츠는 DOM에 저장되고 자바스크립트를 통해 접근하거나 조작할수 있다.
  • 웹 사이트를 구축하는데 사용되는 Web API입니다. DOM은 프로그래밍 언어와 독립적으로 설계되어 단일 API에서 문서의 구조적 표현을 사용할 수 있습니다.

    API : Web of XML Page -> DOM + JavaScript

  • 프로그래밍 언어와 독립적으로 디자인 되었기 때문에 문서의 구조적 표현은 단일 API를 통해 이용 가능하다.

💚 HTML에 JS 적용하기

  • console.dir을 사용해 DOM구조를 조회합니다. DOM을 객체의 모습으로 출력합니다. 조회시 HTML 엘리먼트에 지정할 수 있었던 다양한 속성이 이미 객체 내에 존재하여 많은 속성이 나타납니다.

  • 자식요소를 바로 조회하려면 document.body.chidren으로 조회할 수 있습니다.

  • 부모요소를 조회하려면 console.dir(자식요소.parentElement)로 조회할 수 있습니다.

    Element.closest()
    기준 요소부터 closest() 메소드를 사용해 부모요소 단위로 출발해 각 요소가 지정한 선택자에 만족할 때까지 탐색할 수 있습니다. 가장 가깝게 조건에 만족한 부모요소가 반환되며, 조건에 만족한 요소가 없으면 null값을 반환합니다.


🧡 CRUD

  • HTML 엘리먼트를 만들고, 조회하고, 갱신하고, 삭제하는 방법을 말합니다. CRUD를 먼저 이해한 후에 세세한 메서드 들을 공부해야 합니다.

CREAT : document.creatElement()

document.createElement('div')  // <div></div> 가 추가됩니다.
//자바스크립트로 DOM을 조작하기 위해, 변수에 할당합니다.
const 변수명 = document.cerateElement('div')

APPEND : Element.append()

//생성한 변수를 트리구조와 연결합니다. 마지막 자식 뒤에 삽입합니다.
document.body.append(변수명)

READ : document.querySelector()

const 변수명 = document.querySelector(셀렉터)
//셀렉터 내에 클래스나 아이디를 넣어 HTML요소를 조회합니다.
const 변수명 = document.querySelectorAll(셀렉터)
//여러개의 요소를 한번에 가져오기 위해서 사용합니다.
  • 조회한 요소들은 배열은 아니지만 배열처럼 반복문을 사용할 수 있습니다. Array-like Object 인데, 유사배열, 배열형 객체 등의 이름으로 불립니다.

UPDATE : textContent

const 변수명 = document.createElement('div')  // div요소를 생성합니다.
변수명.textContent = '문자'  // <div>문자</div>
변수명.classList.add('CSS class명') //CSS을 적용합니다.
const 부모요소명 = document.querySelector('부모요소 셀렉터') //자식요소로 추가해주기 위해 먼저 부모요소를 불러옵니다.
부모요소명.append(변수명) // 부모요소 밑에 자식요소로 추가해줍니다.

setAttribute(name, value)
지정된 요소의 속성 값을 설정합니다. 속성이 이미 있으면 값이 업데이트됩니다. 그렇지 않으면 지정된 이름과 값으로 새 속성이 추가됩니다.
속성의 현재값을 얻으려면 getAttribute(), 제거하려면 removeAttribute()를 호출합니다.

DELETE

  • 요소의 위치를 알고 있는 경우
(요소)변수명.remove()
  • 여러 개의 자식 요소를 지우려면 innerHTML을 이용합니다. 간편하고 편리하지만 사이트의 공격벡터가 되어 잠재적인 보안 위험을 초래할 가능성이 있습니다.
document.querySelector('부모요소명').innerHTML = '' ; //부모요소 아래 모든 자식요소를 지웁니다.
  • 자식요소를 지정해서 삭제할 수 있습니다.
while(부모요소명.firstChild) {
  부모요소명.removeChild(부모요소명.firstChild);
} // 부모요소 안에 첫번쨰 자식요소를 제거합니다.

while(부모요소명.children.length > 1) {
  부모요소명. removeChild(부모요소명.lastChild);
} // 부모요소 안에 자식요소가 한개만 남을 때까지 마지막 요소를 제거합니다.
  • 직접 클래스 이름으로 찾아서 지울 수도 있습니다.
const 변수명 = document.querySelectorAll ('.클래스명') //'클래스명'을 가진 모든 요소들을 불러옵니다.
변수명.forEach(function(클래스명) {
  클래스명.remove();
})
// OR
for(let 클래스명 of 변수명) {
  클래스명.remove()
}
  • 그냥 innerHTML을 이용해 요소를 삭제할 수도 있습니다.

🧡 이벤트 객체

  • 이벤트 객체는 DOM과 관련된 이벤트가 발생되면 발생되는 관련 정보를 저장하는 객체라고 생각하면 됩니다. 예컨대 누른키의 키코드를 저장해주는 것 등이 있습니다.
  • 보통 이벤트객체매개변수는 [event] 혹은 [e]라고 많이 씁니다.

💚 공통 이벤트객체 속성과 메서드의 종류

  • currentTarget : 현재 이벤트를 처리중인 요소를 반환
  • target : 이벤트를 trigger한 요소를 반환
  • type : 발생된 이벤트 타입을 반환
  • view : 이벤트가 발생한 window개체에 대한 참조를 반환


🌈 Reference

profile
백 번을 보면 한 가지는 안다 👀

0개의 댓글