package com.sixin.module_p.ui.zuzhuang

import androidx.lifecycle.MutableLiveData
import androidx.lifecycle.viewModelScope
import com.lukouguoji.module_base.base.BasePageViewModel
import com.lukouguoji.module_base.bean.CarOrUldBean
import com.lukouguoji.module_base.bean.GcjBoxAddReqBean
import com.lukouguoji.module_base.bean.GjcBoxAddListBean
import com.lukouguoji.module_base.bean.JianBean
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.commonAdapter
import com.lukouguoji.module_base.ktx.launchCollect
import com.lukouguoji.module_base.ktx.limit
import com.lukouguoji.module_base.ktx.loge
import com.lukouguoji.module_base.ktx.noNull
import com.lukouguoji.module_base.ktx.showToast
import com.lukouguoji.module_base.ktx.toJson
import com.lukouguoji.module_base.ktx.toMap
import com.lukouguoji.module_base.ktx.toRequestBody
import com.lukouguoji.module_base.util.Common
import com.sixin.module_p.helper.PDAHelper
import com.sixin.module_p.model.PdaZzSelectDialogModel
import dev.DevUtils
import dev.utils.common.NumberUtils
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach

class PdaZuZhuangViewModel : BasePageViewModel() {

    // 平板车或集装器
    val carUld = MutableLiveData("")

    // 运单号
    val waybill = MutableLiveData("")

    // 平板车和集装器 数据
    val carUldBean = MutableLiveData(CarOrUldBean())
    var insertId = ""

    // 总件数
    val totalCount = MutableLiveData(0)

    // 总重量
    val totalWeight = MutableLiveData(0.0)

    ///////////////////////////////////////////////////////////////////////////
    // 方法区
    ///////////////////////////////////////////////////////////////////////////

    private fun reset() {
        carUld.value = ""
        waybill.value = ""
        carUldBean.value = CarOrUldBean()
        insertId = ""
        totalCount.value = 0
        totalWeight.value = 0.0
        pageModel.refresh()
        pageModel.handleDataList(emptyList())
    }

    fun init() {
        // 监听扫描信息
        FlowBus.with<String>(ConstantEvent.SCAN_CODE_RESULT)
            .onEach {
                onPdaScan(it)
            }
            .launchIn(viewModelScope)
    }

    /**
     * 清空 点击
     */
    fun clearClick() {
        carUld.value = ""
    }

    /**
     * 确认点击
     */
    fun confirmClick() {
        if (!verifyCarULD()) {
            return
        }
        val adapter = pageModel.rv!!.commonAdapter()!!
        val items = adapter.items as List<GjcBoxAddListBean>
        if (items.isEmpty()) {
            showToast("请扫描或选择运单")
            return
        }
        Common.secondConfirmDialog(
            DevUtils.getTopActivity(),
            "是否确认组装?"
        ) { dialog ->
            dialog.dismiss()
            doConfirm(items)
        }
    }

    private fun doConfirm(items: List<GjcBoxAddListBean>) {
        val bean = GcjBoxAddReqBean(locId = insertId)
        bean.setGjcBoxAddList(items, carUldBean.value!!.uldWeight.noNull("0.0"))
        showLoading()
        launchCollect({
            val map = bean.toMap()
            map["isAdd"] = true
            NetApply.api
                .gjcBoxAddConfirm(map.toRequestBody())
        }) {
            onSuccess = {
                if (it.verifySuccess()) {
                    showToast("操作成功")
                    FlowBus.with<Any>(ConstantEvent.GJC_BOX_ADD_SUCCESS)
                        .tryEmit(true)
                    reset()
                } else {
                    showToast(it.msg.noNull("操作失败"))
                }
            }
            onComplete = {
                dismissLoading()
            }
        }
    }

    /**
     * 校验当前平板车和ULD是否都扫描成功
     */
    private fun verifyCarULD(): Boolean {
        if (carUldBean.value!!.carId.isNullOrEmpty() && carUldBean.value!!.uld.isNullOrEmpty()) {
            showToast("请扫描平板车或ULD信息")
            return false
        }
        return true
    }

    /**
     * Pda扫码回调
     */
    private fun onPdaScan(data: String) {
        val waybill = PDAHelper.getWaybillFormScan(data)
        if (waybill.isEmpty()) {
            carUld.value = data
            carUldChange(false)
        } else {
            this.waybill.value = waybill
            waybillChange(false)
        }
    }

    /**
     * 平板车/集装器 改变监听
     */
    fun carUldChange(focus: Boolean) {
        if (focus) return
        carUld.value?.let {
            getCarOrUldData(it)
        }
    }

    /**
     * 运单号 改变监听
     */
    fun waybillChange(focus: Boolean) {
        if (focus) return
        val code = waybill.value ?: return
        if (NumberUtils.isNumber(code)) {
            // 运单号
            if (code.length == 11) {
                addWaybillInfo(code)
            }
            // 运单号 + 件号
            else if (code.length == 16) {
                addWaybillInfo(code.substring(0, 11), code.substring(11))
            }
        }
        if (code.length > 16) {
            loge("件号 : $code")
            addWaybillInfo(code, code)
        }
    }

