ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • shadow Dom, template로 html모듈화
    JavaScript ES6 2022. 6. 3. 13:54
    <input type="range">

    이런 태그들이 위처럼 생긴건 shadow DOM덕분이다. 저건 실제로 div태그들을 겹쳐서 만든건데, 개발자도구에서 

    'show user agent shadow DOM'을 클릭하면 확인가능하다.

     

    이 shadow DOM을 만들어보자.

    <div id="morder"></div>
    
        <script>
    
            document.querySelector('#mordor').attachShadow({mode:'open'}) 
            //어둠의 공간을 열어주는 함수 즉, shadowRoot라고 div안에 숨길 html의 공간을 열어주는 함수
            document.querySelector('#mordor').shadowRoot.innerHTML = '<p>안녕</p>'
    
        </script>

    기본적으론 html태그를 찾고, 거기에 attachShadow를 붙여서 shadowRoot를 열어주고, 거기에 숨길 태그를 넣어주는 것이다.

     

    이걸 Web Components와 합치면 html모듈을 만들 수 있다.

    <custom-input></custom-input>
    
    <template id="template1">
    	<label>이메일인풋이에요</label><input>
        	<style>label { color : red }</style>
    </template>
    
    <script>
    
    	class 클래스 extends HTMLElement {
    		connectedCallback() {
        			this.attachShadow({mode:'open'});
                    	this.shadowRoot.append(template1.content.cloneNode(true));
                        
                        	let el = this.shadowRoot.querySelector('label');
                        	el.addEventListener('click', function(){
                        		console.log('클릭함')
                        	});
            }
    
    	customElements.define('custom-input',클래스);
        
    </script>

    여기서 만약 스타일을 넣고 싶을때, innerHTML에 <style></style>태그를 넣어서 label {color:red} 하면 모든 label태그가 빨간색이 된다. 이렇게 쓰면 컴포넌트끼리 스타일도 겹치기 때문에 위험하다.

    이럴때, shadow DOM을 쓰면 좋다. 위처럼 shadowRoot를 열어서 그 안에 html을 넣어주면 다른 태그에 영향을 주지 않는다.

    그리고 좀 더 깨끗하게 하려면 html 임시보관함을 사용할 수 있다. template태그를 쓰면 되는데, 위처럼 template를 만들고, append해줄 수 있다.

     

    만약, label태그를 누르는 이벤트리스너를 작성하고 싶으면, label태그를 shadowRoot에 저장하고, shadowDOM에 부착하면 된다.

    'JavaScript ES6' 카테고리의 다른 글

    Web components로 커스텀 html태그 만들기  (0) 2022.06.03
    Map / Set자료형  (0) 2022.06.03
    Symbol자료형  (0) 2022.06.03
    for in / for of 반복문  (0) 2022.06.02
    async / await  (0) 2022.06.02

    댓글

Designed by Tistory.