import * as i0 from '@angular/core';
import { InjectionToken, inject, input, computed, ViewEncapsulation, ChangeDetectionStrategy, Component, makeEnvironmentProviders, Injector, PLATFORM_ID, NgZone, Injectable } from '@angular/core';
import { NgxSonnerToaster, toast } from '@shival99/ngx-sonner';
import { ZThemeService, ZTranslateService } from '@shival99/z-ui/services';
import { zMergeClasses } from '@shival99/z-ui/utils';
import { cva } from 'class-variance-authority';
import { Overlay, OverlayConfig } from '@angular/cdk/overlay';
import { ComponentPortal } from '@angular/cdk/portal';
import { DOCUMENT, isPlatformBrowser } from '@angular/common';

/* eslint-disable @typescript-eslint/no-explicit-any */
const Z_TOAST_DATA = new InjectionToken('Z_TOAST_DATA');
const Z_TOAST_ANIMATION_DURATION = 200;
const Z_TOASTER_CONFIG = new InjectionToken('Z_TOASTER_CONFIG');
const Z_TOASTER_DEFAULT_CONFIG = {
    zTheme: 'system',
    zPosition: 'top-right',
    zRichColors: true,
    zExpand: true,
    zDuration: 2500,
    zVisibleToasts: 3,
    zCloseButton: true,
    zDir: 'auto',
};

const zToastVariants = cva('group toast group-[.toaster]:bg-background group-[.toaster]:text-foreground group-[.toaster]:border-border group-[.toaster]:shadow-lg', {
    variants: {
        zVariant: {
            default: 'group-[.toaster]:bg-background group-[.toaster]:text-foreground',
            success: 'group-[.toaster]:bg-green-50 group-[.toaster]:text-green-800 group-[.toaster]:border-green-200 dark:group-[.toaster]:bg-green-950 dark:group-[.toaster]:text-green-200 dark:group-[.toaster]:border-green-800',
            error: 'group-[.toaster]:bg-red-50 group-[.toaster]:text-red-800 group-[.toaster]:border-red-200 dark:group-[.toaster]:bg-red-950 dark:group-[.toaster]:text-red-200 dark:group-[.toaster]:border-red-800',
            warning: 'group-[.toaster]:bg-amber-50 group-[.toaster]:text-amber-800 group-[.toaster]:border-amber-200 dark:group-[.toaster]:bg-amber-950 dark:group-[.toaster]:text-amber-200 dark:group-[.toaster]:border-amber-800',
            info: 'group-[.toaster]:bg-blue-50 group-[.toaster]:text-blue-800 group-[.toaster]:border-blue-200 dark:group-[.toaster]:bg-blue-950 dark:group-[.toaster]:text-blue-200 dark:group-[.toaster]:border-blue-800',
        },
    },
    defaultVariants: {
        zVariant: 'default',
    },
});

