import { __decorate, __metadata } from 'tslib';
import * as i3 from '@angular/cdk/overlay';
import { CdkConnectedOverlay, CdkOverlayOrigin, OverlayModule } from '@angular/cdk/overlay';
import * as i0 from '@angular/core';
import { Injectable, Component, Input, ViewChild, EventEmitter, forwardRef, Directive, HostBinding, Output, HostListener, NgModule } from '@angular/core';
import { NG_VALUE_ACCESSOR, FormsModule } from '@angular/forms';
import * as i3$1 from 'ng-devui/i18n';
import * as i2$1 from 'ng-devui/position';
import { PositioningModule } from 'ng-devui/position';
import * as i4 from 'ng-devui/utils';
import { fadeInOut, AppendToBodyDirectionsConfig, addClassToOrigin, removeClassFromOrigin, WithConfig, LazyLoadModule, HighlightModule } from 'ng-devui/utils';
import { Subject, of, fromEvent } from 'rxjs';
import { takeUntil, map, filter, debounceTime, tap, switchMap } from 'rxjs/operators';
import * as i2 from '@angular/common';
import { CommonModule } from '@angular/common';
import * as i5 from 'ng-devui/loading';
import { LoadingModule } from 'ng-devui/loading';

class AutoCompleteConfig {
    constructor() {
        this.autoComplete = {
            delay: 300,
            minLength: 1,
            itemTemplate: null,
            noResultItemTemplate: null,
            formatter: (item) => item ? (item.label || item.toString()) : '',
            valueParser: (item) => item
        };
    }
}
AutoCompleteConfig.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteConfig, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
AutoCompleteConfig.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteConfig, providedIn: 'root' });
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteConfig, decorators: [{
            type: Injectable,
            args: [{ providedIn: 'root' }]
        }] });

