본문 바로가기
컴퓨터 사이언스/TIL 정리

[자바스크립트] 문서 객체 모델 DOM, 이벤트

by 메리뉴데이 2022. 7. 19.

<모던 자바스크립트 튜토리얼>

 

 

문서 객체 모델이란?

DOM은 웹 문서를 하나의 객체로 정의한다.

웹 문서를 이루는 텍스트나 이미지, 표 등의 모든 요소도 각각 객체로 정의한다.

그래서, DOM은 웹 문서와 그 안의 모든 요소를 객체로 인식하고 처리하는 것을 말한다.

이러한 문서 객체 모델(DOM)의 구조를 DOM 트리로 나타낸다.

 

 

 

DOM 트리

DOM은 웹 문서의 요소를 부모 요소와 자식 요소로 구분한다. 

DOM은 HTML 요소의 계층과 달리,  

               문서 안의 요소 뿐만 아니라 각 요소에 사용한 내용과 속성도 자식으로 나타낸다.

               ex. body의 자식인 h1의 요소 내용도 h1의 자식이 되지만, img 요소의 src이나 alt 속성도 각각의 자식이 된다.

부모와 자식 구조로 표시하면 마치 나무 형태가 되어 DOM 트리라고 한다. 

이 DOM 트리로 웹 문서의 DOM 구조를 파악하고, 자바스크립트를 사용해 원하는 객체에 접근해 원하는 부분을 수정할 수 있게 된다 !

 

DOM을 구성하는 기본 원칙

1. 모든 HTML 태그는 요소(element) 노드이다.
2. HTML 태그에서 사용하는 텍스트 내용은 자식 노드인 text 노드이다.
3. HTML 태그에 있는 속성은 자식 노드인 속성(attribute) 노드이다.
4. 주석은 주석(comment) 노드이다.

    cf. 노드의 종류 : root element(html), element, attribute, text, comment

 

 

 

 

DOM에 접근하기

 id, class, 태그 등의 선택자를 사용해서 DOM에 접근할 수 있다.

 

getElementById() : id 선택자(id명)로 접근하는 메소드

                                      ex. document.getElementById("box1");

 

getElemenstByClassName() : class 선택자(class명)로 접근하는 메소드

                                                          ex. document.getElementsByClassName("myBoxes");

                                                          이 메소드를 사용하면 클래스 이름이 같은 DOM 요소들이 HTMLCollection 객체로 저장된다.

                                                          HTMLCollection 객체는 배열과 비슷하고, 배열은 아니지만 배열처럼 사용할 수 있다.

 

getElementsByTagName() : id나 class(이름)를 따로 지정하지 않은 DOM 요소에 접근할 때는 태그(명)를 이용한다.

                                                        ex. document.getElementsByTagName("div");

 

 

위의 세 가지 메서드의 반환값은 HTMLCollection 객체이다. 이 객체에는  HTML 요소('div', 'a', 'p' 등)만 저장된다.

cf. 아래의 두 가지 메서드의 반환값은 노드이거나 노드 리스트(노드를 한 번에 여러 개 저장한 것으로 배열과 비슷)이다. 

 

DOM 트리의 텍스트, 속성 노드까지 자유롭게 제어하려면

querySelector()나 querySelectorAll() 메소드를 사용해야 한다 !

이 두 메서드에서 선택자를 표시할 때 id 이름 앞에는 #(해시 기호)를, class 이름 앞에는 .(온점)을 붙이고, 태그는 그냥 태그명만을 작성한다.  cf. querySelector() 메서드에서 class 이름으로 접근할 때는 class 이름을 사용한 여러 요소 중에서 첫 번째 요소만 반환 !

 

 

웹 요소의 내용을 수정하는 innerText, innerHTML 프로퍼티

innerText 프로퍼티 : 텍스트 내용을 표시

                                        ex. let now = new Date();        // 자바스크립트의 내장 객체인 Date 객체 생성자

                                               document.getElementByID("current").innerText = now;      // Date 객체로 생성된 내용만 표시됨