    /**
     * 获取运单信息
     * @param waybillCode 运单号
     * @param jianCode 件号
     * @param whid 仓库ID, 不为空,则视为更新
     */
    private fun addWaybillInfo(waybillCode: String, jianCode: String = "", whid: String = "") {
        // 非更新
        if (whid.isEmpty()) {
            val find =
                (pageModel.rv!!.commonAdapter()!!.items as List<GjcBoxAddListBean>).find { it.waybillBean.getWaybillCode() == waybillCode }
            if (find != null) {
                if (jianCode.isEmpty()) {
                    showToast("该运单已在列表中")
                } else {
                    addJian(jianCode, find)
                }
                return
            }
        }
        launchCollect({
            NetApply.api.getGjcWaybillInfo(waybillCode)
        }) {
            onSuccess = {
                if (it.verifySuccess() && it.data != null && !it.data!!.whList.isNullOrEmpty()) {
                    val filter = it.data!!.whList!!.filter { bean -> bean.location.isNullOrEmpty() }
                    if (filter.isEmpty()) {
                        showToast("该运单已装配到设备上")
                    } else {
                        // 重新获取列表
                        val adapter = pageModel.rv!!.commonAdapter()!!
                        val list = adapter.items as List<GjcBoxAddListBean>
                        if (whid.isNotEmpty()) {
                            // 更新数据
                            filter.find { b -> b.whid == whid }?.let { b ->
                                list.find { l -> l.waybillBean.whid == whid }?.let { f ->
                                    f.waybillBean = b
                                    adapter.notifyItemChanged(list.indexOf(f))
                                    addJian(jianCode, f)
                                }
                            }
                        } else if (filter.size > 1) {
                            PdaZzSelectDialogModel(filter) { b ->
                                val listBean = GjcBoxAddListBean(b)
                                adapter.addItem(listBean)
                                loge("新增数据 ${b.whid} , 添加件 : $jianCode")
                                addJian(jianCode, listBean)
                            }.show(DevUtils.getTopActivity())
                        } else {
                            val first = filter.first()
                            val listBean = GjcBoxAddListBean(first)
                            adapter.addItem(listBean)
                            loge("新增数据 ${first.whid} , 添加件 : $jianCode")
                            addJian(jianCode, listBean)
                        }
                    }
                    computeTotal()
                } else {
                    showToast(it.msg.noNull("获取运单信息失败"))
                }
            }
        }
    }

    /**
     * 获取平板车/集装器数据
     */
    private fun getCarOrUldData(data: String) {
        if (data.isEmpty()) {
            return
        }
        launchCollect({
            NetApply.api
                .getCarOrUldInfoForSyZz(data)
        }) {
            onSuccess = {
                if (it.verifySuccess()) {
                    val bean = carUldBean.value!!.createForMerge(it.data!!.data!!)
                    insertCarOrULD(bean)
                } else {
                    showToast(it.msg.noNull("获取数据失败"))
                }
            }
        }
    }

    /**
     * 插入数据
     */
    private fun insertCarOrULD(bean: CarOrUldBean) {
        val map = hashMapOf(
            "carid" to bean.carId,
            "carweight" to bean.carWeight,
            "locId" to insertId,
            "gjcLoading" to listOf(
                mapOf(
                    "carid" to bean.carId,
                    "locId" to insertId,
                    "maxweight" to bean.maxWeight,
                    "maxvolume" to bean.maxVolume,
                    "uld" to bean.uld,
                    "uldflag" to bean.uldFlag,
                    "uldweight" to bean.uldWeight,
                )
            )
        )
        launchCollect({
            NetApply.api
                .gjcBoxInsert(map.toRequestBody())
        }) {
            onSuccess = {
                if (it.verifySuccess()) {
                    it.data?.locId?.let { id -> insertId = id }
                    carUldBean.value = bean
                    loge("插入数据成功 : ${carUldBean.value.toJson()}")
                } else {
                    showToast(it.msg.noNull("插入数据失败"))
                }
            }
        }
    }

    /**
     * 添加件号
     */
    private fun addJian(code: String, bean: GjcBoxAddListBean) {
        if (code.isEmpty()) {
            computeTotal()
            return
        }
        if (bean.jianList.find { b -> b.code == JianBean.getCode(code) } == null) {
            bean.jianList.add(JianBean.create(code))
        }
        computeTotal()
    }

    /**
     * 计算总数
     */
    fun computeTotal(list: List<GjcBoxAddListBean>? = null) {
        val adapter = pageModel.rv!!.commonAdapter()!!
        val items = list ?: adapter.items as List<GjcBoxAddListBean>
        var count = 0
        var weight = 0.0
        items.forEach { bean ->
            count += if (bean.jianList.isEmpty()) bean.waybillBean.pc.noNull("0")
                .toInt() else bean.jianList.size
            weight += (bean.waybillBean.weight.noNull().toDouble())
        }
        totalCount.value = count
        totalWeight.value = weight.limit(2).toDouble()
    }

    override fun getData() {
    }
}