class AutoCompletePopupComponent {
    constructor(autoCompleteConfig, elementRef) {
        this.autoCompleteConfig = autoCompleteConfig;
        this.elementRef = elementRef;
        this.maxHeight = 300;
        this.disabled = false;
        this.isSearching = false;
        this.appendToBody = false;
        this.cdkOverlayOffsetY = 0;
        this.showAnimation = true;
        this.activeIndex = 0;
        this.hoverIndex = 0;
        this.labelMinHeight = 20; // position.top小于20px时候，表示光标在第一行
        this.showLoading = false;
        this.popPosition = 'bottom';
        this.onChange = (_) => null;
        this.onTouched = () => null;
        this.formatter = this.autoCompleteConfig.autoComplete.formatter;
    }
    writeValue(obj) {
        this.value = obj;
    }
    setDisabledState(isDisabled) {
        this.disabled = isDisabled;
    }
    registerOnChange(fn) {
        this.onChange = fn;
    }
    registerOnTouched(fn) {
        this.onTouched = fn;
    }
    onSelect(event, item) {
        if (this.disabledKey && item && item[this.disabledKey]) {
            event.preventDefault();
            event.stopPropagation();
            return;
        }
        if (this.overview === 'single') {
            // 单选场景和单行场景不需要冒泡
            event.preventDefault();
            event.stopPropagation();
        }
        this.value = item;
        this.onTouched();
        this.onChange({ type: 'select', value: this.value });
    }
    selectCurrentItem(event) {
        this.activeIndex = this.hoverIndex;
        this.onSelect(event, this.source[this.hoverIndex]);
    }
    onActiveIndexChange(index) {
        this.activeIndex = index;
    }
    reset() {
        this.activeIndex = 0;
        this.hoverIndex = 0;
    }
    scrollToActive(index) {
        const that = this;
        setTimeout(() => {
            const scrollIndex = index === undefined ? this.activeIndex : index;
            const selectIndex = scrollIndex;
            const scrollPane = that.dropdownUl.nativeElement.children[selectIndex];
            if (scrollPane.scrollIntoViewIfNeeded) {
                scrollPane.scrollIntoViewIfNeeded(false);
            }
            else {
                const containerInfo = that.dropdownUl.nativeElement.getBoundingClientRect();
                const elementInfo = scrollPane.getBoundingClientRect();
                if (elementInfo.bottom > containerInfo.bottom || elementInfo.top < containerInfo.top) {
                    scrollPane.scrollIntoView(false);
                }
            }
        });
    }
    next() {
        if (this.isOpen && this.source && this.source.length) {
            if (this.hoverIndex === this.source.length - 1) {
                this.hoverIndex = 0;
                this.scrollToActive(this.hoverIndex);
                return;
            }
            this.hoverIndex = this.hoverIndex + 1;
            this.scrollToActive(this.hoverIndex);
        }
    }
    prev() {
        if (this.isOpen && this.source && this.source.length) {
            if (this.hoverIndex === 0) {
                this.hoverIndex = this.source.length - 1;
                this.scrollToActive(this.hoverIndex);
                return;
            }
            this.hoverIndex = this.hoverIndex - 1;
            this.scrollToActive(this.hoverIndex);
        }
    }
    trackByFn(index, item) {
        return index;
    }
    animationEnd($event) {
        if (!this.isOpen && this.selectMenuElement) {
            const targetElement = this.selectMenuElement.nativeElement;
            setTimeout(() => {
                targetElement.style.display = 'none';
            });
        }
    }
    loadMoreEvent($event) {
        this.showLoading = true;
        this.onChange({ type: 'loadMore', value: this });
    }
    loadFinish($event) {
        this.showLoading = false;
    }
    onPositionChange(position) {
        this.popPosition = position.connectionPair.originY;
    }
}
AutoCompletePopupComponent.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompletePopupComponent, deps: [{ token: AutoCompleteConfig }, { token: i0.ElementRef }], target: i0.ɵɵFactoryTarget.Component });
AutoCompletePopupComponent.ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "14.2.0", type: AutoCompletePopupComponent, selector: "d-auto-complete-popup", inputs: { width: "width", cssClass: "cssClass", maxHeight: "maxHeight", disabled: "disabled", disabledKey: "disabledKey", source: "source", position: "position", isOpen: "isOpen", term: "term", popTipsText: "popTipsText", overview: "overview", itemTemplate: "itemTemplate", noResultItemTemplate: "noResultItemTemplate", searchingTemplate: "searchingTemplate", isSearching: "isSearching", formatter: "formatter", dropdown: "dropdown", selectWidth: "selectWidth", enableLazyLoad: "enableLazyLoad", appendToBody: "appendToBody", cdkOverlayOffsetY: "cdkOverlayOffsetY", origin: "origin", showAnimation: "showAnimation" }, viewQueries: [{ propertyName: "selectMenuElement", first: true, predicate: ["selectMenuElement"], descendants: true }, { propertyName: "dropdownUl", first: true, predicate: ["dropdownUl"], descendants: true }, { propertyName: "connectedOverlay", first: true, predicate: CdkConnectedOverlay, descendants: true }], ngImport: i0, template: "<ng-container *ngIf=\"appendToBody\">\r\n  <ng-template\r\n    cdk-connected-overlay\r\n    [cdkConnectedOverlayOrigin]=\"origin\"\r\n    [cdkConnectedOverlayWidth]=\"width\"\r\n    [cdkConnectedOverlayOpen]=\"isOpen && !disabled\"\r\n    [cdkConnectedOverlayOffsetY]=\"cdkOverlayOffsetY\"\r\n    [cdkConnectedOverlayPositions]=\"overlayPositions\"\r\n    (positionChange)=\"onPositionChange($event)\"\r\n  >\r\n    <ng-template [ngTemplateOutlet]=\"popTpl\"> </ng-template>\r\n  </ng-template>\r\n</ng-container>\r\n\r\n<ng-container *ngIf=\"!appendToBody\">\r\n  <ng-template [ngTemplateOutlet]=\"popTpl\"> </ng-template>\r\n</ng-container>\r\n\r\n<ng-template #popTpl>\r\n  <div\r\n    class=\"devui-dropdown-menu\"\r\n    [ngClass]=\"{ 'devui-dropdown-menu-cdk': appendToBody }\"\r\n    [style.display]=\"isOpen && (source?.length || noResultItemTemplate) && !disabled ? 'inline-block' : 'none'\"\r\n    [style.top]=\"overview === 'multiline' ? (position?.top < labelMinHeight ? '50%' : '100%') : '100%'\"\r\n    [style.left]=\"overview === 'multiline' ? position?.left + 'px' : '0'\"\r\n    [@fadeInOut]=\"isOpen && !disabled ? (appendToBody ? popPosition : 'bottom') : 'void'\"\r\n    (@fadeInOut.done)=\"animationEnd($event)\"\r\n    [@.disabled]=\"!showAnimation\"\r\n    #selectMenuElement\r\n    dLoading\r\n    [showLoading]=\"showLoading\"\r\n    [backdrop]=\"true\"\r\n  >\r\n    <ul\r\n      class=\"devui-list-unstyled devui-scrollbar scroll-height\"\r\n      [style.maxHeight]=\"maxHeight + 'px'\"\r\n      dLazyLoad\r\n      [enableLazyLoad]=\"enableLazyLoad\"\r\n      (loadMore)=\"loadMoreEvent($event)\"\r\n      #dropdownUl\r\n    >\r\n      <ng-container *ngIf=\"!isSearching || !searchingTemplate\">\r\n        <li *ngIf=\"popTipsText && popTipsText.length > 0\" class=\"devui-popup-tips\">\r\n          {{ popTipsText }}\r\n        </li>\r\n        <li\r\n          *ngFor=\"let item of source; let $index = index; trackBy: trackByFn\"\r\n          class=\"devui-dropdown-item\"\r\n          [title]=\"formatter(item)\"\r\n          [ngClass]=\"{\r\n            selected: $index == activeIndex,\r\n            'devui-dropdown-bg': $index == hoverIndex,\r\n            disabled: disabledKey && item[disabledKey]\r\n          }\"\r\n          (click)=\"onSelect($event, item)\"\r\n        >\r\n          <ng-template\r\n            [ngTemplateOutlet]=\"itemTemplate || defaultItemTemplate\"\r\n            [ngTemplateOutletContext]=\"{\r\n              formatter: formatter,\r\n              term: term,\r\n              source: source,\r\n              item: item,\r\n              $index: $index\r\n            }\"\r\n          >\r\n          </ng-template>\r\n        </li>\r\n        <div class=\"devui-no-data-tip\" *ngIf=\"!source?.length && noResultItemTemplate\">\r\n          <ng-template [ngTemplateOutlet]=\"noResultItemTemplate\" [ngTemplateOutletContext]=\"{ term: term, source: source }\"> </ng-template>\r\n        </div>\r\n      </ng-container>\r\n      <div class=\"devui-no-data-tip\" *ngIf=\"isSearching && searchingTemplate\">\r\n        <ng-template [ngTemplateOutlet]=\"searchingTemplate\" [ngTemplateOutletContext]=\"{ term: term }\"> </ng-template>\r\n      </div>\r\n    </ul>\r\n  </div>\r\n</ng-template>\r\n\r\n<ng-template #defaultItemTemplate let-item=\"item\" let-term=\"term\">\r\n  <d-highlight [value]=\"formatter(item)\" [term]=\"term\"></d-highlight>\r\n</ng-template>\r\n", styles: [".devui-dropdown-menu{width:100%;display:block}.devui-dropdown-menu-cdk{position:static}ul.devui-list-unstyled{margin:0}.devui-popup-tips{color:#575d6c;color:var(--devui-text-weak, #575d6c);padding:4px 12px}\n"], dependencies: [{ kind: "directive", type: i2.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i2.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i2.NgIf, selector: "[ngIf]", inputs: ["ngIf", "ngIfThen", "ngIfElse"] }, { kind: "directive", type: i2.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "directive", type: i3.CdkConnectedOverlay, selector: "[cdk-connected-overlay], [connected-overlay], [cdkConnectedOverlay]", inputs: ["cdkConnectedOverlayOrigin", "cdkConnectedOverlayPositions", "cdkConnectedOverlayPositionStrategy", "cdkConnectedOverlayOffsetX", "cdkConnectedOverlayOffsetY", "cdkConnectedOverlayWidth", "cdkConnectedOverlayHeight", "cdkConnectedOverlayMinWidth", "cdkConnectedOverlayMinHeight", "cdkConnectedOverlayBackdropClass", "cdkConnectedOverlayPanelClass", "cdkConnectedOverlayViewportMargin", "cdkConnectedOverlayScrollStrategy", "cdkConnectedOverlayOpen", "cdkConnectedOverlayDisableClose", "cdkConnectedOverlayTransformOriginOn", "cdkConnectedOverlayHasBackdrop", "cdkConnectedOverlayLockPosition", "cdkConnectedOverlayFlexibleDimensions", "cdkConnectedOverlayGrowAfterOpen", "cdkConnectedOverlayPush"], outputs: ["backdropClick", "positionChange", "attach", "detach", "overlayKeydown", "overlayOutsideClick"], exportAs: ["cdkConnectedOverlay"] }, { kind: "directive", type: i4.LazyLoadDirective, selector: "[dLazyLoad]", inputs: ["enableLazyLoad", "contentMode", "target", "imgLoadSrc"], outputs: ["loadMore"] }, { kind: "directive", type: i5.LoadingDirective, selector: "[dLoading]", inputs: ["message", "backdrop", "loadingTemplateRef", "positionType", "view", "showLoading", "loading", "zIndex", "loadingStyle"], exportAs: ["dLoading"] }, { kind: "component", type: i4.HighlightComponent, selector: "d-highlight", inputs: ["value", "term", "highlightClass"] }], animations: [fadeInOut] });
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompletePopupComponent, decorators: [{
            type: Component,
            args: [{ selector: 'd-auto-complete-popup', animations: [fadeInOut], preserveWhitespaces: false, template: "<ng-container *ngIf=\"appendToBody\">\r\n  <ng-template\r\n    cdk-connected-overlay\r\n    [cdkConnectedOverlayOrigin]=\"origin\"\r\n    [cdkConnectedOverlayWidth]=\"width\"\r\n    [cdkConnectedOverlayOpen]=\"isOpen && !disabled\"\r\n    [cdkConnectedOverlayOffsetY]=\"cdkOverlayOffsetY\"\r\n    [cdkConnectedOverlayPositions]=\"overlayPositions\"\r\n    (positionChange)=\"onPositionChange($event)\"\r\n  >\r\n    <ng-template [ngTemplateOutlet]=\"popTpl\"> </ng-template>\r\n  </ng-template>\r\n</ng-container>\r\n\r\n<ng-container *ngIf=\"!appendToBody\">\r\n  <ng-template [ngTemplateOutlet]=\"popTpl\"> </ng-template>\r\n</ng-container>\r\n\r\n<ng-template #popTpl>\r\n  <div\r\n    class=\"devui-dropdown-menu\"\r\n    [ngClass]=\"{ 'devui-dropdown-menu-cdk': appendToBody }\"\r\n    [style.display]=\"isOpen && (source?.length || noResultItemTemplate) && !disabled ? 'inline-block' : 'none'\"\r\n    [style.top]=\"overview === 'multiline' ? (position?.top < labelMinHeight ? '50%' : '100%') : '100%'\"\r\n    [style.left]=\"overview === 'multiline' ? position?.left + 'px' : '0'\"\r\n    [@fadeInOut]=\"isOpen && !disabled ? (appendToBody ? popPosition : 'bottom') : 'void'\"\r\n    (@fadeInOut.done)=\"animationEnd($event)\"\r\n    [@.disabled]=\"!showAnimation\"\r\n    #selectMenuElement\r\n    dLoading\r\n    [showLoading]=\"showLoading\"\r\n    [backdrop]=\"true\"\r\n  >\r\n    <ul\r\n      class=\"devui-list-unstyled devui-scrollbar scroll-height\"\r\n      [style.maxHeight]=\"maxHeight + 'px'\"\r\n      dLazyLoad\r\n      [enableLazyLoad]=\"enableLazyLoad\"\r\n      (loadMore)=\"loadMoreEvent($event)\"\r\n      #dropdownUl\r\n    >\r\n      <ng-container *ngIf=\"!isSearching || !searchingTemplate\">\r\n        <li *ngIf=\"popTipsText && popTipsText.length > 0\" class=\"devui-popup-tips\">\r\n          {{ popTipsText }}\r\n        </li>\r\n        <li\r\n          *ngFor=\"let item of source; let $index = index; trackBy: trackByFn\"\r\n          class=\"devui-dropdown-item\"\r\n          [title]=\"formatter(item)\"\r\n          [ngClass]=\"{\r\n            selected: $index == activeIndex,\r\n            'devui-dropdown-bg': $index == hoverIndex,\r\n            disabled: disabledKey && item[disabledKey]\r\n          }\"\r\n          (click)=\"onSelect($event, item)\"\r\n        >\r\n          <ng-template\r\n            [ngTemplateOutlet]=\"itemTemplate || defaultItemTemplate\"\r\n            [ngTemplateOutletContext]=\"{\r\n              formatter: formatter,\r\n              term: term,\r\n              source: source,\r\n              item: item,\r\n              $index: $index\r\n            }\"\r\n          >\r\n          </ng-template>\r\n        </li>\r\n        <div class=\"devui-no-data-tip\" *ngIf=\"!source?.length && noResultItemTemplate\">\r\n          <ng-template [ngTemplateOutlet]=\"noResultItemTemplate\" [ngTemplateOutletContext]=\"{ term: term, source: source }\"> </ng-template>\r\n        </div>\r\n      </ng-container>\r\n      <div class=\"devui-no-data-tip\" *ngIf=\"isSearching && searchingTemplate\">\r\n        <ng-template [ngTemplateOutlet]=\"searchingTemplate\" [ngTemplateOutletContext]=\"{ term: term }\"> </ng-template>\r\n      </div>\r\n    </ul>\r\n  </div>\r\n</ng-template>\r\n\r\n<ng-template #defaultItemTemplate let-item=\"item\" let-term=\"term\">\r\n  <d-highlight [value]=\"formatter(item)\" [term]=\"term\"></d-highlight>\r\n</ng-template>\r\n", styles: [".devui-dropdown-menu{width:100%;display:block}.devui-dropdown-menu-cdk{position:static}ul.devui-list-unstyled{margin:0}.devui-popup-tips{color:#575d6c;color:var(--devui-text-weak, #575d6c);padding:4px 12px}\n"] }]
        }], ctorParameters: function () { return [{ type: AutoCompleteConfig }, { type: i0.ElementRef }]; }, propDecorators: { width: [{
                type: Input
            }], cssClass: [{
                type: Input
            }], maxHeight: [{
                type: Input
            }], disabled: [{
                type: Input
            }], disabledKey: [{
                type: Input
            }], source: [{
                type: Input
            }], position: [{
                type: Input
            }], isOpen: [{
                type: Input
            }], term: [{
                type: Input
            }], popTipsText: [{
                type: Input
            }], overview: [{
                type: Input
            }], itemTemplate: [{
                type: Input
            }], noResultItemTemplate: [{
                type: Input
            }], searchingTemplate: [{
                type: Input
            }], isSearching: [{
                type: Input
            }], formatter: [{
                type: Input
            }], dropdown: [{
                type: Input
            }], selectWidth: [{
                type: Input
            }], enableLazyLoad: [{
                type: Input
            }], appendToBody: [{
                type: Input
            }], cdkOverlayOffsetY: [{
                type: Input
            }], origin: [{
                type: Input
            }], showAnimation: [{
                type: Input
            }], selectMenuElement: [{
                type: ViewChild,
                args: ['selectMenuElement']
            }], dropdownUl: [{
                type: ViewChild,
                args: ['dropdownUl']
            }], connectedOverlay: [{
                type: ViewChild,
                args: [CdkConnectedOverlay]
            }] } });

