'use client';
'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

var tslib = require('tslib');
var decorators_js = require('lit/decorators.js');
var classMap_js = require('lit/directives/class-map.js');
var ifDefined_js = require('lit/directives/if-defined.js');
var live_js = require('lit/directives/live.js');
var staticHtml_js = require('lit/static-html.js');
var formControlElement = require('../../base/form-control-element.cjs.js');
var formPlaceholder = require('../../styles/form-placeholder.cjs.js');
var svg = require('../../styles/svg.cjs.js');
var defaultvalue = require('../../utils/defaultvalue.cjs.js');
var validatorMixin = require('../../utils/validatorMixin.cjs.js');
var sgdsIconButton = require('../IconButton/sgds-icon-button.cjs.js');
var sgdsInput = require('../Input/sgds-input.cjs.js');
var quantityToggle = require('./quantity-toggle.cjs.js');
var formTextControl = require('../../styles/form-text-control.cjs.js');

/**
 * @summary The quantity toggle component is used to increase or decrease an incremental venue,  best used when the user needs to enter or adjust the quantity of a selected item.
 *
 * @slot invalidIcon - The slot for invalid icon
 *
 * @event sgds-change - Emitted when an alteration to the control's value is committed by the user.
 * @event sgds-input - Emitted when the control receives input and its value changes.
 *
 */
