import { __esDecorate, __runInitializers } from "tslib";
import { cancelEvent } from '@api-client/core/lib/events/Utils.js';
import { html, nothing } from 'lit';
import { property, queryAsync, state } from 'lit/decorators.js';
import { classMap } from 'lit/directives/class-map.js';
import { when } from 'lit/directives/when.js';
import { UiElement } from '../../UiElement.js';
import { ripple } from '../../effects/rippleDirective.js';
import { close, arrowDropDown, check } from '../../icons/Icons.js';
import { setDisabled } from '../../../lib/disabled.js';
import '../../ripple/ui-ripple.js';
export var ChipType;
(function (ChipType) {
    ChipType["assist"] = "assist";
    ChipType["filter"] = "filter";
    ChipType["input"] = "input";
    ChipType["suggestion"] = "suggestion";
})(ChipType || (ChipType = {}));
let UiChip = (() => {
    let _classSuper = UiElement;
    let _disabled_decorators;
    let _disabled_initializers = [];
    let _disabled_extraInitializers = [];
    let _type_decorators;
    let _type_initializers = [];
    let _type_extraInitializers = [];
    let _elevated_decorators;
    let _elevated_initializers = [];
    let _elevated_extraInitializers = [];
    let _closable_decorators;
    let _closable_initializers = [];
    let _closable_extraInitializers = [];
    let _checked_decorators;
    let _checked_initializers = [];
    let _checked_extraInitializers = [];
    let _list_decorators;
    let _list_initializers = [];
    let _list_extraInitializers = [];
    let _ripple_decorators;
    let _ripple_initializers = [];
    let _ripple_extraInitializers = [];
    let _showRipple_decorators;
    let _showRipple_initializers = [];
    let _showRipple_extraInitializers = [];
    let _hasIcon_decorators;
    let _hasIcon_initializers = [];
    let _hasIcon_extraInitializers = [];
    let _hasAvatar_decorators;
    let _hasAvatar_initializers = [];
    let _hasAvatar_extraInitializers = [];
    return class UiChip extends _classSuper {
        static {
            const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(_classSuper[Symbol.metadata] ?? null) : void 0;
            _disabled_decorators = [property({ type: Boolean, reflect: true })];
            _type_decorators = [property({ type: String })];
            _elevated_decorators = [property({ type: Boolean, reflect: true })];
            _closable_decorators = [property({ type: Boolean, reflect: true })];
            _checked_decorators = [property({ type: Boolean, reflect: true })];
            _list_decorators = [property({ type: String, reflect: true })];
            _ripple_decorators = [queryAsync('ui-ripple')];
            _showRipple_decorators = [state()];
            _hasIcon_decorators = [state()];
            _hasAvatar_decorators = [state()];
            __esDecorate(this, null, _disabled_decorators, { kind: "accessor", name: "disabled", static: false, private: false, access: { has: obj => "disabled" in obj, get: obj => obj.disabled, set: (obj, value) => { obj.disabled = value; } }, metadata: _metadata }, _disabled_initializers, _disabled_extraInitializers);
            __esDecorate(this, null, _type_decorators, { kind: "accessor", name: "type", static: false, private: false, access: { has: obj => "type" in obj, get: obj => obj.type, set: (obj, value) => { obj.type = value; } }, metadata: _metadata }, _type_initializers, _type_extraInitializers);
            __esDecorate(this, null, _elevated_decorators, { kind: "accessor", name: "elevated", static: false, private: false, access: { has: obj => "elevated" in obj, get: obj => obj.elevated, set: (obj, value) => { obj.elevated = value; } }, metadata: _metadata }, _elevated_initializers, _elevated_extraInitializers);
            __esDecorate(this, null, _closable_decorators, { kind: "accessor", name: "closable", static: false, private: false, access: { has: obj => "closable" in obj, get: obj => obj.closable, set: (obj, value) => { obj.closable = value; } }, metadata: _metadata }, _closable_initializers, _closable_extraInitializers);
            __esDecorate(this, null, _checked_decorators, { kind: "accessor", name: "checked", static: false, private: false, access: { has: obj => "checked" in obj, get: obj => obj.checked, set: (obj, value) => { obj.checked = value; } }, metadata: _metadata }, _checked_initializers, _checked_extraInitializers);
            __esDecorate(this, null, _list_decorators, { kind: "accessor", name: "list", static: false, private: false, access: { has: obj => "list" in obj, get: obj => obj.list, set: (obj, value) => { obj.list = value; } }, metadata: _metadata }, _list_initializers, _list_extraInitializers);
            __esDecorate(this, null, _ripple_decorators, { kind: "accessor", name: "ripple", static: false, private: false, access: { has: obj => "ripple" in obj, get: obj => obj.ripple, set: (obj, value) => { obj.ripple = value; } }, metadata: _metadata }, _ripple_initializers, _ripple_extraInitializers);
            __esDecorate(this, null, _showRipple_decorators, { kind: "accessor", name: "showRipple", static: false, private: false, access: { has: obj => "showRipple" in obj, get: obj => obj.showRipple, set: (obj, value) => { obj.showRipple = value; } }, metadata: _metadata }, _showRipple_initializers, _showRipple_extraInitializers);
            __esDecorate(this, null, _hasIcon_decorators, { kind: "accessor", name: "hasIcon", static: false, private: false, access: { has: obj => "hasIcon" in obj, get: obj => obj.hasIcon, set: (obj, value) => { obj.hasIcon = value; } }, metadata: _metadata }, _hasIcon_initializers, _hasIcon_extraInitializers);
            __esDecorate(this, null, _hasAvatar_decorators, { kind: "accessor", name: "hasAvatar", static: false, private: false, access: { has: obj => "hasAvatar" in obj, get: obj => obj.hasAvatar, set: (obj, value) => { obj.hasAvatar = value; } }, metadata: _metadata }, _hasAvatar_initializers, _hasAvatar_extraInitializers);
            if (_metadata) Object.defineProperty(this, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
        }
        #disabled_accessor_storage = __runInitializers(this, _disabled_initializers, false
        /**
         * The type of the rendered chip.
         * @attribute
         *
         * @see https://m3.material.io/components/chips/guidelines
         */
        );
        /**
         * Whether the chip is disabled. The user can't interact with the chip when `true`.
         * @attribute
         */
        get disabled() { return this.#disabled_accessor_storage; }
        set disabled(value) { this.#disabled_accessor_storage = value; }
        #type_accessor_storage = (__runInitializers(this, _disabled_extraInitializers), __runInitializers(this, _type_initializers, void 0));
        /**
         * The type of the rendered chip.
         * @attribute
         *
         * @see https://m3.material.io/components/chips/guidelines
         */
        get type() { return this.#type_accessor_storage; }
        set type(value) { this.#type_accessor_storage = value; }
        #elevated_accessor_storage = (__runInitializers(this, _type_extraInitializers), __runInitializers(this, _elevated_initializers, void 0));
        /**
         * Whether the chip should be rendered as elevated.
         * @attribute
         */
        get elevated() { return this.#elevated_accessor_storage; }
        set elevated(value) { this.#elevated_accessor_storage = value; }
        #closable_accessor_storage = (__runInitializers(this, _elevated_extraInitializers), __runInitializers(this, _closable_initializers, void 0));
        /**
         * Whether the chip renders the "close" icon at the end.
         * @attribute
         */
        get closable() { return this.#closable_accessor_storage; }
        set closable(value) { this.#closable_accessor_storage = value; }
        #checked_accessor_storage = (__runInitializers(this, _closable_extraInitializers), __runInitializers(this, _checked_initializers, void 0));
        /**
         * Whether the chip is currently checked.
         * Note, this controls the presentation layer only. It has no meaning when it comes to forms and inputs.
         * @attribute
         */
        get checked() { return this.#checked_accessor_storage; }
        set checked(value) { this.#checked_accessor_storage = value; }
        #list_accessor_storage = (__runInitializers(this, _checked_extraInitializers), __runInitializers(this, _list_initializers, void 0));
        /**
         * The ID attribute of the list element that is rendered after activating the chip.
         * When this is set the chip renders the dropdown icon at the end and sets `aria-*`
         * attributes informing the assistive technology that this chip controls a list.
         *
         * @attribute
         */
        get list() { return this.#list_accessor_storage; }
        set list(value) { this.#list_accessor_storage = value; }
        #ripple_accessor_storage = (__runInitializers(this, _list_extraInitializers), __runInitializers(this, _ripple_initializers, void 0));
        get ripple() { return this.#ripple_accessor_storage; }
        set ripple(value) { this.#ripple_accessor_storage = value; }
        #showRipple_accessor_storage = (__runInitializers(this, _ripple_extraInitializers), __runInitializers(this, _showRipple_initializers, false
        /**
         * Determines when the element has an icon in the "icon" slot.
         */
        ));
        get showRipple() { return this.#showRipple_accessor_storage; }
        set showRipple(value) { this.#showRipple_accessor_storage = value; }
        #hasIcon_accessor_storage = (__runInitializers(this, _showRipple_extraInitializers), __runInitializers(this, _hasIcon_initializers, void 0));
        /**
         * Determines when the element has an icon in the "icon" slot.
         */
        get hasIcon() { return this.#hasIcon_accessor_storage; }
        set hasIcon(value) { this.#hasIcon_accessor_storage = value; }
        #hasAvatar_accessor_storage = (__runInitializers(this, _hasIcon_extraInitializers), __runInitializers(this, _hasAvatar_initializers, void 0));
        /**
         * Determines when the element has an image in the "avatar" slot.
         */
        get hasAvatar() { return this.#hasAvatar_accessor_storage; }
        set hasAvatar(value) { this.#hasAvatar_accessor_storage = value; }
        constructor() {
            super();
            this.disabled = false;
            this.type = ChipType.assist;
            this.hasIcon = false;
            this.hasAvatar = false;
            this.actionController.cancelKeyboardEvents = true;
            this.addEventListener('click', this.handleClick.bind(this));
            this.addEventListener('keydown', this.handleKeyDown.bind(this));
            this.addEventListener('keyup', this.handleKeyUp.bind(this));
            this.addEventListener('pointerdown', this.handlePointerDown.bind(this));
            this.addEventListener('pointerup', this.handlePointerUp.bind(this));
            this.addEventListener('pointercancel', this.handlePointerCancel.bind(this));
            this.addEventListener('pointerleave', this.handlePointerLeave.bind(this));
            this.addEventListener('contextmenu', this.handleContextMenu.bind(this));
            this.addEventListener('focus', this.handleFocus.bind(this));
            this.addEventListener('blur', this.handleBlur.bind(this));
        }
        connectedCallback() {
            super.connectedCallback();
            if (!this.hasAttribute('role')) {
                this.setAttribute('role', 'button');
            }
            if (!this.hasAttribute('tabindex') && !this.disabled) {
                this.setAttribute('tabindex', '0');
            }
        }
        willUpdate(cp) {
            if (cp.has('disabled')) {
                setDisabled(this, cp.get('disabled'));
            }
        }
        async pressRipple() {
            const element = await this.getRipple();
            if (element && !element.isPressed) {
                element.beginPress();
            }
        }
        async endRipple() {
            const element = await this.getRipple();
            element?.endPress();
        }
        beginPress(options) {
            super.beginPress(options);
            this.pressRipple();
        }
        async handleKeyDown(e) {
            super.handleKeyDown(e);
            if (this.type === ChipType.filter && e.code === 'ArrowDown') {
                e.preventDefault();
                this.listAction();
            }
            else if (this.closable && e.code === 'Backspace') {
                e.preventDefault();
                this.closeAction();
            }
        }
        async handleFocus() {
            const element = await this.getRipple();
            element?.beginFocus();
        }
        async handleBlur() {
            const element = await this.getRipple();
            element?.endFocus();
        }
        getRipple = (__runInitializers(this, _hasAvatar_extraInitializers), () => {
            this.showRipple = true;
            return this.ripple;
        });
        endPress(info) {
            super.endPress(info);
            this.endRipple();
            const { cancelled, reason } = info;
            if (cancelled) {
                return;
            }
            if (reason === 'enter' || reason === 'space') {
                this.click();
            }
        }
        handleClick(e) {
            super.handleClick(e);
            if (this.type === ChipType.filter) {
                this.toggleChecked();
            }
        }
        /**
         * Toggles the "filter" type of the chip.
         */
        toggleChecked() {
            this.checked = !this.checked;
            this.dispatchEvent(new Event('select'));
        }
        /**
         * Sets the `hasIcon` state property when the "icon" slot change event is dispatched.
         */
        handleIconSlotChange(e) {
            const slot = e.target;
            this.hasIcon = !!slot.assignedNodes().length;
        }
        /**
         * Sets the `_hasAvatar` state property when the "avatar" slot change event is dispatched.
         */
        handleAvatarSlotChange(e) {
            const slot = e.target;
            this.hasAvatar = !!slot.assignedNodes().length;
        }
        handleListClick(e) {
            e.preventDefault();
            e.stopPropagation();
            this.listAction();
        }
        handleClose(e) {
            e.preventDefault();
            e.stopPropagation();
            this.closeAction();
        }
        async closeAction() {
            this.dispatchEvent(new Event('close'));
        }
        async listAction() {
            this.dispatchEvent(new Event('list'));
        }
        render() {
            const { pressed = false } = this;
            const containerClasses = classMap({
                surface: true,
                withIcon: this.hasIcon,
                withAvatar: this.hasAvatar,
                pressed,
            });
            return html `
      <div class="${containerClasses}" ${ripple(this.getRipple)}>
        <div class="container"></div>
        ${when(this.showRipple, this.renderRipple)}
        <div class="content">
          ${this.renderLeadingIcon()} ${this.renderAvatar()}
          <slot></slot>
          ${this.renderTrailingIcon()}
        </div>
      </div>
    `;
        }
        renderLeadingIcon() {
            const { type } = this;
            if (type === ChipType.suggestion) {
                return nothing;
            }
            if (type === ChipType.filter) {
                const iconClasses = classMap({
                    'leading-icon': true,
                    'check-mark': true,
                    'checked': !!this.checked,
                });
                return html `<span class="${iconClasses}" role="presentation">${check}</span>`;
            }
            return html `<slot name="icon" @slotchange="${this.handleIconSlotChange}"></slot>`;
        }
        renderAvatar() {
            const { type } = this;
            if (type === ChipType.input) {
                return html `<slot name="avatar" @slotchange="${this.handleAvatarSlotChange}"></slot>`;
            }
            return nothing;
        }
        renderTrailingIcon() {
            const { closable = false, list, type } = this;
            if (type === ChipType.filter) {
                if (list) {
                    return html `<span
          class="trailing-icon"
          role="presentation"
          @click="${this.handleListClick}"
          @keypress="${cancelEvent}"
          >${arrowDropDown}</span
        >`;
                }
            }
            if (type === ChipType.input && closable) {
                return html `<span
        class="trailing-icon"
        @click="${this.handleClose}"
        @keypress="${cancelEvent}"
        role="button"
        aria-label="Activate to close or disabled this chip."
        >${close}</span
      >`;
            }
            return nothing;
        }
        renderRipple = () => {
            const { disabled } = this;
            return html `<ui-ripple class="ripple" ?disabled="${disabled}"></ui-ripple>`;
        };
    };
})();
/**
 * @slot icon - The leading icon, sized 18x18 px
 * @slot avatar - The leading image, sized 24x24 px
 * @fires list - When the user requested to activate the list associated with the element.
 * @fires select - When the checked state changed through a user interaction. This only related to
 *                 `filter` chips. Note, `select` is dispatched just before the `click` event.
 */
export default UiChip;
//# sourceMappingURL=Chip.js.map