innerHTML 프로퍼티 : HTML 태그까지 반영하여 표시

                                           ex. document.getElementByID("current").innerHTML = "<em>" + now + "</em>";

                                                  // 요소의 내용 뿐 아니라, 태그도 같이 표시하여 내용에 스타일을 주고 있음

 

 

속성을 가져오거나 수정하는 getAttribute(), setAttribute() 메서드

getAttribute() : 속성에 접근

                               ex. let cup = document.querySelector("#cup");        // id가 cup인 요소에 접근

                                      alert("이미지 소스: " + cup.getAttribute("src"));    // cup의 src 속성(값)을 알림 창에 메세지와 함께 표시

setAttribute() : 접근한 속성의 값을 바꿈

                              ex. cup.setAttribute("src", newPic);       // src 속성의 값을 newPic으로 설정

 

 

 

 

이벤트와 이벤트 처리기

대부분의 함수는 사용자가 화면에서 버튼을 클릭하거나 항목을 선택했을 때 실행되는데,

버튼 클릭이나 항목을 선택하는 것을 이벤트라고 한다.

이벤트가 발생했을 때 실행(처리)하는 함수를 이벤트 처리기(이벤트 핸들러)라고 한다.

자바스크립트에서 사용하는 이벤트의 종류와 이벤트 처리기를 연결하는 방법은 다음과 같다.

 

<마우스 이벤트> : 마우스를 이용해 버튼이나 휠 버튼을 조작할 때 발생

종류 설명
click 사용자가 HTML 요소를 클릭할 때 발생
dbclick 사용자가 HTML 요소를 더블클릭할 때 발생
mousedown 사용자가 요소 위에서 마우스 버튼을 눌렀을 때 발생
mousemove 사용자가 요소 위에서 마우스 포인터를 움직일 때 발생
mouseover 마우스 포인터가 요소 위로 옮겨질 때 발생
mouseout 마우스 포인터가 요소를 벗어날 때 발생
mouseup 사용자가 요소 위에 놓인 마우스 버튼에서 손을 뗄 때 발생

 

<키보드 이벤트> : 키보드에서 특정 키를 조작할 때 발생

종류 설명
keydown 사용자가 키를 누르는 동안 발생
keypress 사용자가 키를 눌렀을 때 발생
keyup 사용자가 키에서 손을 뗄 때 발생

 

<문서 로딩 이벤트> : 서버에서 웹 문서를 가져오거나 문서를 위아래로 스크롤하는 등 웹 문서를 브라우저 창에 보여주는 것과 관련된 이벤트

종류 설명
abort 문서가 완전히 로딩되기 전에 불러오기를 멈췄을 때 발생
error 문서가 정확히 로딩되지 않았을 때 발생
load 문서 로딩이 끝나면 발생
resize 문서 화면 크기가 바뀌었을 때 발생
scroll 문서 화면이 스크롤되었을 때 발생
unload 문서에서 벗어날 때 발생

 

<폼 이벤트> : 폼 요소에 내용을 입력하면서 발생하는 이벤트

종류 설명
blur 폼 요소에 포커스를 잃었을 때 발생
change 목록이나 체크 상태 등이 변경되면 발생. <input>, <select>, <textarea> 태그에서 사용
focus 폼 요소에 포커스가 놓였을 때 발생. <label>, <select>, <textarea>, <button> 태그에서 사용
reset 폼이 리셋되었을 때 발생
submit submit 버튼을 클릭했을 때 발생

 

cf. 이 외에도 자바스크립트에는 다양한 이벤트가 있다.  https://developer.mozilla.org/en-US/docs/Web/Events

 

Event reference | MDN

