import { MDCMenu } from "@material/menu";
import { MDCRipple } from "@material/ripple";
import { strings as menuStrings } from "@material/menu/constants";
import { h, } from "@stencil/core";
import { MenuListRenderer } from "./menu-list-renderer";
const { SELECTED_EVENT } = menuStrings;
/**
 * @private
 */
export class MenuList {
    constructor() {
        /**
         * Size of the icons in the list
         */
        this.iconSize = 'small';
        this.MenuListRenderer = new MenuListRenderer();
        this.setup = () => {
            this.setupMenu();
            this.setupListeners();
        };
        this.setupMenu = () => {
            if (this.mdcMenu) {
                this.teardown();
                this.mdcMenu = null;
            }
            const element = this.element.shadowRoot.querySelector('.mdc-menu');
            if (!element) {
                return;
            }
            this.mdcMenu = new MDCMenu(element);
            this.mdcMenu.hasTypeahead = true;
            this.mdcMenu.wrapFocus = true;
            // eslint-disable-next-line sonarjs/constructor-for-side-effects
            for (const item of this.mdcMenu.items)
                new MDCRipple(item);
        };
        this.setupListeners = () => {
            if (!this.mdcMenu) {
                return;
            }
            this.mdcMenu.unlisten(SELECTED_EVENT, this.handleMenuSelect);
            this.mdcMenu.listen(SELECTED_EVENT, this.handleMenuSelect);
        };
        this.teardown = () => {
            var _a, _b;
            (_a = this.mdcMenu) === null || _a === void 0 ? void 0 : _a.unlisten(SELECTED_EVENT, this.handleMenuSelect);
            (_b = this.mdcMenu) === null || _b === void 0 ? void 0 : _b.destroy();
        };
        this.handleMenuSelect = (event) => {
            this.handleSingleSelect(event.detail.index);
        };
        this.handleSingleSelect = (index) => {
            const MenuItems = this.items.filter(this.isMenuItem);
            if (MenuItems[index].disabled) {
                return;
            }
            const selectedItem = MenuItems.find((item) => {
                return !!item.selected;
            });
            let interactedItem;
            if (selectedItem) {
                interactedItem = Object.assign(Object.assign({}, selectedItem), { selected: false });
                this.select.emit(interactedItem);
            }
            if (MenuItems[index] !== selectedItem) {
                interactedItem = Object.assign(Object.assign({}, MenuItems[index]), { selected: false });
                this.select.emit(interactedItem);
            }
            this.interact.emit(interactedItem);
        };
        this.isMenuItem = (item) => {
            return !('separator' in item);
        };
    }
    connectedCallback() {
        this.setup();
    }
    disconnectedCallback() {
        this.teardown();
    }
    componentDidLoad() {
        this.setup();
        this.triggerIconColorWarning();
    }
    render() {
        this.config = {
            badgeIcons: this.badgeIcons,
            iconSize: this.iconSize,
        };
        const html = this.MenuListRenderer.render(this.items, this.config);
        return h("div", { key: 'f2a299d2e47ed6344fd817e748b8cc22f0e0e3a7', class: "mdc-menu mdc-menu-surface" }, html);
    }
    itemsChanged() {
        setTimeout(() => {
            this.setup();
        }, 0);
    }
    triggerIconColorWarning() {
        var _a;
        if ((_a = this.items) === null || _a === void 0 ? void 0 : _a.some((item) => 'iconColor' in item)) {
            console.warn("The `iconColor` prop is deprecated, has no visual effect anymore, and will soon be removed! Use the new `Icon` interface, and instead of `iconColor: 'color-name'` write `icon: { name: 'icon-name', color: 'color-name' }`.");
        }
    }
    static get is() { return "limel-menu-list"; }
    static get encapsulation() { return "shadow"; }
    static get delegatesFocus() { return true; }
    static get originalStyleUrls() {
        return {
            "$": ["menu-list.scss"]
        };
    }
    static get styleUrls() {
        return {
            "$": ["menu-list.css"]
        };
    }
    static get properties() {
        return {
            "items": {
                "type": "unknown",
                "mutable": false,
                "complexType": {
                    "original": "Array<MenuItem | ListSeparator>",
                    "resolved": "(ListSeparator | MenuItem<any>)[]",
                    "references": {
                        "Array": {
                            "location": "global",
                            "id": "global::Array"
                        },
                        "MenuItem": {
                            "location": "import",
                            "path": "../menu/menu.types",
                            "id": "src/components/menu/menu.types.ts::MenuItem",
                            "referenceLocation": "MenuItem"
                        },
                        "ListSeparator": {
                            "location": "import",
                            "path": "../list-item/list-item.types",
                            "id": "src/components/list-item/list-item.types.ts::ListSeparator",
                            "referenceLocation": "ListSeparator"
                        }
                    }
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "List of items to display"
                },
                "getter": false,
                "setter": false
            },
            "badgeIcons": {
                "type": "boolean",
                "mutable": false,
                "complexType": {
                    "original": "boolean",
                    "resolved": "boolean",
                    "references": {}
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "Set to `true` if the list should display larger icons with a background"
                },
                "getter": false,
                "setter": false,
                "reflect": false,
                "attribute": "badge-icons"
            },
            "iconSize": {
                "type": "string",
                "mutable": false,
                "complexType": {
                    "original": "IconSize",
                    "resolved": "\"large\" | \"medium\" | \"small\" | \"x-small\"",
                    "references": {
                        "IconSize": {
                            "location": "import",
                            "path": "../icon/icon.types",
                            "id": "src/components/icon/icon.types.ts::IconSize",
                            "referenceLocation": "IconSize"
                        }
                    }
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "Size of the icons in the list"
                },
                "getter": false,
                "setter": false,
                "reflect": false,
                "attribute": "icon-size",
                "defaultValue": "'small'"
            }
        };
    }
    static get events() {
        return [{
                "method": "select",
                "name": "select",
                "bubbles": true,
                "cancelable": true,
                "composed": true,
                "docs": {
                    "tags": [],
                    "text": "Fired when a new value has been selected from the list."
                },
                "complexType": {
                    "original": "MenuItem",
                    "resolved": "MenuItem<any>",
                    "references": {
                        "MenuItem": {
                            "location": "import",
                            "path": "../menu/menu.types",
                            "id": "src/components/menu/menu.types.ts::MenuItem",
                            "referenceLocation": "MenuItem"
                        }
                    }
                }
            }, {
                "method": "interact",
                "name": "interact",
                "bubbles": true,
                "cancelable": true,
                "composed": true,
                "docs": {
                    "tags": [],
                    "text": "Fires when a user interacts with an item in the list (e.g., click,\nkeyboard select)."
                },
                "complexType": {
                    "original": "MenuItem",
                    "resolved": "MenuItem<any>",
                    "references": {
                        "MenuItem": {
                            "location": "import",
                            "path": "../menu/menu.types",
                            "id": "src/components/menu/menu.types.ts::MenuItem",
                            "referenceLocation": "MenuItem"
                        }
                    }
                }
            }];
    }
    static get elementRef() { return "element"; }
    static get watchers() {
        return [{
                "propName": "items",
                "methodName": "itemsChanged"
            }];
    }
}
