포스트

JS Custom Elements, 사용자 정의 태그

JS Custom Elements, 사용자 정의 태그

이 글은 Tistory에서 이전된 포스팅입니다. 원본은 여기에서 확인할 수 있습니다.

Custom Elements

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
class Test extends HTMLElement {
    constructor() {
        // super()를 호출함으로써 시작하여 올바른 프로토타입 체인이 확립되도록 한다.
        super();
    }
    static get observedAttributes() {
        // 모니터링 할 속성 이름
        // 이 메서드는 관찰하기를 원하는 특성들의 이름을 포함하는 배열을 return 해야 한다.
        return ['c', 'l'];
    }
    connectedCallback() {
        // 사용자 정의 요소가 문서에 연결된 요소에 추가될 때마다 호출된다. 
        // 이것은 노드가 이동될 때마다 발생할 것이며, 요소의 내용이 완전히 해석되기 전에 발생할 지도 모른다.
        // DOM에 추가되었다. 렌더링 등의 처리를 하자.
        this.start();
    }
    disconnectedCallback() {
        // 사용자 정의 요소가 document의 DOM에서 연결 해제되었을 때마다 호출된다.
        // DOM에서 제거되었다. 엘리먼트를 정리하는 일을 하자.
        this.stop();
    }
    attributeChangedCallback(name, oldVal, newVal) {
        // 속성이 추가/제거/변경되었다.
        // 어떤 특성이 변경에 대해 알릴지는 static get observedAttributes 메서드에서 명시된다.
    }
    adoptedCallback(oldDoc, newDoc) {
        // 사용자 정의 요소가 새로운 document로 이동되었을 때마다 호출된다.
        // 다른 Document에서 옮겨져 왔다, 자주 쓸 일은 없을 것.
    }
}
customElements.define('test-tag', Test);

js만으로 컴포넌트 단위를 만들 수 있다. 위의 코드처럼 클래스에서 적절한 생명 주기 콜백을 정의하여 사용할  수도 있고

클래스의 인스턴스가 인스턴스화되었을 때 요소가 가질 모든 기능을 클래스 내에 정의할 수도 있다.

tag이름은 규칙이 있다. 하이픈( - )을 하나 이상 포함해야하고 대문자는 안되는 듯 하다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
class SignUpModal extends HTMLElement {
    connectedCallback() {
        ....
        this.innerHTML = `
        <div id="signup-modal" class="modal">
            <div class="modal-content">
                <h2>회원가입</h2>
                <form id="signup-form" onsubmit="return false;">
                    <label for="email">Email:</label>
                    <input type="email" id="email" name="email"><br><br>
                    <label for="username">Username:</label>
                    <input type="text" id="username" name="username"><br><br>
                    <label for="password">Password:</label>
                    <input type="password" id="password" name="password"><br><br>
                    <button type="submit">가입하기</button>
                </form>
                <button id="signup-modal-close">닫기</button>
            </div>
        </div>
        `;        
        const modal = document.querySelector("#signup-modal");
        const formElem = document.querySelector("#signup-form");
        const closeModalButton = document.querySelector("#signup-modal-close");
        ...
    }
}

위와 같이 connectedCallback에 innerHTML을 통해 사용자 정의 태그를 사용할 수도 있다.

단 connectedCallback의 설명에 “사용자 정의 요소가 문서에 연결된 요소에 추가될 때마다 호출된다. 이것은 노드가 이동될 때마다 발생할 것이며, 요소의 내용이 완전히 해석되기 전에 발생할 지도 모른다.”

라는 부분을 주의할 필요가 있다.

참고 자료

https://developer.mozilla.org/ko/docs/Web/API/Web_components/Using_custom_elements

https://velog.io/@design0728/Web-Component-8njgyg44

이 기사는 저작권자의 CC BY-NC 4.0 라이센스를 따릅니다.