Events are fired to notify code of "interesting changes" that may affect code execution. These can arise from user interactions such as using a mouse or resizing a window, changes in the state of the underlying environment (e.g. low battery or media events

developer.mozilla.org

 

이벤트를 처리하는 가장 기본적인 방법은 이벤트가 발생한 HTML 태그에 이벤트 처리기를 직접 연결하는 것이다.

 

 

 

 

DOM에서 이벤트 처리하기

HTML 태그(요소)에서 이벤트 처리기를 연결할 수 있지만, 태그와 스크립트 소스가 섞여 있어 복잡한 프로그램에는 부적합하다.

하지만, DOM에서 이벤트 처리기를 연결하면 HTML 태그와 스크립트 소스를 분리할 수 있다.

기본형 : <태그 on이벤트명 = "함수명">
              ex. <a href= "#" onclick = "alert('버튼을 클릭했습니다.')"> Orange </a>

 

DOM 요소에 함수 직접 연결하기

이벤트 처리기 함수가 간단하다면 DOM 요소에 직접 연결할 수 있다.

ex. let cup = document.querySelector('#cup');

       cup.onclick = function() {

         alert("이미지를 클릭했습니다.");

       }        // img 요소를 가져와 변수에 저장한 후 onclick을 사용하여 변수에 이벤트 처리기(함수)를 직접 연결

 

함수 이름을 사용해 연결하기

이벤트가 발생했을 때 실행할 함수를 따로 정의해 놓았다면 함수 이름을 사용해 연결할 수 있다.

cf. 함수 이름 다음에 괄호 ()를 추가하지 않는다 !

ex. let cup = document.querySelector('#cup');

       cup.onclick = changePic;

       function changePic() {

         cup.src = "images/cup-2.png";

       }        //  img 요소를 cup 변수에 저장한 후 click 이벤트가 발생했을 때 changePic() 함수를 실행

 

 

 

 

 

DOM의 event 객체 알아보기

DOM에는 웹 문서에서 이벤트가 발생한 요소가 무엇인지, 어떤 이벤트가 발생했는지 등의 정보를 저장하는 event 객체가 있다.

이벤트가 발생한 대상에 접근하려면 이벤트 처리기(함수)에서 예약어 this를 사용한다.  

 

 

 

 

addEventListener() 메서드 사용하기

한 요소에 하나의 이벤트 처리기만 연결하던 것을 벗어나, addEventListener() 메서드와 event 객체를 사용하면 한 요소에 여러 이벤트 처리기를 연결해 실행할 수 있다.

기본형 : 요소.addEventListener(이벤트, 함수, 캡쳐 여부);

이벤트 ... 이벤트 유형을 지정하는데, 이때는 on을 붙이지 않고 이벤트를 작성해야 한다 !

함수 ... 이벤트 처리기, 즉 이벤트가 발생하면 실행할 명령이나 함수를 지정. 함수를 정의할 때 event 객체를 인수로 받는다.

캡쳐 여부 ... 이벤트를 캡쳐하는지의 여부를 지정하며, 기본값은 false. false는 DOM의 자식 노드에서 부모 노드로 전달되는 이벤트                              버블링을 한다는 의미이고, true이면 DOM의 부모 노드에서 자식 노드로 전달되는 이벤트 캡처링을 한다는 의미이다.

 

ex. let cover = document.getElementById("cover");       

       cover.addEventListener("mouseover", changePic);          // 마우스 포인터를 올리면 changePic() 실행                                                  cover.addEventListener("mouseout", originPic);               // 마우스 포인터를 치우면 originPic() 실행          

        function changePic() {         

          cover.src = "images/coffee1.png";       

         }       

       function originPic() {         

         cover.src = "images/coffee2.png";       

        }        // addEventListener() 메소드를 사용해서 changePic() 함수와 originPic() 함수, 두 이벤트 처리기를 연결해 실행 ! 

 

 

cf. 단순히 이벤트를 처리하는 함수라면, 메소드 안에서 함수 표현식으로 사용하는 경우도 많다.

     ex.  let cover = document.getElementById("cover");

       cover.addEventListener("mouseover", function() {                // changePic()

          cover.src = "images/coffee1.png";

       });        

       cover.addEventListener("mouseout", function() {                  // originPic()

          cover.src = "images/coffee2.png";

       });