import * as i0 from '@angular/core';
import { Injectable, Pipe, Input, ChangeDetectionStrategy, Component, HostListener, ViewChild, createNgModule } from '@angular/core';
import * as i1 from '@angular/router';
import { RouterModule, RouterEvent, RoutesRecognized, NavigationEnd, ActivatedRoute } from '@angular/router';
import * as i5 from '@angular/common';
import { CommonModule } from '@angular/common';
import * as i3 from '@angular/material/icon';
import { MatIconModule } from '@angular/material/icon';
import { MatTooltipModule } from '@angular/material/tooltip';
import { BehaviorSubject, Subscription, Subject } from 'rxjs';
import { debounceTime, startWith, map, filter, take } from 'rxjs/operators';
import * as i2 from '@angular/cdk/drag-drop';
import { moveItemInArray, DragDropModule } from '@angular/cdk/drag-drop';
import { SdBadge } from '@sd-angular/core/components/badge';
import { SdUtilities } from '@sd-angular/core/utilities';
import * as i4 from '@sd-angular/core/services/notify';

class SdTabBase {
    #tab;
    constructor(tab) {
        this.#tab = tab;
    }
    get tab() {
        return this.#tab;
    }
}
class SdTabActivated extends SdTabBase {
}
class SdTabDeactivated extends SdTabBase {
}

class SdTabRouterService {
    events = new BehaviorSubject(new SdTabBase(undefined));
    actions = new BehaviorSubject(undefined);
    builders = new BehaviorSubject([]);
    currentTabChanges = new BehaviorSubject(undefined);
    newTabs = new BehaviorSubject(undefined);
    updateTabs = new BehaviorSubject(undefined);
    #currentTab = undefined;
    #componentBuilders = [];
    constructor() { }
    addBuilder = (builder) => {
        if (!this.#componentBuilders.some(e => e.component === builder.component)) {
            this.#componentBuilders.push(builder);
            this.builders.next(this.#componentBuilders);
        }
    };
    get currentTab() {
        return this.#currentTab;
    }
    get currentKey() {
        return this.#currentTab?.key || null;
    }
    // select = (tabOrKey: string | SdTab): void => {
    //   const tab = this.#tabs.find(e => {
    //     if (typeof (tabOrKey) === 'string') {
    //       return e.key === tabOrKey;
    //     }
    //     return e.key === tabOrKey?.key;
    //   });
    //   if (tab) {
    //     this.#currentTab = tab;
    //   }
    // }
    // add = (tab: SdTab): void => {
    //   if (!tab.key) {
    //     this.notifyService.notify.warning('Tab key is required');
    //   }
    //   if (!tab.component) {
    //     this.notifyService.notify.warning('Tab component is required');
    //   }
    //   const existedTab = this.#tabs.find(e => e.key === tab.key);
    //   if (!existedTab) {
    //     this.#tabs.push(tab);
    //     this.select(tab);
    //   } else {
    //     this.select(existedTab);
    //   }
    // }
    // remove = (tabOrKey: string | SdTab): void => {
    //   this.#tabs = this.#tabs.filter(e => {
    //     if (typeof (tabOrKey) === 'string') {
    //       return e.key !== tabOrKey;
    //     }
    //     return e.key !== tabOrKey?.key;
    //   });
    // }
    setCurrentTab = (tab) => {
        this.#currentTab = tab;
        this.currentTabChanges.next(tab);
    };
    pushEvent = (tab, Event) => {
        this.events.next(new Event(tab));
    };
    setOptions = () => { };
    close = (tab) => {
        tab = tab || this.#currentTab;
        if (tab) {
            this.actions.next({
                type: 'close',
                tab,
            });
        }
    };
    // Gọi hàm này để thực hiện update tab
    updateTab = (tab) => { };
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
    static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterService, providedIn: 'root' });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterService, decorators: [{
            type: Injectable,
            args: [{
                    providedIn: 'root',
                }]
        }], ctorParameters: () => [] });