class ZToastComponent {
    _themeService = inject(ZThemeService);
    _config = inject(Z_TOASTER_CONFIG, { optional: true }) ?? Z_TOASTER_DEFAULT_CONFIG;
    class = input('', ...(ngDevMode ? [{ debugName: "class" }] : []));
    zVariant = input('default', ...(ngDevMode ? [{ debugName: "zVariant" }] : []));
    zTheme = input(...(ngDevMode ? [undefined, { debugName: "zTheme" }] : []));
    zPosition = input(...(ngDevMode ? [undefined, { debugName: "zPosition" }] : []));
    zRichColors = input(...(ngDevMode ? [undefined, { debugName: "zRichColors" }] : []));
    zExpand = input(...(ngDevMode ? [undefined, { debugName: "zExpand" }] : []));
    zDuration = input(...(ngDevMode ? [undefined, { debugName: "zDuration" }] : []));
    zVisibleToasts = input(...(ngDevMode ? [undefined, { debugName: "zVisibleToasts" }] : []));
    zCloseButton = input(...(ngDevMode ? [undefined, { debugName: "zCloseButton" }] : []));
    zToastOptions = input({}, ...(ngDevMode ? [{ debugName: "zToastOptions" }] : []));
    zDir = input(...(ngDevMode ? [undefined, { debugName: "zDir" }] : []));
    effectiveTheme = computed(() => this.zTheme() ?? this._config.zTheme ?? 'system', ...(ngDevMode ? [{ debugName: "effectiveTheme" }] : []));
    effectivePosition = computed(() => this.zPosition() ?? this._config.zPosition ?? 'bottom-right', ...(ngDevMode ? [{ debugName: "effectivePosition" }] : []));
    effectiveRichColors = computed(() => this.zRichColors() ?? this._config.zRichColors ?? true, ...(ngDevMode ? [{ debugName: "effectiveRichColors" }] : []));
    effectiveExpand = computed(() => this.zExpand() ?? this._config.zExpand ?? false, ...(ngDevMode ? [{ debugName: "effectiveExpand" }] : []));
    effectiveDuration = computed(() => this.zDuration() ?? this._config.zDuration ?? 4000, ...(ngDevMode ? [{ debugName: "effectiveDuration" }] : []));
    effectiveVisibleToasts = computed(() => this.zVisibleToasts() ?? this._config.zVisibleToasts ?? 3, ...(ngDevMode ? [{ debugName: "effectiveVisibleToasts" }] : []));
    effectiveCloseButton = computed(() => this.zCloseButton() ?? this._config.zCloseButton ?? false, ...(ngDevMode ? [{ debugName: "effectiveCloseButton" }] : []));
    effectiveDir = computed(() => this.zDir() ?? this._config.zDir ?? 'auto', ...(ngDevMode ? [{ debugName: "effectiveDir" }] : []));
    zClasses = computed(() => zMergeClasses('toaster group', zToastVariants({ zVariant: this.zVariant() }), this.class()), ...(ngDevMode ? [{ debugName: "zClasses" }] : []));
    detectTheme = computed(() => {
        const theme = this.effectiveTheme();
        if (theme !== 'system') {
            return theme;
        }
        return this._themeService.isDark() ? 'dark' : 'light';
    }, ...(ngDevMode ? [{ debugName: "detectTheme" }] : []));
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.9", ngImport: i0, type: ZToastComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
    static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "21.0.9", type: ZToastComponent, isStandalone: true, selector: "z-toast, z-toaster", inputs: { class: { classPropertyName: "class", publicName: "class", isSignal: true, isRequired: false, transformFunction: null }, zVariant: { classPropertyName: "zVariant", publicName: "zVariant", isSignal: true, isRequired: false, transformFunction: null }, zTheme: { classPropertyName: "zTheme", publicName: "zTheme", isSignal: true, isRequired: false, transformFunction: null }, zPosition: { classPropertyName: "zPosition", publicName: "zPosition", isSignal: true, isRequired: false, transformFunction: null }, zRichColors: { classPropertyName: "zRichColors", publicName: "zRichColors", isSignal: true, isRequired: false, transformFunction: null }, zExpand: { classPropertyName: "zExpand", publicName: "zExpand", isSignal: true, isRequired: false, transformFunction: null }, zDuration: { classPropertyName: "zDuration", publicName: "zDuration", isSignal: true, isRequired: false, transformFunction: null }, zVisibleToasts: { classPropertyName: "zVisibleToasts", publicName: "zVisibleToasts", isSignal: true, isRequired: false, transformFunction: null }, zCloseButton: { classPropertyName: "zCloseButton", publicName: "zCloseButton", isSignal: true, isRequired: false, transformFunction: null }, zToastOptions: { classPropertyName: "zToastOptions", publicName: "zToastOptions", isSignal: true, isRequired: false, transformFunction: null }, zDir: { classPropertyName: "zDir", publicName: "zDir", isSignal: true, isRequired: false, transformFunction: null } }, exportAs: ["zToast"], ngImport: i0, template: "<ngx-sonner-toaster\n  [theme]=\"detectTheme()\"\n  [class]=\"zClasses()\"\n  [position]=\"effectivePosition()\"\n  [richColors]=\"effectiveRichColors()\"\n  [expand]=\"effectiveExpand()\"\n  [duration]=\"effectiveDuration()\"\n  [visibleToasts]=\"effectiveVisibleToasts()\"\n  [closeButton]=\"effectiveCloseButton()\"\n  [toastOptions]=\"zToastOptions()\"\n  [dir]=\"effectiveDir()\" />\n", dependencies: [{ kind: "component", type: NgxSonnerToaster, selector: "ngx-sonner-toaster", inputs: ["invert", "theme", "position", "hotKey", "richColors", "expand", "duration", "visibleToasts", "closeButton", "toastOptions", "offset", "dir", "class", "style"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush, encapsulation: i0.ViewEncapsulation.None });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.9", ngImport: i0, type: ZToastComponent, decorators: [{
            type: Component,
            args: [{ selector: 'z-toast, z-toaster', imports: [NgxSonnerToaster], standalone: true, changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, exportAs: 'zToast', template: "<ngx-sonner-toaster\n  [theme]=\"detectTheme()\"\n  [class]=\"zClasses()\"\n  [position]=\"effectivePosition()\"\n  [richColors]=\"effectiveRichColors()\"\n  [expand]=\"effectiveExpand()\"\n  [duration]=\"effectiveDuration()\"\n  [visibleToasts]=\"effectiveVisibleToasts()\"\n  [closeButton]=\"effectiveCloseButton()\"\n  [toastOptions]=\"zToastOptions()\"\n  [dir]=\"effectiveDir()\" />\n" }]
        }], propDecorators: { class: [{ type: i0.Input, args: [{ isSignal: true, alias: "class", required: false }] }], zVariant: [{ type: i0.Input, args: [{ isSignal: true, alias: "zVariant", required: false }] }], zTheme: [{ type: i0.Input, args: [{ isSignal: true, alias: "zTheme", required: false }] }], zPosition: [{ type: i0.Input, args: [{ isSignal: true, alias: "zPosition", required: false }] }], zRichColors: [{ type: i0.Input, args: [{ isSignal: true, alias: "zRichColors", required: false }] }], zExpand: [{ type: i0.Input, args: [{ isSignal: true, alias: "zExpand", required: false }] }], zDuration: [{ type: i0.Input, args: [{ isSignal: true, alias: "zDuration", required: false }] }], zVisibleToasts: [{ type: i0.Input, args: [{ isSignal: true, alias: "zVisibleToasts", required: false }] }], zCloseButton: [{ type: i0.Input, args: [{ isSignal: true, alias: "zCloseButton", required: false }] }], zToastOptions: [{ type: i0.Input, args: [{ isSignal: true, alias: "zToastOptions", required: false }] }], zDir: [{ type: i0.Input, args: [{ isSignal: true, alias: "zDir", required: false }] }] } });