class AutoCompleteDirective {
    constructor(autoCompleteConfig, elementRef, viewContainerRef, componentFactoryResolver, renderer, injector, positionService, changeDetectorRef, i18n, devConfigService) {
        this.autoCompleteConfig = autoCompleteConfig;
        this.elementRef = elementRef;
        this.viewContainerRef = viewContainerRef;
        this.componentFactoryResolver = componentFactoryResolver;
        this.renderer = renderer;
        this.injector = injector;
        this.positionService = positionService;
        this.changeDetectorRef = changeDetectorRef;
        this.i18n = i18n;
        this.devConfigService = devConfigService;
        this.autocomplete = 'off';
        this.autocapitalize = 'off';
        this.autocorrect = 'off';
        this.delay = 300;
        this.appendToBody = false;
        this.appendToBodyDirections = ['rightDown', 'leftDown', 'rightUp', 'leftUp'];
        this.cdkOverlayOffsetY = 0; // 内部使用不开放
        this.sceneType = ''; // sceneType使用场景：select(下拉框) suggest(联想)
        this.tipsText = ''; // 提示文字
        this.maxHeight = 300;
        this.showAnimation = true;
        /**
         *  【可选】启用数据懒加载，默认不启用
         */
        this.enableLazyLoad = false;
        this.allowEmptyValueSearch = false; // 在value为空时，是否允许进行搜索
        this.loadMore = new EventEmitter();
        this.selectValue = new EventEmitter();
        this.transInputFocusEmit = new EventEmitter(); // input状态传给父组件函数
        /**
         * @deprecated
         */
        this.changeDropDownStatus = new EventEmitter();
        this.toggleChange = new EventEmitter();
        this.KEYBOARD_EVENT_NOT_REFRESH = ['escape', 'enter', 'arrowup', 'arrowdown', /* ie 10 edge */ 'esc', 'up', 'down'];
        this.destroy$ = new Subject();
        this.popTipsText = '';
        this.focus = false;
        this.onChange = (_) => null;
        this.onTouched = () => null;
    }
    set isSearching(isSearching) {
        if (this.popupRef && this.searchingTemplate) {
            const pop = this.popupRef.instance;
            pop.isSearching = isSearching;
            pop.searchingTemplate = this.searchingTemplate;
            if (isSearching) {
                pop.isOpen = true;
            }
        }
    }
    ngOnInit() {
        this.init();
        this.setI18nText();
        this.valueChanges = this.registerInputEvent(this.elementRef);
        // 调用时机：input keyup
        this.subscription = this.valueChanges.subscribe((source) => this.onSourceChange(source));
        // 动态的创建了popup组件，
        const factory = this.componentFactoryResolver.resolveComponentFactory(AutoCompletePopupComponent);
        this.popupRef = this.viewContainerRef.createComponent(factory, this.viewContainerRef.length, this.injector);
        this.fillPopup(this.source);
        if (!this.searchFn) {
            this.searchFn = (term) => {
                return of(this.source.filter((item) => this.formatter(item).toLowerCase().indexOf(term.toLowerCase()) !== -1));
            };
        }
        // 调用时机：选中回车或者鼠标单击下拉选项
        this.popupRef.instance.registerOnChange((item) => {
            if (item.type === 'loadMore') {
                this.loadMore.emit(item.value);
                return;
            }
            const value = this.valueParser(item.value);
            this.writeValue(value);
            this.onChange(value);
            this.hidePopup();
            this.selectValue.emit(item.value);
            if (this.overview && this.overview !== 'single') {
                setTimeout(() => {
                    // 这里稍微延迟一下，等待光标的位置发生变化，好重新获取光标的位置
                    this.restLatestSource();
                }, 0);
            }
        });
        this.setPositions();
    }
    ngOnChanges(changes) {
        if (changes && this.popupRef && changes.source) {
            this.fillPopup(this.source);
        }
        if (changes['appendToBodyDirections']) {
            this.setPositions();
        }
    }
    init() {
        this.minLength = this.minLength ?? this.autoCompleteConfig.autoComplete.minLength;
        this.itemTemplate = this.itemTemplate || this.autoCompleteConfig.autoComplete.itemTemplate;
        this.noResultItemTemplate = this.noResultItemTemplate || this.autoCompleteConfig.autoComplete.noResultItemTemplate;
        this.formatter = this.formatter || this.autoCompleteConfig.autoComplete.formatter;
        this.valueParser = this.valueParser || this.autoCompleteConfig.autoComplete.valueParser;
    }
    setPositions() {
        if (this.popupRef) {
            this.popupRef.instance.overlayPositions =
                this.appendToBodyDirections && this.appendToBodyDirections.length > 0
                    ? this.appendToBodyDirections
                        .map((position) => {
                        if (typeof position === 'string') {
                            return AppendToBodyDirectionsConfig[position];
                        }
                        else {
                            return position;
                        }
                    })
                        .filter((position) => position !== undefined)
                    : undefined;
        }
    }
    setI18nText() {
        this.i18nText = this.i18n.getI18nText().autoComplete;
        // this.i18nLang = this.i18n.getI18nText().locale; // 如果需要获取当前语言
        this.i18n
            .langChange()
            .pipe(takeUntil(this.destroy$))
            .subscribe((data) => {
            this.i18nText = data.autoComplete;
            // this.i18nLang = data.locale; // 如果需要获取当前语言
        });
    }
    restLatestSource() {
        if (this.latestSource && this.latestSource.length > 0) {
            this.writeValue('');
            this.clearInputValue();
            this.showLatestSource();
        }
    }
    // 调用时机：input keyup
    onSourceChange(source) {
        if (!this.elementRef.nativeElement.value) {
            if (this.sceneType !== 'select' && !this.allowEmptyValueSearch) {
                // 下拉场景不展示最近输入
                this.showLatestSource();
            }
            else {
                this.showSource(source, true, true);
            }
        }
        else {
            this.showSource(source, true, true);
        }
    }
    showLatestSource() {
        let tempSource = [];
        if (this.latestSource && this.latestSource.length > 0) {
            this.searchFn('').subscribe((source) => {
                const t = this.latestSource;
                tempSource = t.filter((data) => {
                    if (!data.label) {
                        return source.find((item) => item === data);
                    }
                    else {
                        return source.find((item) => item.label === data.label);
                    }
                });
                const pop = this.popupRef.instance;
                pop.reset();
                this.popTipsText = this.i18nText.latestInput;
                this.fillPopup(tempSource);
                this.openPopup();
                this.changeDetectorRef.markForCheck();
                this.updatePosition();
            });
        }
        if (tempSource.length <= 0) {
            this.hidePopup();
        }
    }
    showSource(source, setOpen, isReset) {
        if ((source && source.length) || this.noResultItemTemplate) {
            const pop = this.popupRef.instance;
            if (isReset) {
                pop.reset();
            }
            this.popTipsText = this.tipsText || '';
            this.fillPopup(source, this.value);
            if (setOpen) {
                this.openPopup();
            }
            this.changeDetectorRef.markForCheck();
            this.updatePosition();
        }
        else {
            this.hidePopup();
        }
    }
    updatePosition() {
        if (this.appendToBody) {
            setTimeout(() => {
                if (this.popupRef.instance.connectedOverlay && this.popupRef.instance.connectedOverlay.overlayRef) {
                    this.popupRef.instance.connectedOverlay.overlayRef.updatePosition();
                }
            });
        }
    }
    openPopup(activeIndex = 0) {
        this.popupRef.instance.activeIndex = activeIndex;
        this.popupRef.instance.isOpen = true;
        this.popupRef.instance.disabled = this.disabled;
        addClassToOrigin(this.elementRef);
        this.changeDropDownStatus.emit(true);
        this.toggleChange.emit(true);
    }
    writeValue(obj) {
        this.value = this.formatter(obj) || '';
        this.writeInputValue(this.value);
    }
    registerOnChange(fn) {
        this.onChange = fn;
    }
    registerOnTouched(fn) {
        this.onTouched = fn;
    }
    setDisabledState(isDisabled) {
        this.disabled = isDisabled;
        this.renderer.setProperty(this.elementRef.nativeElement, 'disabled', isDisabled);
        if (this.popupRef) {
            this.popupRef.instance.setDisabledState(isDisabled);
        }
    }
    ngOnDestroy() {
        this.unSubscription();
        this.destroy$.next();
        this.destroy$.complete();
    }
    onFocus($event) {
        this.focus = true;
        this.transInputFocusEmit.emit({
            focus: true,
            popupRef: this.popupRef,
        });
        const isOpen = this.sceneType !== 'select';
        if (this.sceneType === 'select') {
            this.searchFn('').subscribe((source) => {
                this.showSource(source, isOpen, false);
            });
        }
    }
    onBlur($event) {
        this.focus = false;
        // this.hidePopup();    // TODO: 直接做失焦关闭，与点击操作将有冲突，存在click未完成已经blur，这个改动需要考虑
        this.onTouched();
    }
    onEscKeyup($event) {
        this.hidePopup();
    }
    onEnterKeyDown($event) {
        if (!this.popupRef.instance.source || !this.popupRef.instance.isOpen) {
            return;
        }
        if (this.popupRef) {
            this.popupRef.instance.selectCurrentItem($event);
        }
    }
    onArrowUpKeyDown($event) {
        if (this.popupRef) {
            $event.preventDefault();
            $event.stopPropagation();
            this.popupRef.instance.prev();
        }
    }
    onArrowDownKeyDown($event) {
        if (this.popupRef) {
            $event.preventDefault();
            $event.stopPropagation();
            this.popupRef.instance.next();
        }
    }
    onDocumentClick($event) {
        if (this.focus) {
            this.transInputFocusEmit.emit({
                focus: this.focus,
                popupRef: this.popupRef,
            });
        }
        // TODO: sceneType为'select'时，自定义了太多处理，十分不优雅，需要合一化
        const hostElement = this.elementRef.nativeElement;
        if (this.popupRef && this.popupRef.instance.isOpen) {
            if ((!hostElement.contains($event.target) && this.sceneType === 'select') || this.sceneType !== 'select') {
                this.hidePopup();
            }
            if (!hostElement.contains($event.target)) {
                this.transInputFocusEmit.emit({
                    focus: false,
                    popupRef: this.popupRef,
                });
            }
        }
        else if (hostElement.contains($event.target) && this.sceneType !== 'select') {
            if (!this.elementRef.nativeElement.value && !this.allowEmptyValueSearch) {
                this.showLatestSource();
            }
            else {
                this.searchFn(this.elementRef.nativeElement.value).subscribe((source) => {
                    this.showSource(source, true, false);
                });
            }
        }
    }
    hidePopup() {
        if (this.popupRef) {
            this.popupRef.instance.isOpen = false;
            removeClassFromOrigin(this.elementRef);
            this.changeDropDownStatus.emit(false);
            this.toggleChange.emit(false);
        }
    }
    fillPopup(source, term) {
        this.position = this.positionService.position(this.elementRef.nativeElement);
        const pop = this.popupRef.instance;
        pop.source = source;
        pop.maxHeight = this.maxHeight;
        pop.term = term;
        pop.disabledKey = this.disabledKey;
        pop.enableLazyLoad = this.enableLazyLoad;
        pop.disabled = this.disabled;
        if (this.appendToBody) {
            pop.appendToBody = true;
            pop.origin = new CdkOverlayOrigin(this.elementRef);
            pop.width = this.dAutoCompleteWidth ? this.dAutoCompleteWidth : this.elementRef.nativeElement.offsetWidth;
            pop.cdkOverlayOffsetY = this.cdkOverlayOffsetY;
        }
        else {
            pop.appendToBody = false;
        }
        [
            'formatter',
            'itemTemplate',
            'noResultItemTemplate',
            'cssClass',
            'dropdown',
            'popTipsText',
            'position',
            'overview',
            'showAnimation',
        ].forEach((key) => {
            if (this[key] !== undefined) {
                pop[key] = this[key];
            }
        });
    }
    writeInputValue(value) {
        this.renderer.setProperty(this.elementRef.nativeElement, 'value', value);
    }
    clearInputValue() {
        this.renderer.setProperty(this.elementRef.nativeElement, 'value', '');
    }
    unSubscription() {
        if (this.subscription) {
            this.subscription.unsubscribe();
            this.subscription = null;
        }
    }
    onTermChange(term) {
        this.value = term;
        if (this.popupRef) {
            this.popupRef.instance.term = term;
        }
        this.onChange(term);
    }
    registerInputEvent(elementRef) {
        return fromEvent(elementRef.nativeElement, 'input').pipe(map((e) => e.target.value), filter((term) => !this.disabled && this.searchFn && term.length >= 0), debounceTime(this.delay), tap((term) => this.onTermChange(term)), switchMap((term) => this.searchFn(term, this)));
    }
}
AutoCompleteDirective.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteDirective, deps: [{ token: AutoCompleteConfig }, { token: i0.ElementRef }, { token: i0.ViewContainerRef }, { token: i0.ComponentFactoryResolver }, { token: i0.Renderer2 }, { token: i0.Injector }, { token: i2$1.PositionService }, { token: i0.ChangeDetectorRef }, { token: i3$1.I18nService }, { token: i4.DevConfigService }], target: i0.ɵɵFactoryTarget.Directive });
AutoCompleteDirective.ɵdir = i0.ɵɵngDeclareDirective({ minVersion: "14.0.0", version: "14.2.0", type: AutoCompleteDirective, selector: "[dAutoComplete]", inputs: { disabled: "disabled", cssClass: "cssClass", delay: "delay", minLength: "minLength", itemTemplate: "itemTemplate", noResultItemTemplate: "noResultItemTemplate", searchingTemplate: "searchingTemplate", isSearching: "isSearching", appendToBody: "appendToBody", appendToBodyDirections: "appendToBodyDirections", cdkOverlayOffsetY: "cdkOverlayOffsetY", dAutoCompleteWidth: "dAutoCompleteWidth", formatter: "formatter", sceneType: "sceneType", tipsText: "tipsText", overview: "overview", latestSource: "latestSource", source: "source", valueParser: "valueParser", searchFn: "searchFn", dropdown: "dropdown", maxHeight: "maxHeight", disabledKey: "disabledKey", showAnimation: "showAnimation", enableLazyLoad: "enableLazyLoad", allowEmptyValueSearch: "allowEmptyValueSearch" }, outputs: { loadMore: "loadMore", selectValue: "selectValue", transInputFocusEmit: "transInputFocusEmit", changeDropDownStatus: "changeDropDownStatus", toggleChange: "toggleChange" }, host: { listeners: { "focus": "onFocus($event)", "blur": "onBlur($event)", "keydown.esc": "onEscKeyup($event)", "keydown.Enter": "onEnterKeyDown($event)", "keydown.ArrowUp": "onArrowUpKeyDown($event)", "keydown.ArrowDown": "onArrowDownKeyDown($event)", "document:click": "onDocumentClick($event)" }, properties: { "attr.autocomplete": "this.autocomplete", "attr.autocapitalize": "this.autocapitalize", "attr.autocorrect": "this.autocorrect" } }, providers: [
        {
            provide: NG_VALUE_ACCESSOR,
            useExisting: forwardRef(() => AutoCompleteDirective),
            multi: true,
        },
    ], exportAs: ["autoComplete"], usesOnChanges: true, ngImport: i0 });