class SdTabInfoPipe {
    tabRouterService;
    constructor(tabRouterService) {
        this.tabRouterService = tabRouterService;
    }
    transform(tabInfo, tab) {
        if (tabInfo) {
            return tabInfo;
        }
        const builders = this.tabRouterService.builders.getValue();
        const builder = builders.find(e => e.component === tab.component);
        if (builder) {
            const { url, params, queryParams, data } = tab;
            return {
                name: typeof builder.name === 'function' ? builder.name({ url, params, queryParams, data }) : builder.name,
                icon: typeof builder.icon === 'function' ? builder.icon({ url, params, queryParams }) : builder.icon,
                tooltip: typeof builder.tooltip === 'function' ? builder.tooltip({ url, params, queryParams }) : builder.tooltip,
                color: typeof builder.color === 'function' ? builder.color({ url, params, queryParams }) : builder.color,
            };
        }
        return {
            name: tab.url,
            icon: undefined,
        };
    }
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabInfoPipe, deps: [{ token: SdTabRouterService }], target: i0.ɵɵFactoryTarget.Pipe });
    static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "19.2.17", ngImport: i0, type: SdTabInfoPipe, isStandalone: true, name: "sdTabInfo" });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabInfoPipe, decorators: [{
            type: Pipe,
            args: [{
                    name: 'sdTabInfo',
                    standalone: true,
                }]
        }], ctorParameters: () => [{ type: SdTabRouterService }] });

