import Alpine from 'alpinejs';
import { initSmoothScroll } from './smooth-scroll';
import { initAnimations } from './animations';

Alpine.data('header', () => ({
    open: false,
    scrolled: false,
    init() {
        const update = () => { this.scrolled = window.scrollY > 24; };
        const closeAtDesktop = event => {
            if (event.matches && this.open) this.closeMenu(false);
        };
        const desktop = window.matchMedia('(min-width: 1024px)');
        update();
        window.addEventListener('scroll', update, { passive: true });
        desktop.addEventListener('change', closeAtDesktop);
        this.$watch('open', value => {
            document.documentElement.style.overflow = value ? 'hidden' : '';
            window.dispatchEvent(new CustomEvent('servoknit:menu', { detail: { open: value } }));
            if (value) this.$nextTick(() => this.$refs.firstLink?.focus());
        });
        const onKeydown = event => {
            if (event.key === 'Escape' && this.open) this.closeMenu(true);
        };
        window.addEventListener('keydown', onKeydown);
    },
    toggleMenu() { this.open ? this.closeMenu(true) : this.open = true; },
    closeMenu(returnFocus = true) {
        this.open = false;
        if (returnFocus) this.$nextTick(() => this.$refs.trigger?.focus());
    },
    containFocus(event) {
        const focusable = [...this.$el.querySelectorAll('a[href], button:not([disabled])')].filter(el => el.offsetParent !== null);
        if (!focusable.length) return;
        const first = focusable[0];
        const last = focusable[focusable.length - 1];
        if (event.shiftKey && document.activeElement === first) { event.preventDefault(); last.focus(); }
        else if (!event.shiftKey && document.activeElement === last) { event.preventDefault(); first.focus(); }
    },
}));

Alpine.data('processSlider', total => ({
    active: 0,
    total,
    moveTo(index) {
        const panels = [...this.$refs.track.children];
        const target = Math.max(0, Math.min(index, panels.length - 1));
        this.$refs.track.scrollTo({
            left: panels[target] ? panels[target].offsetLeft - panels[0].offsetLeft : 0,
            behavior: window.matchMedia('(prefers-reduced-motion: reduce)').matches ? 'auto' : 'smooth',
        });
        this.active = target;
    },
    previous() { this.moveTo(this.active - 1); },
    next() { this.moveTo(this.active + 1); },
    sync() {
        const track = this.$refs.track;
        const panels = [...track.children];
        if (!panels.length) return;
        const start = panels[0].offsetLeft;
        this.active = panels.reduce((closest, panel, index) => (
            Math.abs(panel.offsetLeft - start - track.scrollLeft) < Math.abs(panels[closest].offsetLeft - start - track.scrollLeft) ? index : closest
        ), 0);
    },
}));

window.Alpine = Alpine;
Alpine.start();

const reduced = window.matchMedia('(prefers-reduced-motion: reduce)').matches;
const lenis = reduced ? null : initSmoothScroll();
initAnimations({ lenis, reduced });
