LWC에서 재귀적인 구성 요소 직접 제작

1. 목적



React나 Vue에서의 컴포넌트 필요에 따라서, 때때로 공통 처리를 위해서, 재귀적인 컴퍼넌트를 구현한 적이 있습니다만, 이번 LWC에서의 재귀적인 컴포넌트의 구현 방법을 공유합니다.

2. 소스 구성도


lwc
 ├─menu
 ├─menuItem
 └─menuContainer

menu





menu.html
<template>
    <div class="slds-dropdown-trigger slds-dropdown-trigger_click slds-is-open">
        <div class="slds-dropdown slds-dropdown_left slds-dropdown_small">
            <ul class="slds-dropdown__list">
                <c-menu-item child-items={_items}>
                </c-menu-item>
            </ul>
        </div>
    </div>
</template>

menu.js
import { LightningElement, api } from 'lwc';

export default class Menu extends LightningElement {

    @api get items() {
        return this._items || [];
    }

    set items(value) {
        this._items = value;
    }
}

menu.js-meta.xml
<?xml version="1.0" encoding="UTF-8"?>
<LightningComponentBundle xmlns="http://soap.sforce.com/2006/04/metadata">
    <apiVersion>52.0</apiVersion>
    <isExposed>false</isExposed>
</LightningComponentBundle>

menuItem





menuItem.html
<template>
    <template for:each={_children} for:item="it" for:index="index">
        <template if:false={it.items}>
            <li class="slds-dropdown__item" role="presentation" key={item}>
                <a href="#">
                    <span class="slds-truncate" title={it.label}>{it.label}</span>
                </a>
            </li>
        </template>
        <template if:true={it.items}>
            <li class="slds-dropdown__header slds-truncate" key={item}>
                <span title={it.label}>{it.label}</span>
            </li>
            <c-menu-item child-items={it.items} key={item}></c-menu-item>
        </template>
    </template>
</template>

menuItem.js
import { LightningElement, api, track } from 'lwc';

export default class MenuItem extends LightningElement {
    @track _children = [];

    /**
     * childItemsを取得
     */
    @api
    get childItems() {
        return this._children;
    }

    /**
     * childItemsを設定
     * @param {any} value
     */
    set childItems(value) {
        this._children = value || [];
    }
}

menuItem.js-meta.xml
<?xml version="1.0" encoding="UTF-8"?>
<LightningComponentBundle xmlns="http://soap.sforce.com/2006/04/metadata">
    <apiVersion>52.0</apiVersion>
    <isExposed>false</isExposed>
</LightningComponentBundle>

menuContainer





menuContainer.html
<template>
    <div class="slds-card" style="height:500px;width:1200px">
        <c-menu items={items}></c-menu>
    </div>
</template>

menuContainer.js
import { LightningElement, track } from 'lwc';

export default class MenuContainer extends LightningElement {

    @track items = [{
            label: 'メニュー1',
            items: [{
                label: 'サブメニュー1-1',
            }, {
                label: 'サブメニュー1-2',
            }, ],
        },
        {
            label: 'メニュー2',
            items: [{
                label: 'サブメニュー2-1',
            }, {
                label: 'サブメニュー2-2',
            }, ],
        },
    ];
}

menuContainer.js-meta.xml
<?xml version="1.0" encoding="UTF-8"?>
<LightningComponentBundle xmlns="http://soap.sforce.com/2006/04/metadata">
    <apiVersion>52.0</apiVersion>
    <isExposed>false</isExposed>
</LightningComponentBundle>

3. 로칼로 동작 확인



menuContainer 중에 마우스 오른쪽 버튼을 클릭하고 SFDX:Preview Component Locally
Use Desktop Browser 선택하기


서버를 시작하고 브라우저를 자동으로 엽니다.


4. 참고

좋은 웹페이지 즐겨찾기