/**
 * Provides global toast configuration options
 * Use this in app.config.ts: providers: [provideZToast({ zPosition: 'top-right' })]
 *
 * @param config - Partial configuration to override default options
 * @returns EnvironmentProviders for the toast service
 *
 * @example
 * ```typescript
 * // In app.config.ts
 * export const appConfig: ApplicationConfig = {
 *   providers: [
 *     provideZToast({
 *       zPosition: 'top-right',
 *       zDuration: 5000,
 *       zCloseButton: true,
 *     }),
 *   ],
 * };
 * ```
 */
function provideZToast(config) {
    const mergedConfig = {
        ...Z_TOASTER_DEFAULT_CONFIG,
        ...config,
    };
    return makeEnvironmentProviders([{ provide: Z_TOASTER_CONFIG, useValue: mergedConfig }]);
}

class ZToastService {
    _overlay = inject(Overlay);
    _injector = inject(Injector);
    _platformId = inject(PLATFORM_ID);
    _document = inject(DOCUMENT);
    _ngZone = inject(NgZone);
    _providedConfig = inject(Z_TOASTER_CONFIG, { optional: true });
    _zTranslate = inject(ZTranslateService);
    _overlayRef = null;
    _toasterAttached = false;
    _mutationObserver = null;
    create(config) {
        if (this._toasterAttached) {
            return;
        }
        this._attachToaster(config);
    }
    show(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast(this._translate(message), options);
    }
    success(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.success(this._translate(message), options);
    }
    error(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.error(this._translate(message), options);
    }
    warning(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.warning(this._translate(message), options);
    }
    info(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.info(this._translate(message), options);
    }
    loading(message, options) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.loading(this._translate(message), options);
    }
    promise(promise, messages) {
        this._ensureToasterAttached();
        this._moveToTop();
        return toast.promise(promise, messages);
    }
    dismiss(toastId) {
        toast.dismiss(toastId);
    }
    dismissAll() {
        toast.dismiss();
    }
    destroy() {
        this._disconnectObserver();
        if (this._overlayRef) {
            this._overlayRef.dispose();
            this._overlayRef = null;
            this._toasterAttached = false;
        }
    }
    ngOnDestroy() {
        this.destroy();
    }
    _ensureToasterAttached() {
        if (!this._toasterAttached) {
            this._attachToaster();
        }
    }
    _moveToTop() {
        const wrapperElement = this._overlayRef?.overlayElement?.parentElement;
        if (!wrapperElement?.hasAttribute('popover')) {
            return;
        }
        try {
            wrapperElement.hidePopover();
            wrapperElement.showPopover();
        }
        catch {
            console.warn('Popover API not supported on this browser.');
        }
    }
    _setupOverlayObserver() {
        if (!isPlatformBrowser(this._platformId)) {
            return;
        }
        if (this._mutationObserver) {
            return;
        }
        const overlayContainer = this._document.querySelector('.cdk-overlay-container');
        if (!overlayContainer) {
            return;
        }
        this._ngZone.runOutsideAngular(() => {
            this._mutationObserver = new MutationObserver(mutations => {
                const hasNewPopover = mutations.some(mutation => mutation.type === 'childList' &&
                    Array.from(mutation.addedNodes).some(node => node instanceof HTMLElement && node.classList.contains('cdk-overlay-popover')));
                if (hasNewPopover) {
                    this._moveToTop();
                }
            });
            this._mutationObserver.observe(overlayContainer, {
                childList: true,
                subtree: false,
            });
        });
    }
    _disconnectObserver() {
        if (this._mutationObserver) {
            this._mutationObserver.disconnect();
            this._mutationObserver = null;
        }
    }
    _attachToaster(config) {
        if (!isPlatformBrowser(this._platformId)) {
            return;
        }
        if (this._toasterAttached) {
            return;
        }
        this._overlayRef = this._createOverlay();
        if (!this._overlayRef) {
            return;
        }
        const effectiveConfig = {
            ...Z_TOASTER_DEFAULT_CONFIG,
            ...this._providedConfig,
            ...config,
        };
        const injector = Injector.create({
            parent: this._injector,
            providers: [{ provide: Z_TOASTER_CONFIG, useValue: effectiveConfig }],
        });
        const portal = new ComponentPortal(ZToastComponent, null, injector);
        this._overlayRef.attach(portal);
        this._toasterAttached = true;
        this._setupOverlayObserver();
    }
    _createOverlay() {
        if (!isPlatformBrowser(this._platformId)) {
            return null;
        }
        const overlayConfig = new OverlayConfig({
            hasBackdrop: false,
            positionStrategy: this._overlay.position().global(),
            scrollStrategy: this._overlay.scrollStrategies.noop(),
        });
        const overlayRef = this._overlay.create(overlayConfig);
        overlayRef.overlayElement.style.zIndex = '99999';
        return overlayRef;
    }
    _translate(message) {
        if (!message) {
            return message;
        }
        return this._zTranslate.instant(message) || message;
    }
    static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.0.9", ngImport: i0, type: ZToastService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
    static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "21.0.9", ngImport: i0, type: ZToastService, providedIn: 'root' });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.0.9", ngImport: i0, type: ZToastService, decorators: [{
            type: Injectable,
            args: [{ providedIn: 'root' }]
        }] });

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

export { ZToastComponent, ZToastService, Z_TOASTER_CONFIG, Z_TOASTER_DEFAULT_CONFIG, Z_TOAST_DATA, provideZToast, zToastVariants };
//# sourceMappingURL=shival99-z-ui-components-z-toast.mjs.map
