import { h } from "@stencil/core";
/**
 * Affix 固钉组件
 * 将页面元素固定在可视范围内，滚动超过阈值后吸附在顶部或底部
 */
export class Affix {
    host;
    /** 距离窗口顶部达到指定偏移后触发固定 */
    top = 0;
    /** 距离窗口底部达到指定偏移后触发固定（与 top 互斥，优先 bottom） */
    bottom;
    /** 自定义滚动容器 selector（默认 window） */
    target = '';
    /** 当前是否处于固定状态 */
    affixed = false;
    /** 固定状态变化事件，detail 为当前 affixed 布尔值 */
    hbChange;
    scrollTarget = null;
    componentDidLoad() {
        this.scrollTarget = this.resolveTarget();
        if (this.scrollTarget) {
            this.scrollTarget.addEventListener('scroll', this.handleScroll, { passive: true });
        }
        // Note: 真实浏览器在首次 layout 后测量；jsdom 无布局，此处不立即测量，
        // 避免在不精确的 getBoundingClientRect 下误触发 affixed。
    }
    disconnectedCallback() {
        if (this.scrollTarget) {
            this.scrollTarget.removeEventListener('scroll', this.handleScroll);
            this.scrollTarget = null;
        }
    }
    resolveTarget() {
        if (typeof window === 'undefined') {
            return null;
        }
        if (this.target) {
            const el = document.querySelector(this.target);
            return el || window;
        }
        return window;
    }
    updateAffixed(next) {
        if (next === this.affixed) {
            return;
        }
        this.affixed = next;
        this.hbChange.emit(next);
    }
    handleScroll = () => {
        const host = this.host;
        if (!host) {
            return;
        }
        const rect = host.getBoundingClientRect();
        if (this.bottom !== undefined) {
            const viewportH = window.innerHeight || 0;
            this.updateAffixed(rect.bottom > viewportH - this.bottom);
            return;
        }
        this.updateAffixed(rect.top <= this.top);
    };
    onTestScroll() {
        // 测试钩子：jsdom 无真实滚动，通过事件触发一次测量
        this.handleScroll();
    }
    get fixedStyle() {
        if (this.bottom !== undefined) {
            return {
                position: 'fixed',
                bottom: `${this.bottom}px`,
                left: '0',
                right: '0',
                zIndex: 'var(--hb-z-index-fixed)',
            };
        }
        return {
            position: 'fixed',
            top: `${this.top}px`,
            left: '0',
            right: '0',
            zIndex: 'var(--hb-z-index-fixed)',
        };
    }
    render() {
        return (h("div", { key: 'e342673fa2ca768295c96ba2ba6f06c9dee2f38f', class: { 'hb-affix': true, 'hb-affix--fixed': this.affixed }, style: this.affixed ? this.fixedStyle : undefined }, h("slot", { key: 'fd66d7c127a33851bd0ca92a4e42f87a2a623ca7' })));
    }
    static get is() { return "hb-affix"; }
    static get encapsulation() { return "shadow"; }
    static get originalStyleUrls() {
        return {
            "$": ["affix.css"]
        };
    }
    static get styleUrls() {
        return {
            "$": ["affix.css"]
        };
    }
    static get properties() {
        return {
            "top": {
                "type": "number",
                "mutable": false,
                "complexType": {
                    "original": "number",
                    "resolved": "number",
                    "references": {}
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "\u8DDD\u79BB\u7A97\u53E3\u9876\u90E8\u8FBE\u5230\u6307\u5B9A\u504F\u79FB\u540E\u89E6\u53D1\u56FA\u5B9A"
                },
                "getter": false,
                "setter": false,
                "attribute": "top",
                "reflect": false,
                "defaultValue": "0"
            },
            "bottom": {
                "type": "number",
                "mutable": false,
                "complexType": {
                    "original": "number | undefined",
                    "resolved": "number",
                    "references": {}
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "\u8DDD\u79BB\u7A97\u53E3\u5E95\u90E8\u8FBE\u5230\u6307\u5B9A\u504F\u79FB\u540E\u89E6\u53D1\u56FA\u5B9A\uFF08\u4E0E top \u4E92\u65A5\uFF0C\u4F18\u5148 bottom\uFF09"
                },
                "getter": false,
                "setter": false,
                "attribute": "bottom",
                "reflect": false
            },
            "target": {
                "type": "string",
                "mutable": false,
                "complexType": {
                    "original": "string",
                    "resolved": "string",
                    "references": {}
                },
                "required": false,
                "optional": false,
                "docs": {
                    "tags": [],
                    "text": "\u81EA\u5B9A\u4E49\u6EDA\u52A8\u5BB9\u5668 selector\uFF08\u9ED8\u8BA4 window\uFF09"
                },
                "getter": false,
                "setter": false,
                "attribute": "target",
                "reflect": false,
                "defaultValue": "''"
            }
        };
    }
    static get states() {
        return {
            "affixed": {}
        };
    }
    static get events() {
        return [{
                "method": "hbChange",
                "name": "hbChange",
                "bubbles": true,
                "cancelable": true,
                "composed": true,
                "docs": {
                    "tags": [],
                    "text": "\u56FA\u5B9A\u72B6\u6001\u53D8\u5316\u4E8B\u4EF6\uFF0Cdetail \u4E3A\u5F53\u524D affixed \u5E03\u5C14\u503C"
                },
                "complexType": {
                    "original": "boolean",
                    "resolved": "boolean",
                    "references": {}
                }
            }];
    }
    static get elementRef() { return "host"; }
    static get listeners() {
        return [{
                "name": "hbTestScroll",
                "method": "onTestScroll",
                "target": undefined,
                "capture": false,
                "passive": false
            }];
    }
}
//# sourceMappingURL=Affix.js.map
