BOM(Browser Object Model)은 브라우저를 스크립트 언어로 제어하기 위해 객체로 모델링 한 것이다. 그래서 JS에서 BOM API를 사용해서 브라우저를 제어할 수 있다. window객체(브라우저)는 BOM의 최상위 객체이며 전역객체로 브라우저당 1개이다.
이 BOM에서 document 즉, html파일을 스크립트 언어로 제어하기 위해 객체로 모델링 한 것을 DOM이라고 한다. 그래서 JS 에서 DOM API를 사용해서 HTML문서를 제어할 수 있는 것이다. DOM 최상위 node는 window객체의 자식인 document객체이며 document객체는 HTML문서 하나당 하나이다.
▲우리가 항상 기본적으로 사용하는 html파일의 틀이다. 위 틀을 DOM으로 나타내보면 아래와 같다.
하나씩 개념과 예제를 보면서 알아보자.
/*
1.노드 생성
document객체의 createElement("태그명") 혹은 createTextNode("텍스트")
2.생성된 노드 부모에 붙이기
부모요소.prepend(노드 혹은 문자열(텍스트노드)) :부무의 자식요소 맨 앞에 붙인다
부모요소.append(노드 혹은 문자열(텍스트노드)) :부모의 자식요소 맨 뒤에 붙인다
부모요소.appendChild(노드)
부모요소.insertBefore(새노드, 기존 자식노드)
기존요소.insertAdjacentElement(위치,새노드);부모요소가 필요없다 즉 기존요소를 기준으로 위치를 정해서 삽입한다
기존요소.insertAdjacentHTML(위치,'태그형태의 문자열')
※insertBefor 와 insertAdjacentElement차이점
insertBefore() requires you to provide the parent node, an existing child node, and the new node to be inserted; the new node is put before the child node
insertAdjacentElement only requires you to provide an existing node and the new node. The new node is inserted at some place related to the existing node. There's no need to provide the parent node.
3.노드 추가 및 삭제
부모요소.removeChild(자식요소)
자신요소.remove()
4.노드 복제
타켓요소.cloneNode(true)
5.노드 가져오기:
태그명으로 얻어 오기
document.getElementsTagName("태그명");
name속성으로 얻어 오기
document.getElementsByName("name속성 값");
클래스명으로 얻어오기
document.getElementsByClassName("클래스명")
id값으로 얻어 오기
document.getElementById("id속성값");
querySelector('css선택자')
일치하는 요소가 있으면 무조건 첫번째 요소만 반환.없으면 null반환
querySelectorAll('css선택자')
일치하는 모든 요소반환(Nodelist) 없으면 length가 0인 Nodelist반환
속성
childNodes속성는 텍스트나 주석등도 노드로 처리
children속성은 태그만 노드로 처리
아래는 엘리먼트 노드뿐만 아니라 텍스트 노드도 대상이된다
parentNode
firstChild 는 children[0]과 같다
lastChild
previousSibling
nextSibling
엘리먼트 노드(태그) 대상일때는
parentElement
firstElementChild 는 children[0]과 같다
lastElementChild
previousElementSibling
nextElementSibling
*/
<body>
<h2>DOM API 사용하기:노드 추가하기</h2>
<fieldset>
<legend>표 설정하기</legend>
<input type="text" class="table" /> 행
<input type="text" class="table" /> 렬 <button>표만들기</button>
</fieldset>
<div class="box">
<span>여기에 표를 위치 시킵니다.</span>
</div>
</body>
▲ 우리는 현재 body태그안에 위와같은 형태의 코드를 먼저 깔고 시작한다.
▲ body태그의 브라우저 실행시 결과
우리의 목표는 행과 열을 입력하고 표만들기 버튼을 누르면 '여기에 표를 위치 시킵니다' 를 기준으로 위 또는 아래에 표를 만들어지게 하는 것이다.
window.addEventListener('load', function () {
var fieldset = document.querySelector('fieldset');
var span = document.querySelector('div.box > span');
var divNode = document.querySelector('.box');
var button = fieldset.querySelector('button');
/*
태그명으로 얻어 오기
document.getElementsTagName("태그명");
name속성으로 얻어 오기
document.getElementsByName("name속성 값");
클래스명으로 얻어오기
document.getElementsByClassName("클래스명")
id값으로 얻어 오기
document.getElementById("id속성값");
querySelector('css선택자')
일치하는 요소가 있으면 무조건 첫번째 요소만 반환.없으면 null반환
querySelectorAll('css선택자')
일치하는 모든 요소반환(Nodelist) 없으면 length가 0인 Nodelist반환
*/
▲ document객체의 querySelector함수를 이용해서 필요한 요소들을 가져온다. 다양한 함수로 얻어올 수 있지만 querySelector가 제일 무난하여 본인은 querySelector로 요소를 가져왔다.
button.onclick = function () {
var row = parseInt(fieldset.children[1].value);
var column = parseInt(fieldset.children[2].value);
//1.table 엘리먼트 생성
var table = document.createElement('table');
//속성 추가
table.setAttribute('style', 'background-color:black;border-spacing:1px');
for (var i = 1; i <= row; i++) {
//2.tr엘리먼트 생성
var tr = document.createElement("tr");
tr.setAttribute('style', 'background-color:white;');
for (var k = 1; k <= column; k++) {
//3.td엘리먼트 생성
var td = document.createElement("td");
var textNode = document.createTextNode(i + '행' + k + "열");
//4.텍스트 노드를 td에 추가
td.append(textNode);
//5.생성된 td를 tr에 추가
tr.append(td);
}
//6.tr을 table에 추가
table.append(tr);
}
//7.table을 div에 추가
divNode.append(table);
};
});
▲ 본격적으로 createElement로 요소를 만들어나가고 각 요소들을 부모element에 append해서 붙여준다.
최종적으로 DOM tree에 붙여야 브라우저에 출력되므로 DOM tree에 붙어있는 divNode에 붙이면 된다.
또다른 예제를 보자
<body>
<h2>DOM API 사용하기:노드 삭제하기</h2>
<fieldset>
<legend>행 삭제하기</legend>
<table style="width:400px;background-color:black;border-spacing: 1px;text-align: center;">
<tr style="background-color: white;">
<td><input type="checkbox" value="1"/></td>
<td>1행1열</td>
<td>1행2열</td>
<td>1행3열</td>
</tr>
<tr style="background-color: white;">
<td><input type="checkbox" value="2"/></td>
<td>2행1열</td>
<td>2행2열</td>
<td>2행3열</td>
</tr>
<tr style="background-color: white;">
<td><input type="checkbox" value="3"/></td>
<td>3행1열</td>
<td>3행2열</td>
<td>3행3열</td>
</tr>
<tr style="background-color: white;">
<td><input type="checkbox" value="4"/></td>
<td>4행1열</td>
<td>4행2열</td>
<td>4행3열</td>
</tr>
<tr style="background-color: white;">
<td><input type="checkbox" value="5"/></td>
<td>5행1열</td>
<td>5행2열</td>
<td>5행3열</td>
</tr>
</table>
<hr/>
<button>행 삭제하기</button>
</fieldset>
</body>
▲ 위 처럼 테이블을 만들었다. 우리의 목표는 삭제하고 싶은 행의 checkbox에 check를 한 뒤 행 삭제하기 버튼을 누르면 check된 행이 삭제되는 기능을 만드는 것이다.
<script>
var table = document.querySelector('table');
var button = document.querySelector('button');
button.onclick=function(){
//체크한 체크박스들 얻기
var checkboxes=table.querySelectorAll('input[type=checkbox]:checked');
console.log(checkboxes.length);
//체크한 체크박스의 부모인 tr삭제
checkboxes.forEach(function(checkbox,index){
console.log('%s:%s',checkbox.value,index);
checkbox.parentElement.parentElement.remove();
});
};
</script>
▲ script태그지만 이번에는 addEventListener를 사용하지 않기위해서 body태그 안에 넣어보았다.
▲ 4행을 삭제하고 다시 3행을 삭제해보았다.
이처럼 DOM을 잘 알면 JS를 사용하여 HTML파일을 원하는대로 제어할 수 있다.
'JavaScript > Javascript_Advanced' 카테고리의 다른 글
[JS]DOM(Document Object Model) part.3 (0) | 2022.04.15 |
---|---|
[JS]DOM(Document Object Model) part.2 (0) | 2022.04.14 |
[JS]Function(함수) part.4 (0) | 2022.04.12 |
[JS]Function(함수) part.3 (0) | 2022.04.12 |
[JS]Function(함수) part.2 (0) | 2022.04.12 |