class SdTabRouterItemComponent {
    cdRef;
    tabRouterService;
    tab;
    #subsctiption = new Subscription();
    tabInfo;
    constructor(cdRef, tabRouterService) {
        this.cdRef = cdRef;
        this.tabRouterService = tabRouterService;
    }
    ngOnInit() {
        this.#subsctiption.add(this.tabRouterService.events.pipe(debounceTime(100)).subscribe(() => {
            this.cdRef.markForCheck();
        }));
        this.#subsctiption.add(this.tab.tabInfoChanges.pipe(startWith(null)).subscribe(tabInfo => {
            if (tabInfo) {
                this.tabInfo = tabInfo;
                this.cdRef.markForCheck();
            }
        }));
    }
    ngOnDestroy() {
        this.#subsctiption.unsubscribe();
    }
    close = (event) => {
        event.preventDefault();
        event.stopPropagation();
        this.#closeTab();
    };
    onMousedown = (event) => {
        if (event.button === 1) {
            event.preventDefault();
        }
    };
    onMouseup = (event) => {
        if (event.button === 1) {
            event.preventDefault();
            event.stopPropagation();
            this.#closeTab();
        }
    };
    #closeTab = async () => {
        if (this.tab?.beforeClose) {
            //
            if (this.tab?.beforeClose()) {
                const result = this.tab?.beforeClose();
                if (typeof result === 'boolean') {
                    if (result) {
                        this.tabRouterService.close(this.tab);
                    }
                }
                else {
                    if (await result) {
                        this.tabRouterService.close(this.tab);
                    }
                }
            }
        }
        else {
            this.tabRouterService.close(this.tab);
        }
    };
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterItemComponent, deps: [{ token: i0.ChangeDetectorRef }, { token: SdTabRouterService }], target: i0.ɵɵFactoryTarget.Component });
    static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "19.2.17", type: SdTabRouterItemComponent, isStandalone: true, selector: "sd-tab-router-item", inputs: { tab: "tab" }, ngImport: i0, template: "<a\n  [routerLink]=\"[tab.url]\"\n  [queryParams]=\"tab.queryParams\"\n  [state]=\"{ switchTab: true }\"\n  class=\"tab-router__item d-flex align-items-center\"\n  style=\"gap: 8px\"\n  [class.tab-router__item--active]=\"tab.isActive\"\n  (mousedown)=\"onMousedown($event)\"\n  (mouseup)=\"onMouseup($event)\">\n  @let info = tabInfo | sdTabInfo: tab;\n  @if (info) {\n    <sd-badge\n      style=\"overflow: hidden;white-space: nowrap;\"\n      [icon]=\"info.icon\"\n      [title]=\"info.icon\"\n      [tooltip]=\"info.tooltip || info.name\"\n      [title]=\"info.name\"\n      [color]=\"info.color\"></sd-badge>\n    <button\n      aria-hidden=\"true\"\n      class=\"tab-router__close d-flex align-items-center justify-content-center ml-auto p-0\"\n      (click)=\"close($event)\"\n      (mousedown)=\"$event.stopPropagation()\">\n      <mat-icon aria-hidden=\"true\" fontIcon=\"close\"></mat-icon>\n    </button>\n  }\n</a>\n", styles: [":host{display:block;overflow:hidden;position:relative;flex:1 1 64px;max-width:240px}:host:after{content:\"\";position:absolute;right:0;top:0;bottom:0;height:16px;width:1px;background:#dde0e5;margin:auto}:host:last-child:after{content:none}:host::ng-deep .tab-router__item sd-badge .c-badge-title{white-space:nowrap;overflow:hidden;text-overflow:ellipsis;width:184px}.flex-1{flex:1}.tab-router__icon{background-color:#5c6bc0;width:16px;height:16px;line-height:16px;text-align:center;font-size:10px;color:#fff;border-radius:2px;text-transform:uppercase}.tab-router__icon .mat-icon{height:10px;width:10px;font-size:10px}.tab-router__close{color:#757575;outline:none;border:0;background:none;border-radius:50%;height:16px;width:16px}.tab-router__close:hover{background-color:#0000001f}.tab-router__close .mat-icon{font-size:12px;height:12px;width:12px}.tab-router__item{background:#f2f3f4;padding:8px;color:inherit;text-decoration:none;font-size:12px;line-height:16px;overflow:hidden}.tab-router__item:hover{background-color:#fff}.tab-router__name{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.tab-router__item--active{border-radius:8px 8px 0 0;background-color:#fff}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: RouterModule }, { kind: "directive", type: i1.RouterLink, selector: "[routerLink]", inputs: ["target", "queryParams", "fragment", "queryParamsHandling", "state", "info", "relativeTo", "preserveFragment", "skipLocationChange", "replaceUrl", "routerLink"] }, { kind: "ngmodule", type: MatIconModule }, { kind: "component", type: i3.MatIcon, selector: "mat-icon", inputs: ["color", "inline", "svgIcon", "fontSet", "fontIcon"], exportAs: ["matIcon"] }, { kind: "component", type: SdBadge, selector: "sd-badge", inputs: ["type", "color", "primary", "secondary", "success", "info", "warning", "error", "fontSet", "title", "description", "tooltip", "icon", "size"], outputs: ["sdClick"] }, { kind: "pipe", type: SdTabInfoPipe, name: "sdTabInfo" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterItemComponent, decorators: [{
            type: Component,
            args: [{ selector: 'sd-tab-router-item', changeDetection: ChangeDetectionStrategy.OnPush, standalone: true, imports: [CommonModule, RouterModule, MatIconModule, SdBadge, SdTabInfoPipe], template: "<a\n  [routerLink]=\"[tab.url]\"\n  [queryParams]=\"tab.queryParams\"\n  [state]=\"{ switchTab: true }\"\n  class=\"tab-router__item d-flex align-items-center\"\n  style=\"gap: 8px\"\n  [class.tab-router__item--active]=\"tab.isActive\"\n  (mousedown)=\"onMousedown($event)\"\n  (mouseup)=\"onMouseup($event)\">\n  @let info = tabInfo | sdTabInfo: tab;\n  @if (info) {\n    <sd-badge\n      style=\"overflow: hidden;white-space: nowrap;\"\n      [icon]=\"info.icon\"\n      [title]=\"info.icon\"\n      [tooltip]=\"info.tooltip || info.name\"\n      [title]=\"info.name\"\n      [color]=\"info.color\"></sd-badge>\n    <button\n      aria-hidden=\"true\"\n      class=\"tab-router__close d-flex align-items-center justify-content-center ml-auto p-0\"\n      (click)=\"close($event)\"\n      (mousedown)=\"$event.stopPropagation()\">\n      <mat-icon aria-hidden=\"true\" fontIcon=\"close\"></mat-icon>\n    </button>\n  }\n</a>\n", styles: [":host{display:block;overflow:hidden;position:relative;flex:1 1 64px;max-width:240px}:host:after{content:\"\";position:absolute;right:0;top:0;bottom:0;height:16px;width:1px;background:#dde0e5;margin:auto}:host:last-child:after{content:none}:host::ng-deep .tab-router__item sd-badge .c-badge-title{white-space:nowrap;overflow:hidden;text-overflow:ellipsis;width:184px}.flex-1{flex:1}.tab-router__icon{background-color:#5c6bc0;width:16px;height:16px;line-height:16px;text-align:center;font-size:10px;color:#fff;border-radius:2px;text-transform:uppercase}.tab-router__icon .mat-icon{height:10px;width:10px;font-size:10px}.tab-router__close{color:#757575;outline:none;border:0;background:none;border-radius:50%;height:16px;width:16px}.tab-router__close:hover{background-color:#0000001f}.tab-router__close .mat-icon{font-size:12px;height:12px;width:12px}.tab-router__item{background:#f2f3f4;padding:8px;color:inherit;text-decoration:none;font-size:12px;line-height:16px;overflow:hidden}.tab-router__item:hover{background-color:#fff}.tab-router__name{white-space:nowrap;overflow:hidden;text-overflow:ellipsis}.tab-router__item--active{border-radius:8px 8px 0 0;background-color:#fff}\n"] }]
        }], ctorParameters: () => [{ type: i0.ChangeDetectorRef }, { type: SdTabRouterService }], propDecorators: { tab: [{
                type: Input,
                args: [{ required: true }]
            }] } });

