'use strict';

(function () {
    const initPurchaseTable = (options) => {
        const table = document.getElementById(options.tableId);
        const addRowButton = document.getElementById(options.addRowButtonId);
        if (!table || !addRowButton) {
            return;
        }

        const body = table.querySelector('tbody');
        if (!body) {
            return;
        }

        const grandTotalInput = options.grandTotalInputId ? document.getElementById(options.grandTotalInputId) : null;
        const taxesInput = options.taxesInputId ? document.getElementById(options.taxesInputId) : null;
        const supplierSelect = options.supplierSelectId ? document.getElementById(options.supplierSelectId) : null;
        const firstProductSelect = body.querySelector('.purchase-product');
        const moneyFormatter = new Intl.NumberFormat('es-CO', {
            minimumFractionDigits: 2,
            maximumFractionDigits: 2,
        });

        const formatMoney = (value) => {
            const numeric = Number(value);
            if (!Number.isFinite(numeric)) {
                return '$0,00';
            }

            return '$' + moneyFormatter.format(numeric);
        };

        const allProductOptions = [];
        const parseVariants = (rawValue) => {
            let variants = [];
            try {
                const parsed = JSON.parse(String(rawValue || '[]'));
                variants = Array.isArray(parsed) ? parsed : [];
            } catch (error) {
                variants = [];
            }

            return variants
                .map((variant) => {
                    const variantId = Number(variant && variant.id ? variant.id : 0);
                    const variantName = String(variant && variant.nombre ? variant.nombre : '').trim();
                    if (!Number.isFinite(variantId) || variantId <= 0 || variantName === '') {
                        return null;
                    }

                    const stockRaw = variant && variant.cantidad !== undefined ? Number(variant.cantidad) : null;
                    const stock = Number.isFinite(stockRaw) ? Math.max(0, Math.floor(stockRaw)) : null;

                    return {
                        id: String(variantId),
                        nombre: variantName,
                        cantidad: stock,
                    };
                })
                .filter((variant) => variant !== null);
        };

        if (firstProductSelect) {
            Array.from(firstProductSelect.options).forEach((option, index) => {
                if (index === 0) {
                    return;
                }

                allProductOptions.push({
                    value: String(option.value || ''),
                    text: String(option.textContent || ''),
                    cost: String(option.getAttribute('data-cost') || '0'),
                    supplierId: String(option.getAttribute('data-supplier-id') || '').trim(),
                    hasVariants: String(option.getAttribute('data-has-variants') || '0') === '1',
                    variants: parseVariants(option.getAttribute('data-variants') || '[]'),
                });
            });
        }

        const populateVariantSelect = (row, productSelect, keepCurrentValue = true) => {
            if (!row || !productSelect) {
                return;
            }

            const variantSelect = row.querySelector('.purchase-variant');
            if (!variantSelect) {
                return;
            }

            const previousValue = keepCurrentValue ? String(variantSelect.value || '') : '';
            const selectedOption = productSelect.options[productSelect.selectedIndex];
            const variants = parseVariants(selectedOption ? selectedOption.getAttribute('data-variants') || '[]' : '[]');
            const hasVariants = String(selectedOption ? selectedOption.getAttribute('data-has-variants') || '0' : '0') === '1'
                && variants.length > 0;

            variantSelect.innerHTML = '';
            const placeholder = document.createElement('option');
            placeholder.value = '';
            placeholder.textContent = hasVariants ? 'Selecciona variación...' : 'Sin variación';
            variantSelect.appendChild(placeholder);

            if (!hasVariants) {
                variantSelect.disabled = true;
                variantSelect.required = false;
                variantSelect.value = '';
                return;
            }

            variants.forEach((variant) => {
                const option = document.createElement('option');
                option.value = variant.id;
                option.textContent = variant.cantidad === null
                    ? variant.nombre
                    : `${variant.nombre} (Stock: ${variant.cantidad})`;
                variantSelect.appendChild(option);
            });

            variantSelect.disabled = false;
            variantSelect.required = true;

            if (previousValue !== '') {
                const hasPrevious = Array.from(variantSelect.options).some((option) => option.value === previousValue);
                variantSelect.value = hasPrevious ? previousValue : '';
            } else {
                variantSelect.value = '';
            }
        };

        const applySupplierFilterToSelect = (productSelect, keepCurrentValue = true) => {
            if (!productSelect) {
                return;
            }

            const selectedSupplierId = supplierSelect ? String(supplierSelect.value || '').trim() : '';
            const previousValue = keepCurrentValue ? String(productSelect.value || '') : '';

            productSelect.innerHTML = '';

            const placeholderOption = document.createElement('option');
            placeholderOption.value = '';
            placeholderOption.textContent = selectedSupplierId !== '' ? 'Seleccione...' : 'Primero selecciona proveedor';
            productSelect.appendChild(placeholderOption);

            if (selectedSupplierId !== '') {
                allProductOptions.forEach((item) => {
                    if (item.supplierId === '' || item.supplierId !== selectedSupplierId) {
                        return;
                    }

                    const option = document.createElement('option');
                    option.value = item.value;
                    option.textContent = item.text;
                    option.setAttribute('data-cost', item.cost);
                    option.setAttribute('data-supplier-id', item.supplierId);
                    option.setAttribute('data-has-variants', item.hasVariants ? '1' : '0');
                    option.setAttribute('data-variants', JSON.stringify(item.variants));
                    productSelect.appendChild(option);
                });
            }

            if (previousValue !== '') {
                const hasPrevious = Array.from(productSelect.options).some((option) => option.value === previousValue);
                if (hasPrevious) {
                    productSelect.value = previousValue;
                } else {
                    productSelect.value = '';
                }
            } else {
                productSelect.value = '';
            }

            productSelect.disabled = selectedSupplierId === '';
        };

        const applySupplierFilter = () => {
            body.querySelectorAll('.purchase-product').forEach((productSelect) => {
                applySupplierFilterToSelect(productSelect);
                const row = productSelect.closest('tr');
                if (!row) {
                    return;
                }

                populateVariantSelect(row, productSelect);

                const costInput = row.querySelector('.purchase-cost');
                if (productSelect.value === '' && costInput) {
                    costInput.value = '0';
                }
                updateLine(row);
            });
            updateGrandTotal();
        };

        const updateLine = (row) => {
            const qtyInput = row.querySelector('.purchase-qty');
            const qtyRaw = parseFloat(qtyInput?.value || '0');
            const qty = Number.isFinite(qtyRaw) ? Math.max(0, Math.floor(qtyRaw)) : 0;
            if (qtyInput && String(qtyInput.value || '') !== String(qty)) {
                qtyInput.value = String(qty > 0 ? qty : 0);
            }
            const cost = parseFloat(row.querySelector('.purchase-cost')?.value || '0');
            const lineTax = parseFloat(row.querySelector('.purchase-line-tax')?.value || '0');
            const lineTotal = (qty * cost) + lineTax;
            const lineTotalInput = row.querySelector('.purchase-line-total');
            if (lineTotalInput) {
                lineTotalInput.value = formatMoney(lineTotal);
                lineTotalInput.dataset.raw = lineTotal.toFixed(2);
            }
        };

        const updateGrandTotal = () => {
            if (!grandTotalInput) {
                return;
            }

            let subtotal = 0;
            body.querySelectorAll('tr').forEach((row) => {
                subtotal += parseFloat(row.querySelector('.purchase-line-total')?.dataset.raw || '0');
            });

            const globalTaxes = parseFloat(taxesInput?.value || '0');
            const total = Math.max(0, subtotal + globalTaxes);
            grandTotalInput.value = formatMoney(total);
        };

        const bindRowEvents = (row) => {
            row.querySelector('.purchase-product')?.addEventListener('change', (event) => {
                const option = event.target.options[event.target.selectedIndex];
                const cost = option.getAttribute('data-cost') || '0';
                const costInput = row.querySelector('.purchase-cost');
                if (costInput) {
                    costInput.value = parseFloat(cost).toFixed(2);
                }
                populateVariantSelect(row, event.target, false);
                updateLine(row);
                updateGrandTotal();
            });

            row.querySelector('.purchase-qty')?.addEventListener('input', () => {
                updateLine(row);
                updateGrandTotal();
            });

            row.querySelector('.purchase-cost')?.addEventListener('input', () => {
                updateLine(row);
                updateGrandTotal();
            });

            row.querySelector('.purchase-line-tax')?.addEventListener('input', () => {
                updateLine(row);
                updateGrandTotal();
            });

            row.querySelector('.purchase-remove-row')?.addEventListener('click', () => {
                if (body.querySelectorAll('tr').length === 1) {
                    return;
                }
                row.remove();
                updateGrandTotal();
            });
        };

        addRowButton.addEventListener('click', () => {
            const firstRow = body.querySelector('tr');
            if (!firstRow) {
                return;
            }

            const clone = firstRow.cloneNode(true);
            const productSelect = clone.querySelector('.purchase-product');
            const qtyInput = clone.querySelector('.purchase-qty');
            const costInput = clone.querySelector('.purchase-cost');
            const lineTaxInput = clone.querySelector('.purchase-line-tax');
            const lineTotalInput = clone.querySelector('.purchase-line-total');

            if (productSelect) {
                productSelect.value = '';
            }
            if (qtyInput) {
                qtyInput.value = '1';
            }
            if (costInput) {
                costInput.value = '0';
            }
            if (lineTaxInput) {
                lineTaxInput.value = '0';
            }
            if (lineTotalInput) {
                lineTotalInput.value = formatMoney(0);
                lineTotalInput.dataset.raw = '0.00';
            }
            const variantSelect = clone.querySelector('.purchase-variant');
            if (variantSelect) {
                variantSelect.value = '';
                variantSelect.disabled = true;
                variantSelect.required = false;
                variantSelect.innerHTML = '<option value="">Sin variación</option>';
            }

            body.appendChild(clone);
            bindRowEvents(clone);
            const cloneProductSelect = clone.querySelector('.purchase-product');
            applySupplierFilterToSelect(cloneProductSelect, false);
            populateVariantSelect(clone, cloneProductSelect, false);
            updateGrandTotal();
        });

        taxesInput?.addEventListener('input', updateGrandTotal);
        supplierSelect?.addEventListener('change', applySupplierFilter);

        body.querySelectorAll('tr').forEach((row) => bindRowEvents(row));
        applySupplierFilter();
        body.querySelectorAll('tr').forEach((row) => {
            const productSelect = row.querySelector('.purchase-product');
            if (productSelect) {
                populateVariantSelect(row, productSelect);
            }
        });
        body.querySelectorAll('tr').forEach((row) => updateLine(row));
        updateGrandTotal();
    };

    initPurchaseTable({
        tableId: 'purchaseTable',
        addRowButtonId: 'purchaseAddRow',
        grandTotalInputId: 'purchaseGrandTotal',
        taxesInputId: 'purchaseTaxes',
        supplierSelectId: 'purchaseSupplier',
    });

    initPurchaseTable({
        tableId: 'purchaseOrderTable',
        addRowButtonId: 'purchaseOrderAddRow',
        supplierSelectId: 'purchaseOrderSupplier',
    });

    const initOrderDetailRows = () => {
        const collapses = document.querySelectorAll('[data-oc-detail-collapse]');
        if (!collapses.length) {
            return;
        }

        collapses.forEach((collapseEl) => {
            const row = collapseEl.closest('tr.vx-oc-detail-row');
            if (!row) {
                return;
            }

            collapseEl.addEventListener('show.bs.collapse', () => {
                row.classList.remove('d-none');
            });

            collapseEl.addEventListener('hide.bs.collapse', () => {
                row.classList.add('d-none');
            });
        });
    };

    initOrderDetailRows();
})();
