import { d as deepReady, a as waitAfterFramePaint, k as debounce } from './helpers-BNj87EbG.js';
import { L as ListenerAbstract, a as SingleSubject } from './listener-CClDIhvK.js';

class BalVisibilityListener extends ListenerAbstract {
    constructor() {
        super(...arguments);
        this.waitAfterFramePrint = false;
        this.intersectionObserver = undefined;
        this.intersectionCallback = (records) => {
            const isIntersecting = records.some(record => record.isIntersecting);
            if (isIntersecting) {
                this.notify();
            }
        };
    }
    async connect(el) {
        super.connect(el);
        if (typeof IntersectionObserver === 'undefined') {
            return;
        }
        if (this.waitAfterFramePrint) {
            await deepReady(el);
            await waitAfterFramePaint();
        }
        this.destroyMutationObserver();
        this.intersectionObserver = new IntersectionObserver(this.intersectionCallback, {
            root: null, // Use the viewport as the container
            threshold: 0.5, // Trigger when 50% of the element is visible
        });
        this.intersectionObserver.observe(el);
    }
    disconnect() {
        super.disconnect();
        this.destroyMutationObserver();
    }
    destroyMutationObserver() {
        if (this.intersectionObserver !== undefined) {
            this.intersectionObserver.disconnect();
            this.intersectionObserver = undefined;
        }
    }
}

class BalVisibilitySubject extends SingleSubject {
    constructor() {
        super(observer => {
            observer.visibilityListener();
        });
        this.debouncedNotify = debounce(() => this.notify(), 50);
        this.listener = new BalVisibilityListener();
    }
    attach(observer) {
        var _a, _b;
        super.attach(observer);
        (_a = this.listener) === null || _a === void 0 ? void 0 : _a.connect(observer.el);
        (_b = this.listener) === null || _b === void 0 ? void 0 : _b.add(() => this.debouncedNotify());
    }
    detach() {
        var _a;
        super.detach();
        (_a = this.listener) === null || _a === void 0 ? void 0 : _a.disconnect();
    }
}

function ListenToVisibility() {
    return function (target, _propertyKey, _descriptor) {
        const { connectedCallback, componentDidLoad, disconnectedCallback } = target;
        target.connectedCallback = function () {
            if (!this._balVisibilitySubject) {
                this._balVisibilitySubject = new BalVisibilitySubject();
            }
            return connectedCallback && connectedCallback.call(this);
        };
        target.componentDidLoad = function () {
            this._balVisibilitySubject.attach(this);
            return componentDidLoad && componentDidLoad.call(this);
        };
        target.disconnectedCallback = function () {
            if (this._balVisibilitySubject) {
                this._balVisibilitySubject.detach();
                this._balVisibilitySubject = undefined;
            }
            return disconnectedCallback && disconnectedCallback.call(this);
        };
    };
}

export { ListenToVisibility as L };