class SdTabRouterNavComponent {
    cdRef;
    elementRef;
    tabRouterNav;
    tabs = [];
    mode = 'default';
    constructor(cdRef, 
    // eslint-disable-next-line @typescript-eslint/no-explicit-any
    elementRef) {
        this.cdRef = cdRef;
        this.elementRef = elementRef;
    }
    onResize() {
        this.checkUI();
    }
    checkUI = () => {
        const width = this.tabRouterNav?.nativeElement.clientWidth;
        const nameWidth = (width - this.tabs.length * 68) / this.tabs.length;
        if (nameWidth <= 20) {
            this.mode = 'compact';
        }
        else {
            this.mode = 'default';
        }
        this.cdRef.markForCheck();
    };
    onDrop = (event) => {
        moveItemInArray(this.tabs, event.previousIndex, event.currentIndex);
    };
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterNavComponent, deps: [{ token: i0.ChangeDetectorRef }, { token: i0.ElementRef }], target: i0.ɵɵFactoryTarget.Component });
    static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.17", type: SdTabRouterNavComponent, isStandalone: true, selector: "sd-tab-router-nav", inputs: { tabs: "tabs" }, host: { listeners: { "window:resize": "onResize($event)" } }, viewQueries: [{ propertyName: "tabRouterNav", first: true, predicate: ["tabRouterNav"], descendants: true }], ngImport: i0, template: "<div\n  #tabRouterNav\n  cdkDropList\n  cdkDropListLockAxis=\"x\"\n  cdkDropListOrientation=\"horizontal\"\n  (cdkDropListDropped)=\"onDrop($event)\"\n  class=\"tab-router__nav tab-router__nav--{{ mode }} d-flex align-items-center flex-nowrap\"\n  [class.d-none]=\"tabs.length > 1\">\n  <ng-container *ngFor=\"let tab of tabs\">\n    <sd-tab-router-item [tab]=\"tab\" cdkDrag [cdkDragBoundary]=\"elementRef?.nativeElement\"></sd-tab-router-item>\n  </ng-container>\n</div>\n", styles: [".tab-router__nav{background:#f9f9f9;overflow:hidden}.tab-router__nav--compact::ng-deep .tab-router__name{display:none}.tab-router__nav--compact::ng-deep .tab-router__icon{margin:0!important}.tab-router__nav--compact::ng-deep .tab-router__item--active{min-width:240px}.tab-router__nav--compact::ng-deep .tab-router__item--active .tab-router__icon{margin-right:8px!important}.tab-router__nav--compact::ng-deep .tab-router__item--active .tab-router__name{display:-webkit-box}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i5.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "ngmodule", type: DragDropModule }, { kind: "directive", type: i2.CdkDropList, selector: "[cdkDropList], cdk-drop-list", inputs: ["cdkDropListConnectedTo", "cdkDropListData", "cdkDropListOrientation", "id", "cdkDropListLockAxis", "cdkDropListDisabled", "cdkDropListSortingDisabled", "cdkDropListEnterPredicate", "cdkDropListSortPredicate", "cdkDropListAutoScrollDisabled", "cdkDropListAutoScrollStep", "cdkDropListElementContainer"], outputs: ["cdkDropListDropped", "cdkDropListEntered", "cdkDropListExited", "cdkDropListSorted"], exportAs: ["cdkDropList"] }, { kind: "directive", type: i2.CdkDrag, selector: "[cdkDrag]", inputs: ["cdkDragData", "cdkDragLockAxis", "cdkDragRootElement", "cdkDragBoundary", "cdkDragStartDelay", "cdkDragFreeDragPosition", "cdkDragDisabled", "cdkDragConstrainPosition", "cdkDragPreviewClass", "cdkDragPreviewContainer", "cdkDragScale"], outputs: ["cdkDragStarted", "cdkDragReleased", "cdkDragEnded", "cdkDragEntered", "cdkDragExited", "cdkDragDropped", "cdkDragMoved"], exportAs: ["cdkDrag"] }, { kind: "component", type: SdTabRouterItemComponent, selector: "sd-tab-router-item", inputs: ["tab"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterNavComponent, decorators: [{
            type: Component,
            args: [{ selector: 'sd-tab-router-nav', changeDetection: ChangeDetectionStrategy.OnPush, standalone: true, imports: [CommonModule, DragDropModule, SdTabRouterItemComponent], template: "<div\n  #tabRouterNav\n  cdkDropList\n  cdkDropListLockAxis=\"x\"\n  cdkDropListOrientation=\"horizontal\"\n  (cdkDropListDropped)=\"onDrop($event)\"\n  class=\"tab-router__nav tab-router__nav--{{ mode }} d-flex align-items-center flex-nowrap\"\n  [class.d-none]=\"tabs.length > 1\">\n  <ng-container *ngFor=\"let tab of tabs\">\n    <sd-tab-router-item [tab]=\"tab\" cdkDrag [cdkDragBoundary]=\"elementRef?.nativeElement\"></sd-tab-router-item>\n  </ng-container>\n</div>\n", styles: [".tab-router__nav{background:#f9f9f9;overflow:hidden}.tab-router__nav--compact::ng-deep .tab-router__name{display:none}.tab-router__nav--compact::ng-deep .tab-router__icon{margin:0!important}.tab-router__nav--compact::ng-deep .tab-router__item--active{min-width:240px}.tab-router__nav--compact::ng-deep .tab-router__item--active .tab-router__icon{margin-right:8px!important}.tab-router__nav--compact::ng-deep .tab-router__item--active .tab-router__name{display:-webkit-box}\n"] }]
        }], ctorParameters: () => [{ type: i0.ChangeDetectorRef }, { type: i0.ElementRef }], propDecorators: { tabRouterNav: [{
                type: ViewChild,
                args: ['tabRouterNav']
            }], tabs: [{
                type: Input
            }], onResize: [{
                type: HostListener,
                args: ['window:resize', ['$event']]
            }] } });

