<script setup lang="ts">
import { useForm } from '@inertiajs/vue3';
import { computed, ref, watch } from 'vue';
import { toast } from 'vue-sonner';
import { parseRupiah } from '@/lib/rupiah';
import type {
    CuttingMaterialCartItem,
    CuttingProductCatalogItem,
    CuttingRawMaterialCatalogItem,
    CuttingResultCartItem,
} from '@/types/cutting';
import CuttingPosCartDetailDialog from './CuttingPosCartDetailDialog.vue';
import CuttingPosMaterialCatalogPanel from './CuttingPosMaterialCatalogPanel.vue';
import CuttingPosResultCatalogPanel from './CuttingPosResultCatalogPanel.vue';
import CuttingPosSummaryPanel from './CuttingPosSummaryPanel.vue';
import { useCuttingPosCart } from './useCuttingPosCart';

const props = defineProps<{
    rawMaterialCatalog: CuttingRawMaterialCatalogItem[];
    productCatalog: CuttingProductCatalogItem[];
    initialData?: {
        description: string;
        sewing_cost?: string;
        other_cost?: string;
        materials: CuttingMaterialCartItem[];
        results: CuttingResultCartItem[];
    };
    draftMaterials?: CuttingMaterialCartItem[];
    draftResults?: CuttingResultCartItem[];
    submitUrl: string;
    method: 'post' | 'put';
    submitLabel: string;
}>();

const isCreateMode = computed(() => props.method === 'post');
const cartDetailOpen = ref(false);

const form = useForm({
    description: '',
    sewing_cost: '0',
    other_cost: '0',
});

const {
    materialSearch,
    productSearch,
    materialCart,
    resultCart,
    filteredRawMaterials,
    filteredProducts,
    totalMaterialCost,
    totalResultPieces,
    materialLineCost,
    setCarts,
    loadDraftItems,
    getMaterialCartItem,
    getResultCartItem,
    syncResultTotals,
    addMaterial,
    removeMaterial,
    decreaseMaterialQty,
    addResult,
    removeResult,
    decreaseResultQty,
    syncMaterialField,
    syncResultField,
} = useCuttingPosCart({
    rawMaterialCatalog: () => props.rawMaterialCatalog,
    productCatalog: () => props.productCatalog,
    isCreateMode: () => isCreateMode.value,
});

function populateForm() {
    if (!props.initialData) {
        return;
    }

    form.description = props.initialData.description;
    form.sewing_cost = props.initialData.sewing_cost ?? '0';
    form.other_cost = props.initialData.other_cost ?? '0';
    setCarts(props.initialData.materials, props.initialData.results);
}

watch(() => props.initialData, populateForm, { immediate: true });
loadDraftItems(props.draftMaterials ?? [], props.draftResults ?? []);

function buildPayload() {
    const payload: Record<string, unknown> = {
        description: form.description,
        sewing_cost: Number.parseInt(parseRupiah(form.sewing_cost), 10) || 0,
        other_cost: Number.parseInt(parseRupiah(form.other_cost), 10) || 0,
    };

    if (!isCreateMode.value) {
        payload.materials = materialCart.value.map((item) => ({
            raw_material_price_id: item.raw_material_price_id,
            material_usage: item.material_usage,
        }));
        payload.results = resultCart.value.map((item) => ({
            product_variant_id: item.product_variant_id,
            cutting_result: item.cutting_result,
            sample: item.sample,
            original_outside_sample: item.original_outside_sample,
        }));
    }

    return payload;
}

function submit() {
    if (materialCart.value.length === 0) {
        toast.error('Tambahkan minimal satu bahan baku.');

        return;
    }

    if (resultCart.value.length === 0) {
        toast.error('Tambahkan minimal satu hasil produk.');

        return;
    }

    const payload = buildPayload();

    if (props.method === 'put') {
        form.transform(() => payload).put(props.submitUrl, {
            onError: (errors: Record<string, string>) => {
                if (errors.system) {
                    toast.error(errors.system);
                }
            },
        });

        return;
    }

    form.transform(() => payload).post(props.submitUrl, {
        onError: (errors: Record<string, string>) => {
            if (errors.system) {
                toast.error(errors.system);
            }
        },
    });
}
</script>

<template>
    <div class="grid gap-4 xl:grid-cols-[1fr_400px]">
        <div class="space-y-4">
            <CuttingPosMaterialCatalogPanel v-model:material-search="materialSearch"
                :filtered-raw-materials="filteredRawMaterials" :get-material-cart-item="getMaterialCartItem"
                @add-material="addMaterial" @decrease-material-qty="decreaseMaterialQty" />

            <CuttingPosResultCatalogPanel v-model:product-search="productSearch" :filtered-products="filteredProducts"
                :get-result-cart-item="getResultCartItem" @add-result="addResult"
                @decrease-result-qty="decreaseResultQty" />
        </div>

        <CuttingPosSummaryPanel :form="form" :material-cart="materialCart" :result-cart="resultCart"
            :total-result-pieces="totalResultPieces" :submit-label="submitLabel" @submit="submit"
            @open-detail="cartDetailOpen = true" @remove-material="removeMaterial"
            @sync-material-field="syncMaterialField" @remove-result="removeResult"
            @sync-result-totals="syncResultTotals" @sync-result-field="syncResultField" />
    </div>

    <CuttingPosCartDetailDialog v-model:open="cartDetailOpen" :material-cart="materialCart" :result-cart="resultCart"
        :material-line-cost="materialLineCost" :total-material-cost="totalMaterialCost" />
</template>