class SgdsQuantityToggle extends validatorMixin.SgdsFormValidatorMixin(formControlElement["default"]) {
    constructor() {
        super(...arguments);
        /** The input's value. Set to 0 by default */
        this.value = 0;
        /**  Controls the incremental / decremental value of the input */
        this.step = 1;
        /** Sets the quantity toggle as readonly  */
        this.readonly = false;
        /** Gets or sets the default value used to reset this element. The initial value corresponds to the one originally specified in the HTML that created this element. */
        this.defaultValue = 0;
    }
    /**
     * Checks for validity. Under the hood, HTMLFormElement's reportValidity method calls this method to check for component's validity state
     * Note that the native error popup is prevented for SGDS form components by default. Instead the validation message shows up in the feedback container of SgdsInput
     */
    reportValidity() {
        return this._mixinReportValidity();
    }
    /**
     * Checks for validity without any native error popup message
     */
    checkValidity() {
        return this._mixinCheckValidity();
    }
    /**
     * Returns the ValidityState object
     */
    get validity() {
        return this._mixinGetValidity();
    }
    /**
     * Returns the validation message based on the ValidityState
     */
    get validationMessage() {
        return this._mixinGetValidationMessage();
    }
    async _handleChange() {
        const sgdsInput = await this._sgdsInput;
        if (parseInt(sgdsInput.value) < this.step || sgdsInput.value === "") {
            sgdsInput.value = "0";
        }
        this.value = parseInt(sgdsInput.value);
        this._mixinSetFormValue();
        this._mixinValidate(sgdsInput.input);
        this.invalid = !this._mixinReportValidity();
    }
    async _handleInputChange() {
        const sgdsInput = await this._sgdsInput;
        this.invalid = false;
        if (parseInt(sgdsInput.value) < this.step || sgdsInput.value === "") {
            sgdsInput.value = "0";
        }
        this.value = parseInt(sgdsInput.value);
        this._mixinSetFormValue();
        this._mixinValidate(sgdsInput.input);
    }
    async _mixinResetFormControl() {
        const sgdsInput = await this._sgdsInput;
        this.value = this.defaultValue;
        sgdsInput.input.value = this.value.toString();
        this._mixinResetValidity(sgdsInput.input);
    }
    _handleKeyDown(event) {
        const allowedKeys = [
            "Backspace",
            "ArrowUp",
            "ArrowDown",
            "ArrowLeft",
            "ArrowRight",
            ...Array.from(Array(10).keys()).map(key => key.toString()),
            "Tab"
        ];
        // Allow keydown event only if the pressed key is in the allowedKeys array
        if (!allowedKeys.includes(event.key)) {
            event.preventDefault();
        }
    }
    _handleInvalid() {
        this.invalid = true;
    }
    _handleValid() {
        this.invalid = false;
    }
    /** Simulates a click on the plus button */
    plus() {
        this.plusBtn.click();
    }
    /** Simulates a click on the minus button */
    minus() {
        this.minusBtn.click();
    }
    async _onPlus(event) {
        const sgdsInput = await this._sgdsInput;
        event.preventDefault();
        event.stopPropagation();
        this.value = parseInt(sgdsInput.value) + parseInt(sgdsInput.step.toString());
        this._validateOnClick(sgdsInput.input);
    }
    async _onMinus(event) {
        const sgdsInput = await this._sgdsInput;
        event.preventDefault();
        event.stopPropagation();
        if (this.value < this.step) {
            this.value = 0;
        }
        else {
            this.value = parseInt(sgdsInput.value) - parseInt(sgdsInput.step.toString());
        }
        this._validateOnClick(sgdsInput.input);
    }
    /**
     * Validates the input on button clicks of the toggle.
     * Input is validated every time the button is click to update the invalid state
     * to indiciate the validity of quantity toggle
     * @param input native HTMLInputElement
     */
    async _validateOnClick(input) {
        const sgdsInput = await this._sgdsInput;
        await sgdsInput.updateComplete;
        this._mixinSetFormValue();
        this._mixinValidate(input);
        this.invalid = !this._mixinReportValidity();
    }
    _renderFeedback() {
        const wantFeedbackText = this.hasFeedback === "both" || this.hasFeedback === "text";
        return this.invalid && wantFeedbackText
            ? staticHtml_js.html ` <div class="invalid-feedback-container">
          <slot name="invalidIcon">
            <svg xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" fill="none">
              <path
                d="M17.5 10C17.5 14.1421 14.1421 17.5 10 17.5C5.85786 17.5 2.5 14.1421 2.5 10C2.5 5.85786 5.85786 2.5 10 2.5C14.1421 2.5 17.5 5.85786 17.5 10ZM10 6.25C9.49805 6.25 9.10584 6.68339 9.15578 7.18285L9.48461 10.4711C9.51109 10.7359 9.7339 10.9375 10 10.9375C10.2661 10.9375 10.4889 10.7359 10.5154 10.4711L10.8442 7.18285C10.8942 6.68339 10.5019 6.25 10 6.25ZM10.0014 11.875C9.48368 11.875 9.06394 12.2947 9.06394 12.8125C9.06394 13.3303 9.48368 13.75 10.0014 13.75C10.5192 13.75 10.9389 13.3303 10.9389 12.8125C10.9389 12.2947 10.5192 11.875 10.0014 11.875Z"
                fill="currentColor"
              />
            </svg>
          </slot>
          <div id="${this._controlId}-invalid" class="invalid-feedback">
            ${this.invalidFeedback ? this.invalidFeedback : this.validationMessage}
          </div>
        </div>`
            : staticHtml_js.html `${this._renderHintText()}`;
    }
    _renderLabel() {
        const labelTemplate = staticHtml_js.html `
      <label
        for=${this._controlId}
        id=${this._labelId}
        class=${classMap_js.classMap({
            "form-label": true,
            disabled: this.disabled
        })}
        >${this.label}</label
      >
    `;
        return this.label && labelTemplate;
    }
    _renderHintText() {
        const hintTextTemplate = staticHtml_js.html ` <div id="${this._controlId}Help" class="form-text">${this.hintText}</div> `;
        return this.hintText && hintTextTemplate;
    }
    render() {
        return staticHtml_js.html `
      <div class="form-control-container">
        ${this._renderLabel()}
        <div class="input-group">
          <sgds-icon-button
            variant="ghost"
            ariaLabel=${`decrease by ${this.step}`}
            ?disabled=${this.disabled ||
            (this.min !== undefined ? this.value <= this.min : this.value < 1) ||
            this.readonly}
            @click=${this._onMinus}
            name="dash"
          >
          </sgds-icon-button>
          <sgds-input
            type="number"
            class="quantity-toggle"
            name=${ifDefined_js.ifDefined(this.name)}
            step=${ifDefined_js.ifDefined(this.step)}
            min=${ifDefined_js.ifDefined(this.min)}
            max=${ifDefined_js.ifDefined(this.max)}
            .value=${live_js.live(this.value)}
            @sgds-change=${this._handleChange}
            @sgds-input=${this._handleInputChange}
            @sgds-invalid=${this._handleInvalid}
            @sgds-valid=${this._handleValid}
            @keydown=${this._handleKeyDown}
            ?disabled=${this.disabled}
            id=${this._controlId}
            ?invalid=${this.invalid}
            hasFeedback=${ifDefined_js.ifDefined(this.hasFeedback !== "text" ? "style" : undefined)}
          ></sgds-input>
          <sgds-icon-button
            variant="ghost"
            ariaLabel=${`increase by ${this.step}`}
            @click=${this._onPlus}
            ?disabled=${this.disabled ||
            (this.max !== undefined && this.max && this.value >= this.max) ||
            this.readonly}
            name="plus"
          >
          </sgds-icon-button>
        </div>
        <div id="announcer" role="region" aria-live="assertive" class="visually-hidden">${this.value}</div>
        ${this._renderFeedback()}
      </div>
    `;
    }
}
SgdsQuantityToggle.styles = [
    ...formControlElement["default"].styles,
    formPlaceholder["default"],
    svg["default"],
    formTextControl["default"],
    quantityToggle["default"]
];
/** @internal */
SgdsQuantityToggle.dependencies = {
    "sgds-input": sgdsInput.SgdsInput,
    "sgds-icon-button": sgdsIconButton.SgdsIconButton
};
tslib.__decorate([
    decorators_js.query("sgds-icon-button[ariaLabel^='increase by']")
], SgdsQuantityToggle.prototype, "plusBtn", void 0);
tslib.__decorate([
    decorators_js.query("sgds-icon-button[ariaLabel^='decrease by']")
], SgdsQuantityToggle.prototype, "minusBtn", void 0);
tslib.__decorate([
    decorators_js.property({ type: Number, reflect: true })
], SgdsQuantityToggle.prototype, "value", void 0);
tslib.__decorate([
    decorators_js.property({ type: Number })
], SgdsQuantityToggle.prototype, "step", void 0);
tslib.__decorate([
    decorators_js.property({ type: Number })
], SgdsQuantityToggle.prototype, "min", void 0);
tslib.__decorate([
    decorators_js.property({ type: Number })
], SgdsQuantityToggle.prototype, "max", void 0);
tslib.__decorate([
    decorators_js.property({ type: String, reflect: true })
], SgdsQuantityToggle.prototype, "hasFeedback", void 0);
tslib.__decorate([
    decorators_js.property({ type: String, reflect: true })
], SgdsQuantityToggle.prototype, "invalidFeedback", void 0);
tslib.__decorate([
    decorators_js.property({ type: Boolean, reflect: true })
], SgdsQuantityToggle.prototype, "readonly", void 0);
tslib.__decorate([
    defaultvalue.defaultValue()
], SgdsQuantityToggle.prototype, "defaultValue", void 0);
tslib.__decorate([
    decorators_js.queryAsync("sgds-input")
], SgdsQuantityToggle.prototype, "_sgdsInput", void 0);

exports.SgdsQuantityToggle = SgdsQuantityToggle;
exports["default"] = SgdsQuantityToggle;
//# sourceMappingURL=sgds-quantity-toggle.cjs.js.map