__decorate([
    WithConfig(),
    __metadata("design:type", Object)
], AutoCompleteDirective.prototype, "showAnimation", void 0);
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteDirective, decorators: [{
            type: Directive,
            args: [{
                    selector: '[dAutoComplete]',
                    exportAs: 'autoComplete',
                    providers: [
                        {
                            provide: NG_VALUE_ACCESSOR,
                            useExisting: forwardRef(() => AutoCompleteDirective),
                            multi: true,
                        },
                    ],
                }]
        }], ctorParameters: function () { return [{ type: AutoCompleteConfig }, { type: i0.ElementRef }, { type: i0.ViewContainerRef }, { type: i0.ComponentFactoryResolver }, { type: i0.Renderer2 }, { type: i0.Injector }, { type: i2$1.PositionService }, { type: i0.ChangeDetectorRef }, { type: i3$1.I18nService }, { type: i4.DevConfigService }]; }, propDecorators: { autocomplete: [{
                type: HostBinding,
                args: ['attr.autocomplete']
            }], autocapitalize: [{
                type: HostBinding,
                args: ['attr.autocapitalize']
            }], autocorrect: [{
                type: HostBinding,
                args: ['attr.autocorrect']
            }], disabled: [{
                type: Input
            }], cssClass: [{
                type: Input
            }], delay: [{
                type: Input
            }], minLength: [{
                type: Input
            }], itemTemplate: [{
                type: Input
            }], noResultItemTemplate: [{
                type: Input
            }], searchingTemplate: [{
                type: Input
            }], isSearching: [{
                type: Input
            }], appendToBody: [{
                type: Input
            }], appendToBodyDirections: [{
                type: Input
            }], cdkOverlayOffsetY: [{
                type: Input
            }], dAutoCompleteWidth: [{
                type: Input
            }], formatter: [{
                type: Input
            }], sceneType: [{
                type: Input
            }], tipsText: [{
                type: Input
            }], overview: [{
                type: Input
            }], latestSource: [{
                type: Input
            }], source: [{
                type: Input
            }], valueParser: [{
                type: Input
            }], searchFn: [{
                type: Input
            }], dropdown: [{
                type: Input
            }], maxHeight: [{
                type: Input
            }], disabledKey: [{
                type: Input
            }], showAnimation: [{
                type: Input
            }], enableLazyLoad: [{
                type: Input
            }], allowEmptyValueSearch: [{
                type: Input
            }], loadMore: [{
                type: Output
            }], selectValue: [{
                type: Output
            }], transInputFocusEmit: [{
                type: Output
            }], changeDropDownStatus: [{
                type: Output
            }], toggleChange: [{
                type: Output
            }], onFocus: [{
                type: HostListener,
                args: ['focus', ['$event']]
            }], onBlur: [{
                type: HostListener,
                args: ['blur', ['$event']]
            }], onEscKeyup: [{
                type: HostListener,
                args: ['keydown.esc', ['$event']]
            }], onEnterKeyDown: [{
                type: HostListener,
                args: ['keydown.Enter', ['$event']]
            }], onArrowUpKeyDown: [{
                type: HostListener,
                args: ['keydown.ArrowUp', ['$event']]
            }], onArrowDownKeyDown: [{
                type: HostListener,
                args: ['keydown.ArrowDown', ['$event']]
            }], onDocumentClick: [{
                type: HostListener,
                args: ['document:click', ['$event']]
            }] } });