class SdTabDecoratorService {
    static tabRouterService = new BehaviorSubject(undefined);
    constructor(tabRouterService) {
        SdTabDecoratorService.tabRouterService.next(tabRouterService);
    }
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabDecoratorService, deps: [{ token: SdTabRouterService }], target: i0.ɵɵFactoryTarget.Injectable });
    static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabDecoratorService, providedIn: 'root' });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabDecoratorService, decorators: [{
            type: Injectable,
            args: [{
                    providedIn: 'root',
                }]
        }], ctorParameters: () => [{ type: SdTabRouterService }] });

/* eslint-disable @typescript-eslint/no-explicit-any */
class SdTabRouterOutletComponent {
    router;
    activatedRoute;
    cd;
    injector;
    tabDecoratorService;
    tabRouterService;
    sdNotifyService;
    tabRouterNav;
    tabs = [];
    #rootRoute;
    #subscription = new Subscription();
    #firstLoad = true;
    constructor(router, activatedRoute, cd, injector, tabDecoratorService, // KHÔNG XÓA
    tabRouterService, sdNotifyService) {
        this.router = router;
        this.activatedRoute = activatedRoute;
        this.cd = cd;
        this.injector = injector;
        this.tabDecoratorService = tabDecoratorService;
        this.tabRouterService = tabRouterService;
        this.sdNotifyService = sdNotifyService;
        this.#subscription.add(router.events
            .pipe(map((event) => (event instanceof RouterEvent ? event : event.routerEvent)), filter(event => {
            return event instanceof RoutesRecognized || event instanceof NavigationEnd;
        }))
            .subscribe(async (event) => {
            if (this.#firstLoad && event instanceof NavigationEnd) {
                this.#firstLoad = false;
                const route = this.#getActivatedRouteSnapshot(this.activatedRoute.snapshot);
                this.#rootRoute = this.router.routerState.root;
                await this.#activeRoute(event.urlAfterRedirects || event.url, route);
                return;
            }
            if (!this.#firstLoad && event instanceof RoutesRecognized) {
                const route = this.#getActivatedRouteSnapshot(event.state.root);
                this.#rootRoute = this.router.routerState.root;
                await this.#activeRoute(event.urlAfterRedirects || event.url, route);
            }
        }));
        this.#subscription.add(tabRouterService.actions.subscribe((event) => {
            if (event && event.type === 'close') {
                this.#closeTab(event.tab);
            }
        }));
    }
    ngOnDestroy() {
        this.#subscription.unsubscribe();
    }
    tabTrackBy = (index, tab) => {
        return tab.key;
    };
    #closeTab = (tab) => {
        const { isActive, key: activeKey } = tab;
        if (isActive) {
            const activeIndex = this.tabs.findIndex(({ key }) => key === activeKey);
            const nextTab = this.tabs[activeIndex + 1] || this.tabs[activeIndex - 1];
            if (nextTab) {
                const { url: nextUrl } = nextTab;
                const nextQueryParams = {
                    ...(nextTab.queryParams || {}),
                };
                this.tabs = this.tabs.filter(({ key }) => key !== activeKey);
                this.router.navigate([nextUrl], {
                    queryParams: nextQueryParams,
                    state: {
                        switchTab: true,
                    },
                });
            }
            else {
                this.tabs = this.tabs.filter(({ key }) => key !== activeKey);
                this.router.navigateByUrl('/', {
                    state: {
                        switchTab: true,
                    },
                });
            }
        }
        else {
            this.tabs = this.tabs.filter(({ key }) => key !== tab.key);
            this.tabRouterNav?.checkUI();
            this.cd.markForCheck();
        }
    };
    #activeRoute = async (fullUrl, route) => {
        if (!route?.component) {
            return;
        }
        const component = route.component;
        const queryParams = {
            ...(route.queryParams || {}),
        };
        const params = {
            ...(route.params || {}),
        };
        const data = {
            ...(route.data || {}),
        };
        const [url] = fullUrl.split('?');
        const key = SdUtilities.hash({ url, queryParams });
        let existedIndex = -1;
        let activatedIndex = -1;
        this.tabs.forEach((tab, index) => {
            if (tab.key === key) {
                tab.isActive = true;
                existedIndex = index;
            }
            else {
                if (tab.isActive) {
                    activatedIndex = index;
                    this.tabRouterService.pushEvent(tab, SdTabDeactivated);
                }
                tab.isActive = false;
            }
        });
        const currentNavigation = this.router.getCurrentNavigation();
        // Switch tab sẽ ko re-render lại trang
        const switchTab = currentNavigation?.extras?.state?.['switchTab'];
        // Replace tab sẽ close trang hiện tại
        const replaceTab = currentNavigation?.extras?.state?.['replaceTab'];
        if (existedIndex >= 0) {
            const existedTab = this.tabs[existedIndex];
            if (replaceTab && activatedIndex >= 0) {
                if (activatedIndex >= 0) {
                    this.tabs.splice(activatedIndex, 1);
                }
            }
            if (switchTab) {
                this.tabRouterService.setCurrentTab(existedTab);
                this.tabRouterService.pushEvent(existedTab, SdTabActivated);
            }
            else {
                if (typeof route?.parent?.routeConfig?.loadChildren === 'function') {
                    const module = (await route.parent.routeConfig.loadChildren());
                    const moduleRef = createNgModule(module, this.injector);
                    const activatedRoute = this.#getActivatedRoute(this.#rootRoute, component);
                    const tab = {
                        key,
                        component,
                        injector: new SdOutletInjector(activatedRoute, moduleRef),
                        isActive: true,
                        url,
                        params,
                        queryParams,
                        data,
                        tabInfoChanges: new Subject(),
                    };
                    this.tabs[this.tabs.indexOf(existedTab)] = tab;
                }
            }
        }
        else {
            if (typeof route?.parent?.routeConfig?.loadChildren === 'function') {
                const module = (await route.parent.routeConfig.loadChildren());
                const moduleRef = createNgModule(module, this.injector);
                const activatedRoute = this.#getActivatedRoute(this.#rootRoute, component);
                const tab = {
                    key,
                    component,
                    injector: new SdOutletInjector(activatedRoute, moduleRef),
                    isActive: true,
                    url,
                    params,
                    queryParams,
                    data,
                    tabInfoChanges: new Subject(),
                };
                this.tabRouterService.setCurrentTab(tab);
                if (activatedIndex >= 0 && replaceTab) {
                    this.tabs.splice(activatedIndex, 1);
                }
                this.tabs.push(tab);
                // if (existedIndex >= 0 && !switchTab) {
                //   this.tabs[existedIndex] = tab;
                // } else {
                //   this.tabs.push(tab);
                // }
            }
            this.tabRouterNav?.checkUI();
            if (this.tabs.length > 10) {
                this.sdNotifyService.warning('Bạn đã mở quá nhiều tab. Vui lòng tắt các tab không dùng để hệ thống hoạt động tốt hơn.');
            }
            // if (this.tabs.length > 15) {
            //   this.tabs.splice(0, this.tabs.length - 10);
            // }
        }
        // if (existedIndex >= 0 && switchTab) {
        //   const existedTab = this.tabs[existedIndex];
        //   this.tabRouterService.setCurrentTab(existedTab);
        //   this.tabRouterService.pushEvent(existedTab, SdTabActivated);
        // } else {
        //   if (typeof route?.parent?.routeConfig?.loadChildren === 'function') {
        //     const module = await route.parent.routeConfig.loadChildren();
        //     const factory = await this.compiler.compileModuleAsync(module);
        //     const injector = factory.create(this.injector);
        //     const activatedRoute = this.#getActivatedRoute(
        //       this.#rootRoute,
        //       component
        //     );
        //     const tab = {
        //       key,
        //       component,
        //       injector: new SdOutletInjector(activatedRoute, injector),
        //       isActive: true,
        //       name: url,
        //       url,
        //       params,
        //       queryParams,
        //       data
        //     };
        //     this.tabRouterService.setCurrentTab(tab);
        //     if (activatedIndex >= 0 && replaceTab) {
        //       this.tabs.splice(activatedIndex, 1);
        //     }
        //     if (existedIndex >= 0 && !switchTab) {
        //       this.tabs[existedIndex] = tab;
        //     } else {
        //       this.tabs.push(tab);
        //     }
        //   }
        //   this.tabRouterNav?.checkUI();
        //   if (this.tabs.length > 10) {
        //     this.sdNotifyService.notify.warning(
        //       'Bạn đã mở quá nhiều tab. Vui lòng tắt các tab không dùng để hệ thống hoạt động tốt hơn.'
        //     );
        //   }
        //   if (this.tabs.length > 15) {
        //     this.tabs.splice(0, this.tabs.length - 10);
        //   }
        // }
        this.cd.markForCheck();
    };
    #getActivatedRouteSnapshot = (activatedRouteSnapshot) => {
        if (!activatedRouteSnapshot) {
            return null;
        }
        while (activatedRouteSnapshot.firstChild) {
            activatedRouteSnapshot = activatedRouteSnapshot.firstChild;
        }
        return activatedRouteSnapshot;
    };
    #getActivatedRoute = (activatedRoute, component) => {
        if (!activatedRoute) {
            return null;
        }
        if (activatedRoute.component && activatedRoute.component === component) {
            return activatedRoute;
        }
        while (activatedRoute.firstChild) {
            activatedRoute = activatedRoute.firstChild;
            if (activatedRoute.component && activatedRoute.component === component) {
                return activatedRoute;
            }
        }
        return null;
    };
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterOutletComponent, deps: [{ token: i1.Router }, { token: i1.ActivatedRoute }, { token: i0.ChangeDetectorRef }, { token: i0.Injector }, { token: SdTabDecoratorService }, { token: SdTabRouterService }, { token: i4.SdNotifyService }], target: i0.ɵɵFactoryTarget.Component });
    static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "19.2.17", type: SdTabRouterOutletComponent, isStandalone: true, selector: "sd-tab-router-outlet", viewQueries: [{ propertyName: "tabRouterNav", first: true, predicate: ["tabRouterNav"], descendants: true }], ngImport: i0, template: "<sd-tab-router-nav [tabs]=\"tabs\" #tabRouterNav></sd-tab-router-nav>\n\n<div class=\"tab-router__list\">\n  <ng-container *ngFor=\"let tab of tabs; trackBy: tabTrackBy\">\n    <div class=\"tab-router__pane\" [class.active]=\"tab.isActive\" [id]=\"tab.key\">\n      <div class=\"tab-router__content\">\n        <ng-container *ngComponentOutlet=\"tab.component; injector: tab.injector\"></ng-container>\n      </div>\n    </div>\n  </ng-container>\n</div>\n", styles: [":host{display:flex;flex-direction:column;width:100%;height:calc(100vh - 64px)}:host ::ng-deep .sd-loading{max-width:100%;max-height:100%}.tab-router__list{flex:1}.tab-router__pane{display:none;position:relative;height:100%;width:100%}.tab-router__pane.active{display:block}.tab-router__content{position:absolute;inset:0;overflow:auto;height:100%;width:100%}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i5.NgComponentOutlet, selector: "[ngComponentOutlet]", inputs: ["ngComponentOutlet", "ngComponentOutletInputs", "ngComponentOutletInjector", "ngComponentOutletContent", "ngComponentOutletNgModule", "ngComponentOutletNgModuleFactory"], exportAs: ["ngComponentOutlet"] }, { kind: "directive", type: i5.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "ngmodule", type: MatIconModule }, { kind: "ngmodule", type: MatTooltipModule }, { kind: "component", type: SdTabRouterNavComponent, selector: "sd-tab-router-nav", inputs: ["tabs"] }] });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "19.2.17", ngImport: i0, type: SdTabRouterOutletComponent, decorators: [{
            type: Component,
            args: [{ selector: 'sd-tab-router-outlet', standalone: true, imports: [CommonModule, MatIconModule, MatTooltipModule, SdTabRouterNavComponent], template: "<sd-tab-router-nav [tabs]=\"tabs\" #tabRouterNav></sd-tab-router-nav>\n\n<div class=\"tab-router__list\">\n  <ng-container *ngFor=\"let tab of tabs; trackBy: tabTrackBy\">\n    <div class=\"tab-router__pane\" [class.active]=\"tab.isActive\" [id]=\"tab.key\">\n      <div class=\"tab-router__content\">\n        <ng-container *ngComponentOutlet=\"tab.component; injector: tab.injector\"></ng-container>\n      </div>\n    </div>\n  </ng-container>\n</div>\n", styles: [":host{display:flex;flex-direction:column;width:100%;height:calc(100vh - 64px)}:host ::ng-deep .sd-loading{max-width:100%;max-height:100%}.tab-router__list{flex:1}.tab-router__pane{display:none;position:relative;height:100%;width:100%}.tab-router__pane.active{display:block}.tab-router__content{position:absolute;inset:0;overflow:auto;height:100%;width:100%}\n"] }]
        }], ctorParameters: () => [{ type: i1.Router }, { type: i1.ActivatedRoute }, { type: i0.ChangeDetectorRef }, { type: i0.Injector }, { type: SdTabDecoratorService }, { type: SdTabRouterService }, { type: i4.SdNotifyService }], propDecorators: { tabRouterNav: [{
                type: ViewChild,
                args: ['tabRouterNav']
            }] } });
class SdOutletInjector {
    route;
    parent;
    constructor(route, 
    // private childContexts: ChildrenOutletContexts,
    parent) {
        this.route = route;
        this.parent = parent;
    }
    get(token, notFoundValue) {
        if (token === ActivatedRoute && this.route) {
            return this.route;
        }
        // if (token === ChildrenOutletContexts) {
        //   return this.childContexts;
        // }
        return this.parent.injector.get(token, notFoundValue);
    }
}

function SdTabComponent(builder) {
    return (constructor) => {
        SdTabDecoratorService.tabRouterService
            .pipe(filter(service => service !== undefined && service !== null), take(1))
            .subscribe(service => {
            service.addBuilder(builder);
        });
    };
}

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

export { SdTabComponent, SdTabRouterOutletComponent, SdTabRouterService };
//# sourceMappingURL=sd-angular-core-components-tab-router.mjs.map
