package com.lukouguoji.gjc.viewModel

import android.content.Intent
import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.viewModelScope
import com.lukouguoji.module_base.base.BaseViewModel
import com.lukouguoji.module_base.bean.GjcUldUseBean
import com.lukouguoji.module_base.bean.GjcWarehouse
import com.lukouguoji.module_base.common.Constant
import com.lukouguoji.module_base.common.ConstantEvent
import com.lukouguoji.module_base.http.net.NetApply
import com.lukouguoji.module_base.impl.FlowBus
import com.lukouguoji.module_base.ktx.launchLoadingCollect
import com.lukouguoji.module_base.ktx.showToast
import com.lukouguoji.module_base.ktx.toRequestBody
import kotlinx.coroutines.launch

/**
 * 国际出港-修改组装重量 ViewModel
 */
class GjcAssembleWeightEditViewModel : BaseViewModel() {

    ///////////////////////////////////////////////////////////////////////////
    // 数据字段
    ///////////////////////////////////////////////////////////////////////////

    // ULD信息Bean（从列表页传入）
    val uldBean = MutableLiveData<GjcUldUseBean>()

    // 运单列表
    val waybillList = MutableLiveData<List<GjcWarehouse>>(emptyList())

    ///////////////////////////////////////////////////////////////////////////
    // ULD信息显示字段
    ///////////////////////////////////////////////////////////////////////////

    val uldNo = MutableLiveData("")           // ULD编号
    val totalPc = MutableLiveData("")         // 总件数
    val totalWeight = MutableLiveData("")     // 总重量
    val cargoWeight = MutableLiveData("")     // 货重

    ///////////////////////////////////////////////////////////////////////////
    // 底部统计字段
    ///////////////////////////////////////////////////////////////////////////

    val sumCargoWeight = MutableLiveData("0")    // 总货重
    val weightError = MutableLiveData("0%")      // 重量误差百分比

    // 传递参数（用于API调用）
    private var useId: Long = 0
    private var uld: String = ""
    private var fdate: String = ""
    private var fno: String = ""

    init {
        // 监听 waybillList 变化，自动触发统计计算
        waybillList.observeForever {
            calculateStatistics()
        }
    }

    ///////////////////////////////////////////////////////////////////////////
    // 初始化
    ///////////////////////////////////////////////////////////////////////////

    fun initOnCreated(intent: Intent) {
        // 接收传入的完整 Bean 对象
        val bean = intent.getSerializableExtra(Constant.Key.BEAN) as? GjcUldUseBean
        bean?.let {
            uldBean.value = it

            // 提取ULD信息字段
            uldNo.value = it.uld
            totalPc.value = it.pc.toString()
            totalWeight.value = it.totalWeight.toString()
            cargoWeight.value = it.cargoWeight.toString()

            // 保存参数用于API调用
            useId = it.useId
            uld = it.uld
            fdate = it.fdate
            fno = it.fno

            // 加载运单数据
            loadData()
        } ?: run {
            showToast("参数错误")
        }
    }

    ///////////////////////////////////////////////////////////////////////////
    // 数据加载
    ///////////////////////////////////////////////////////////////////////////

    private fun loadData() {
        val params = mapOf(
            "useId" to useId,
            "uld" to uld,
            "fdate" to fdate,
            "fno" to fno
        ).toRequestBody()

        launchLoadingCollect({ NetApply.api.getAssembledWaybillsByUld(params) }) {
            onSuccess = { result ->
                val list = result.data ?: emptyList()

                // 为每个运单设置数据变化回调
                list.forEach { warehouse ->
                    warehouse.onDataChanged = {
                        // 数据变化时重新计算统计
                        calculateStatistics()
                    }
                }

                waybillList.value = list

                if (list.isEmpty()) {
                    showToast("暂无运单数据")
                }
            }
            onFailed = { code, msg ->
                showToast("加载失败：$msg")
            }
        }
    }

    /**
     * 计算统计数据：总货重、重量误差
     * - 总货重：运单列表中所有 checkInWeight（入库重量/组装重量）之和
     * - 重量误差：(总货重 - ULD货重) / ULD货重 * 100%
     */
    private fun calculateStatistics() {
        val records = waybillList.value ?: emptyList()

        // 计算总货重（所有运单 checkInWeight 之和，即列表中显示的重量）
        val sumWeight = records.sumOf { it.checkInWeight }
        sumCargoWeight.value = String.format("%.2f", sumWeight)

        // 计算重量误差百分比（相对于ULD的货重）
        val uldCargoWeight = cargoWeight.value?.toDoubleOrNull() ?: 0.0
        val error = if (sumWeight > 0 && uldCargoWeight > 0) {
            ((sumWeight - uldCargoWeight) / uldCargoWeight * 100)
        } else {
            0.0
        }
        weightError.value = String.format("%.1f%%", error)
    }

    ///////////////////////////////////////////////////////////////////////////
    // 按钮事件
    ///////////////////////////////////////////////////////////////////////////

    /**
     * 点击"取消"按钮
     */
    fun onCancelClick() {
        getTopActivity().finish()
    }

    /**
     * 点击"保存"按钮
     */
    fun onSaveClick() {
        val records = waybillList.value ?: return

        if (records.isEmpty()) {
            showToast("没有可保存的数据")
            return
        }

        // 验证数据
        if (!validateRecords(records)) return

        // 调用批量更新接口
        saveRecords(records)
    }

    ///////////////////////////////////////////////////////////////////////////
    // 业务逻辑
    ///////////////////////////////////////////////////////////////////////////

    /**
     * 验证数据
     */
    private fun validateRecords(records: List<GjcWarehouse>): Boolean {
        records.forEachIndexed { index, record ->
            if (record.weight < 0) {
                showToast("第${index + 1}条记录的重量不能为负数")
                return false
            }
        }
        return true
    }

    /**
     * 批量保存运单重量
     */
    private fun saveRecords(records: List<GjcWarehouse>) {
        launchLoadingCollect({
            NetApply.api.updateIntExpAssemble(records.toRequestBody())
        }) {
            onSuccess = { result ->
                if (result.verifySuccess()) {
                    showToast("保存成功")
                    // 发送刷新事件通知列表页
                    viewModelScope.launch {
                        FlowBus.with<String>(ConstantEvent.EVENT_REFRESH).emit("refresh")
                    }
                    // 关闭页面
                    getTopActivity().finish()
                } else {
                    showToast("保存失败")
                }
            }
            onFailed = { code, msg ->
                showToast("保存失败：$msg")
            }
        }
    }
}