class AutoCompleteModule {
}
AutoCompleteModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
AutoCompleteModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteModule, declarations: [AutoCompleteDirective, AutoCompletePopupComponent], imports: [CommonModule, FormsModule, OverlayModule, LazyLoadModule, LoadingModule, PositioningModule, HighlightModule], exports: [AutoCompleteDirective, AutoCompletePopupComponent] });
AutoCompleteModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteModule, providers: [AutoCompleteConfig], imports: [CommonModule, FormsModule, OverlayModule, LazyLoadModule, LoadingModule, PositioningModule, HighlightModule] });
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "14.2.0", ngImport: i0, type: AutoCompleteModule, decorators: [{
            type: NgModule,
            args: [{
                    imports: [CommonModule, FormsModule, OverlayModule, LazyLoadModule, LoadingModule, PositioningModule, HighlightModule],
                    exports: [AutoCompleteDirective, AutoCompletePopupComponent],
                    declarations: [AutoCompleteDirective, AutoCompletePopupComponent],
                    providers: [AutoCompleteConfig],
                }]
        }] });

/**
 * Generated bundle index. Do not edit.
 */

export { AutoCompleteConfig, AutoCompleteDirective, AutoCompleteModule, AutoCompletePopupComponent };
//# sourceMappingURL=ng-devui-auto-complete.mjs.map
