/**
 * Animals Module — Plataforma Ganadera
 * Optimized for 2000+ animals — Table-first design
 */

$(document).ready(function () { Animals.init(); });

const Animals = {
    page: 1,
    perPage: 50,
    view: localStorage.getItem('ganadera_animal_view') || 'table',
    filters: {},
    sort: { field: 'created_at', dir: 'desc' },
    _searchTimer: null,
    _loading: false,

    async init() {
        // Set active view button
        $(`.al-view-btn[data-view="${this.view}"]`).addClass('active').siblings().removeClass('active');

        await this.loadFilterOptions();
        await this.loadAnimals();
        this.bindEvents();
    },

    /* ── Filter Options ─────────────────────────────── */
    async loadFilterOptions() {
        const [sp, lo] = await Promise.all([
            API.get('/species'),
            API.get('/lots'),
        ]);
        if (sp.success) sp.data.forEach(s =>
            $('#filterSpecies').append(`<option value="${s.id}">${s.name}</option>`)
        );
        if (lo.success) lo.data.forEach(l =>
            $('#filterLot').append(`<option value="${l.id}">${l.name}</option>`)
        );
    },

    /* ── Load Animals ───────────────────────────────── */
    async loadAnimals() {
        if (this._loading) return;
        this._loading = true;

        const p = new URLSearchParams();
        p.set('page', this.page);
        p.set('per_page', this.perPage);
        p.set('sort', this.sort.field);
        p.set('direction', this.sort.dir);

        Object.entries(this.filters).forEach(([k, v]) => { if (v) p.set(k, v); });
        const search = $('#animalSearch').val();
        if (search) p.set('search', search);

        const res = await API.get('/animals?' + p.toString());
        this._loading = false;

        if (!res.success) { Toast.error('Error cargando animales'); return; }

        const data = res.data || [];
        const meta = res.meta || {};

        // Normalize meta fields (API returns current_page/last_page)
        const totalItems = meta.total || data.length;
        const currentPage = meta.current_page || meta.page || 1;
        const lastPage = meta.last_page || meta.total_pages || 1;
        const perPage = meta.per_page || this.perPage;
        const from = meta.from || ((currentPage - 1) * perPage + 1);
        const to = meta.to || Math.min(currentPage * perPage, totalItems);

        const normalizedMeta = { total: totalItems, page: currentPage, total_pages: lastPage, per_page: perPage, from, to };

        // Update count
        if (totalItems > 0) {
            $('#animalsCount').html(`<span class="al-count-num">${totalItems.toLocaleString()}</span> animales <span class="al-count-range">· ${from}–${to}</span>`);
        } else {
            $('#animalsCount').text('Sin resultados');
        }

        // Active filters badge
        const activeFilters = Object.values(this.filters).filter(v => v).length + (search ? 1 : 0);
        const badge = document.getElementById('activeFiltersBadge');
        if (badge) {
            if (activeFilters > 0) { badge.textContent = activeFilters; badge.style.display = ''; }
            else { badge.style.display = 'none'; }
        }

        if (data.length === 0) {
            document.getElementById('animalsCompact').style.display = 'none';
            document.getElementById('animalsGrid').style.display = 'none';
            document.getElementById('animalsTable').style.display = 'none';
            document.getElementById('emptyState').style.display = '';
            $('#animalsPagination').empty();
            return;
        }

        document.getElementById('emptyState').style.display = 'none';
        this.renderView(data);
        this.renderPagination(normalizedMeta);
    },

    /* ── Render View ────────────────────────────────── */
    renderView(data) {
        const views = ['animalsCompact', 'animalsGrid', 'animalsTable'];
        views.forEach(v => document.getElementById(v).style.display = 'none');

        if (this.view === 'compact') {
            this.renderCompact(data);
            document.getElementById('animalsCompact').style.display = '';
        } else if (this.view === 'grid') {
            this.renderCardGrid(data);
            document.getElementById('animalsGrid').style.display = '';
        } else {
            this.renderTable(data);
            document.getElementById('animalsTable').style.display = '';
        }
    },

    /* ── Table View (default — scalable for 800+) ──── */
    renderTable(animals) {
        const frag = document.createDocumentFragment();

        animals.forEach((a, idx) => {
            const tr = document.createElement('tr');
            tr.dataset.id = a.id;
            tr.className = 'al-tbl-row';

            const photoSrc = a.main_photo || a.primary_photo;
            const photo = photoSrc
                ? `<img class="al-tbl-photo" src="/${photoSrc}" alt="" loading="lazy">`
                : `<div class="al-tbl-photo-ph">${this.speciesIcon(a.species_name)}</div>`;

            const sex = a.sex === 'male' ? '<span class="sex-m">♂</span>' : '<span class="sex-f">♀</span>';
            const statusCls = this.statusClass(a.status);
            const statusLabel = this.statusLabel(a.status);
            const healthCls = this.healthClass(a.health_status);
            const healthLabel = this.healthLabel(a.health_status);
            const weight = a.current_weight ? parseFloat(a.current_weight).toFixed(1) + ' kg' : '—';

            tr.innerHTML = `
                <td class="al-tbl-num">${(this.page - 1) * this.perPage + idx + 1}</td>
                <td>${photo}</td>
                <td class="al-tbl-name-cell">
                    <div class="al-tbl-name">${sex} ${this.esc(a.name || 'Sin nombre')}</div>
                    <div class="al-tbl-id">${this.esc(a.tag_id || a.identifier || '#' + a.id)}</div>
                </td>
                <td><span class="al-chip al-chip-species">${this.esc(a.species_name || '—')}</span></td>
                <td class="al-tbl-hide-sm">${this.esc(a.breed_name || '—')}</td>
                <td class="al-tbl-center">${a.birth_date ? this.age(a.birth_date) : '—'}</td>
                <td class="al-tbl-center al-tbl-hide-sm">${weight}</td>
                <td class="al-tbl-hide-md">${this.esc(a.lot_name || '—')}</td>
                <td><span class="al-chip ${statusCls}">${statusLabel}</span></td>
                <td class="al-tbl-hide-sm"><span class="al-chip ${healthCls}">${healthLabel}</span></td>
                <td>
                    <div class="al-tbl-actions">
                        <a href="/animales/${a.id}" class="al-action-btn" title="Ver perfil">
                            <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M1 12s4-8 11-8 11 8 11 8-4 8-11 8-11-8-11-8z"/><circle cx="12" cy="12" r="3"/></svg>
                        </a>
                        <a href="/animales/${a.id}/editar" class="al-action-btn" title="Editar">
                            <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2"><path d="M11 4H4a2 2 0 00-2 2v14a2 2 0 002 2h14a2 2 0 002-2v-7"/><path d="M18.5 2.5a2.1 2.1 0 013 3L12 15l-4 1 1-4 9.5-9.5z"/></svg>
                        </a>
                    </div>
                </td>`;
            frag.appendChild(tr);
        });

        const body = document.getElementById('animalsTableBody');
        body.innerHTML = '';
        body.appendChild(frag);
    },

    /* ── Compact Grid ─────────────────────────────── */
    renderCompact(animals) {
        const frag = document.createDocumentFragment();

        animals.forEach(a => {
            const div = document.createElement('div');
            div.className = 'al-compact-item';
            div.dataset.id = a.id;

            const photoSrc = a.main_photo || a.primary_photo;
            const photo = photoSrc
                ? `<img class="al-compact-photo" src="/${photoSrc}" alt="" loading="lazy">`
                : `<div class="al-compact-photo-placeholder">${this.speciesIcon(a.species_name)}</div>`;

            const sex = a.sex === 'male'
                ? '<span class="al-sex sex-m">♂</span>'
                : '<span class="al-sex sex-f">♀</span>';

            const statusCls = this.statusClass(a.status);
            const statusLabel = this.statusLabel(a.status);

            div.innerHTML = `
                <div class="al-compact-header">
                    ${photo}
                    <div class="al-compact-info">
                        <span class="al-compact-name">${sex} ${this.esc(a.name || 'Sin nombre')}</span>
                        <span class="al-compact-id">${this.esc(a.tag_id || a.identifier || '#' + a.id)}</span>
                    </div>
                </div>
                <div class="al-compact-meta">
                    ${a.species_name ? `<span class="al-chip al-chip-species">${this.esc(a.species_name)}</span>` : ''}
                    ${a.breed_name ? `<span class="al-chip al-chip-breed">${this.esc(a.breed_name)}</span>` : ''}
                    <span class="al-chip ${statusCls}">${statusLabel}</span>
                </div>`;
            frag.appendChild(div);
        });

        const container = document.getElementById('animalsCompact');
        container.innerHTML = '';
        container.appendChild(frag);
    },

    /* ── Card Grid (with photos) ──────────────────── */
    renderCardGrid(animals) {
        const frag = document.createDocumentFragment();

        animals.forEach(a => {
            const div = document.createElement('div');
            div.className = 'al-card';
            div.dataset.id = a.id;

            const photoSrc = a.main_photo || a.primary_photo;
            const img = photoSrc
                ? `<img class="al-card-img" src="/${photoSrc}" alt="" loading="lazy">`
                : `<div class="al-card-img-ph">${this.speciesIcon(a.species_name, 28)}</div>`;

            const sex = a.sex === 'male' ? '<span class="sex-m">♂</span>' : '<span class="sex-f">♀</span>';
            const statusCls = this.statusClass(a.status);
            const statusLabel = this.statusLabel(a.status);

            div.innerHTML = `
                ${img}
                <div class="al-card-body">
                    <div class="al-card-name">${sex} ${this.esc(a.name || 'Sin nombre')}</div>
                    <div class="al-card-sub">${this.esc(a.tag_id || a.identifier || '#' + a.id)}${a.birth_date ? ' · ' + this.age(a.birth_date) : ''}</div>
                    <div class="al-card-chips">
                        ${a.species_name ? `<span class="al-chip al-chip-species">${this.esc(a.species_name)}</span>` : ''}
                        ${a.breed_name ? `<span class="al-chip al-chip-breed">${this.esc(a.breed_name)}</span>` : ''}
                        <span class="al-chip ${statusCls}">${statusLabel}</span>
                    </div>
                </div>`;
            frag.appendChild(div);
        });

        const container = document.getElementById('animalsGrid');
        container.innerHTML = '';
        container.appendChild(frag);
    },

    /* ── Pagination ──────────────────────────────── */
    renderPagination(meta) {
        const $p = $('#animalsPagination');
        $p.empty();
        if (!meta.total_pages || meta.total_pages <= 1) return;

        const pg = meta.page;
        const tp = meta.total_pages;

        $p.append(`<span class="al-pg-info">Pág. ${pg} de ${tp}</span>`);
        $p.append(`<button class="al-pg-btn" ${pg <= 1 ? 'disabled' : ''} data-page="${pg - 1}">‹ Ant</button>`);

        const pages = this.getPageRange(pg, tp);
        let lastP = 0;
        pages.forEach(i => {
            if (i - lastP > 1) $p.append('<span class="al-pg-dots">…</span>');
            $p.append(`<button class="al-pg-btn${i === pg ? ' active' : ''}" data-page="${i}">${i}</button>`);
            lastP = i;
        });

        $p.append(`<button class="al-pg-btn" ${pg >= tp ? 'disabled' : ''} data-page="${pg + 1}">Sig ›</button>`);
    },

    getPageRange(current, total) {
        if (total <= 9) return Array.from({ length: total }, (_, i) => i + 1);
        const pages = new Set([1, 2, total - 1, total]);
        for (let i = current - 2; i <= current + 2; i++) {
            if (i > 0 && i <= total) pages.add(i);
        }
        return [...pages].sort((a, b) => a - b);
    },

    /* ── Events ──────────────────────────────────── */
    bindEvents() {
        const self = this;

        // View toggle
        $('.al-view-btn').on('click', function () {
            $('.al-view-btn').removeClass('active');
            $(this).addClass('active');
            self.view = $(this).data('view');
            localStorage.setItem('ganadera_animal_view', self.view);
            self.loadAnimals();
        });

        // Per page
        $('#perPageSelect').on('change', function () {
            self.perPage = parseInt($(this).val());
            self.page = 1;
            self.loadAnimals();
        });

        // Filters
        $('#filterSpecies, #filterBreed, #filterSex, #filterStatus, #filterHealthStatus, #filterLot').on('change', function () {
            self.filters = {
                species_id: $('#filterSpecies').val(),
                breed_id: $('#filterBreed').val(),
                sex: $('#filterSex').val(),
                status: $('#filterStatus').val(),
                health_status: $('#filterHealthStatus').val(),
                lot_id: $('#filterLot').val(),
            };
            self.page = 1;
            self.loadAnimals();
        });

        // Species → breeds
        $('#filterSpecies').on('change', async function () {
            const sid = $(this).val();
            const $b = $('#filterBreed').html('<option value="">Raza</option>');
            if (sid) {
                const r = await API.get(`/breeds?species_id=${sid}`);
                if (r.success) r.data.forEach(b =>
                    $b.append(`<option value="${b.id}">${b.name}</option>`)
                );
            }
        });

        // Clear
        $('#btnClearFilters').on('click', () => {
            $('#filtersBar select').val('');
            $('#animalSearch').val('');
            self.filters = {};
            self.page = 1;
            self.loadAnimals();
        });

        // Search (debounced)
        $('#animalSearch').on('input', function () {
            clearTimeout(self._searchTimer);
            self._searchTimer = setTimeout(() => {
                self.page = 1;
                self.loadAnimals();
            }, 350);
        });

        // Pagination
        $(document).on('click', '.al-pg-btn:not(:disabled)', function () {
            self.page = parseInt($(this).data('page'));
            self.loadAnimals();
            window.scrollTo({ top: 0, behavior: 'smooth' });
        });

        // Click → animal profile (compact + card)
        $(document).on('click', '.al-compact-item, .al-card', function () {
            window.location.href = '/animales/' + $(this).data('id');
        });

        // Table row click
        $(document).on('click', '.al-tbl-row', function (e) {
            if (!$(e.target).closest('.al-tbl-actions').length) {
                window.location.href = '/animales/' + $(this).data('id');
            }
        });

        // Sort
        $(document).on('click', '.al-table th.sortable', function () {
            const f = $(this).data('sort');
            if (self.sort.field === f) {
                self.sort.dir = self.sort.dir === 'asc' ? 'desc' : 'asc';
            } else {
                self.sort = { field: f, dir: 'asc' };
            }
            $('.al-table th').removeClass('sort-asc sort-desc');
            $(this).addClass(self.sort.dir === 'asc' ? 'sort-asc' : 'sort-desc');
            self.loadAnimals();
        });

        // Toggle filters panel on mobile
        $('#btnToggleFilters').on('click', function () {
            document.getElementById('filtersBar').classList.toggle('al-filters-open');
        });
    },

    /* ── Helpers ──────────────────────────────────── */
    statusClass(s) {
        return { active: 'al-chip-active', sold: 'al-chip-sold', disposed: 'al-chip-disposed', dead: 'al-chip-dead' }[s] || '';
    },
    statusLabel(s) {
        return { active: 'Activo', sold: 'Vendido', disposed: 'Baja', dead: 'Muerto' }[s] || s || '—';
    },
    healthClass(s) {
        if (!s || s === 'healthy') return 'al-chip-healthy';
        return { sick: 'al-chip-sick', quarantine: 'al-chip-quarantine', treatment: 'al-chip-treatment' }[s] || '';
    },
    healthLabel(s) {
        return { healthy: 'Sano', sick: 'Enfermo', quarantine: 'Cuarentena', treatment: 'Tratamiento' }[s] || s || 'Sano';
    },
    speciesIcon(name, size) {
        const n = (name || '').toLowerCase();
        if (n.includes('cabra') || n.includes('caprin')) return '🐐';
        if (n.includes('vaca') || n.includes('bovin') || n.includes('res')) return '🐄';
        if (n.includes('cerdo') || n.includes('porcin')) return '🐷';
        if (n.includes('gallina') || n.includes('pollo') || n.includes('ave')) return '🐔';
        if (n.includes('oveja') || n.includes('ovin') || n.includes('borrego')) return '🐑';
        if (n.includes('caballo') || n.includes('equin') || n.includes('yegua')) return '🐴';
        const s = size || 14;
        return `<svg width="${s}" height="${s}" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.5"><circle cx="12" cy="12" r="10"/></svg>`;
    },
    age(bd) {
        const b = new Date(bd + 'T00:00:00'), n = new Date();
        const m = (n.getFullYear() - b.getFullYear()) * 12 + n.getMonth() - b.getMonth();
        if (m < 1) return Math.max(0, Math.floor((n - b) / 864e5)) + 'd';
        if (m < 12) return m + 'm';
        const y = Math.floor(m / 12), r = m % 12;
        return r ? y + 'a ' + r + 'm' : y + 'a';
    },
    esc(s) {
        if (!s) return '';
        const d = document.createElement('div');
        d.textContent = s;
        return d.innerHTML;
    },
};
