------------------------------------------------------
-- 战意逻辑
------------------------------------------------------

local Lang = require("common.Lang")
local Util = require("common.Util")
local Msg = require("core.Msg")
local ObjHuman = require("core.ObjHuman")
local Broadcast = require("broadcast.Broadcast")
local Grid = require("bag.Grid")
local BagLogic = require("bag.BagLogic")
local ItemDefine = require("bag.ItemDefine")
local HeroLogic = require("hero.HeroLogic")
local Log = require("common.Log")
local FuwenExcel = require("excel.fuwen")
local BingshuLogic = require("fuwen.BingshuLogic")

-- 战意回退配置
local BATTLE_WILL_ROLLBACK_CONFIG = {
    [1] = {  -- 初级
        needItemID = 1050,              -- 消耗道具ID
        needItemCnt = 1,                -- 消耗数量：1个
        returnBattleWillCnt = 1,        -- 返还战意：1个
        returnFragmentID = 177,         -- 返还战意碎片道具ID
        returnFragmentCnt = 0,          -- 返还战意碎片：0
        returnAncientSpiritID = 135,    -- 返还远古之灵道具ID
        returnAncientSpiritCnt = 0       -- 返还远古之灵：0
    },
    [2] = {  -- 中级
        needItemID = 1050,
        needItemCnt = 5,                -- 消耗数量：5个
        returnBattleWillCnt = 4,        -- 返还战意：4个
        returnFragmentID = 177,
        returnFragmentCnt = 10000,      -- 返还战意碎片：10,000
        returnAncientSpiritID = 135,
        returnAncientSpiritCnt = 0
    },
    [3] = {  -- 高级
        needItemID = 1050,
        needItemCnt = 12,               -- 消耗数量：12个
        returnBattleWillCnt = 9,        -- 返还战意：9个
        returnFragmentID = 177,
        returnFragmentCnt = 40000,      -- 返还战意碎片：40,000
        returnAncientSpiritID = 135,
        returnAncientSpiritCnt = 0
    },
    [4] = {  -- 超级
        needItemID = 1050,
        needItemCnt = 50,               -- 消耗数量：50个
        returnBattleWillCnt = 19,       -- 返还战意：19个
        returnFragmentID = 177,
        returnFragmentCnt = 90000,      -- 返还战意碎片：90,000
        returnAncientSpiritID = 135,
        returnAncientSpiritCnt = 100   -- 返还远古之灵：100
    }
}

-- 从配置表中动态获取战意技能组ID
-- 配置表中 skill 表的所有技能都是战意技能
local function getBattleWillGroupIDs()
    local groupIDs = {}
    local groupIDSet = {}
    
    -- 遍历所有兵书技能（isBingshuSkill=1），收集所有 groupID
    -- 因为整个 skill 表都是战意，所以所有兵书技能的 groupID 都是战意技能组ID
    for skillID, skillConfig in pairs(FuwenExcel.skill) do
        if skillConfig and skillConfig.isBingshuSkill == 1 then
            local groupID = skillConfig.groupID
            if groupID and not groupIDSet[groupID] then
                table.insert(groupIDs, groupID)
                groupIDSet[groupID] = true
            end
        end
    end
    
    -- 如果没有找到，使用默认值（兼容性处理）
    if #groupIDs == 0 then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGroupIDs] 未找到战意技能，使用默认值: {1001, 1002}")
        return {1001, 1002}
    end
    
    -- 排序以确保一致性
    table.sort(groupIDs)
    -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGroupIDs] 找到战意技能组ID: "..table.concat(groupIDs, ","))
    return groupIDs
end

-- 缓存战意技能组ID列表（在模块加载时初始化）
local BATTLE_WILL_GROUP_IDS = getBattleWillGroupIDs()

-- 判断是否是战意技能
local function isBattleWillSkill(skillConfig)
    if not skillConfig or not skillConfig.groupID then
        return false
    end
    for _, groupID in ipairs(BATTLE_WILL_GROUP_IDS) do
        if skillConfig.groupID == groupID then
            return true
        end
    end
    return false
end

----------------------------------------- 工具函数 -----------------------------------------

-- 获取战意格子数据（通过索引）
-- 战意数据存储在 heroGrid.bingshu[index] 中，需要判断 groupID == 1002
function getBattleWillGrid(heroGrid, index)
    if not heroGrid then 
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] heroGrid为nil")
        return 
    end
    if not index then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] index为nil")
        return
    end
    -- 从bingshu中获取战意数据
    if not heroGrid.bingshu then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] heroGrid.bingshu为nil")
        return
    end
    local bingshuGrid = heroGrid.bingshu[index]
    if not bingshuGrid then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] heroGrid.bingshu["..index.."]为nil")
        return
    end
    local skillID = bingshuGrid.skillID
    if not skillID then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] skillID为nil, index="..index)
        return
    end
    
    -- 检查是否是战意技能（groupID=1001"狂暴"或groupID=1002"战意"）
    local skillConfig = FuwenExcel.skill[skillID]
    if not skillConfig then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] skillConfig为nil, skillID="..skillID)
        return
    end
    if not isBattleWillSkill(skillConfig) then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] 不是战意技能, groupID="..(skillConfig.groupID or "nil")..", skillID="..skillID..", index="..index)
        return
    end
    
    -- Log.write(Log.LOGID_DEBUG, "[getBattleWillGrid] 找到战意技能: index="..index..", skillID="..skillID..", level="..(skillConfig.lv or "nil"))
    return bingshuGrid, index
end

-- 查找战意所在的索引（遍历所有bingshu格子）
function findBattleWillIndex(heroGrid)
    if not heroGrid or not heroGrid.bingshu then
        -- Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] heroGrid或heroGrid.bingshu为nil")
        return nil
    end
    
    -- Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] 开始遍历所有bingshu格子，查找战意技能（groupID=1001或1002）")
    -- Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] BINGSHU_MAXCNT="..BingshuLogic.BINGSHU_MAXCNT)
    
    -- 遍历所有bingshu格子，查找groupID=1001或1002的技能
    for i = 1, BingshuLogic.BINGSHU_MAXCNT do
        local bingshuGrid = heroGrid.bingshu[i]
        if bingshuGrid then
            local skillID = bingshuGrid.skillID
            --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."]存在, skillID="..(skillID or "nil"))
            if skillID then
                local skillConfig = FuwenExcel.skill[skillID]
                if skillConfig then
                    --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."] skillConfig存在, skillID="..skillID..", groupID="..(skillConfig.groupID or "nil")..", lv="..(skillConfig.lv or "nil")..", name="..(skillConfig.name or "nil"))
                    if isBattleWillSkill(skillConfig) then
                        --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] ✓ 找到战意: index="..i..", skillID="..skillID..", level="..(skillConfig.lv or "nil")..", name="..(skillConfig.name or "nil")..", groupID="..(skillConfig.groupID or "nil"))
                        return i
                    else
                        --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."]不是战意, groupID="..(skillConfig.groupID or "nil"))
                    end
                else
                    --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."] skillConfig为nil, skillID="..skillID)
                end
            else
                --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."] skillID为nil")
            end
        else
            --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] bingshu["..i.."]不存在")
        end
    end
    
    --Log.write(Log.LOGID_DEBUG, "[findBattleWillIndex] ✗ 未找到战意技能（groupID=1001或1002），已遍历所有"..BingshuLogic.BINGSHU_MAXCNT.."个格子")
    return nil
end

-- 获取战意等级
-- 根据skillID判断等级：1002=1级, 2002=2级, 3002=3级, 4002=4级
function getBattleWillLevel(heroGrid, index)
    local grid, actualIndex = getBattleWillGrid(heroGrid, index)
    if not grid then 
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillLevel] grid为nil, index="..(index or "nil"))
        return 0 
    end
    local skillID = grid.skillID
    if not skillID then
        -- Log.write(Log.LOGID_DEBUG, "[getBattleWillLevel] skillID为nil")
        return 0
    end
    
    -- 通过配置表获取等级
    local skillConfig = FuwenExcel.skill[skillID]
    if skillConfig and isBattleWillSkill(skillConfig) then
        local level = skillConfig.lv or 0
        --Log.write(Log.LOGID_DEBUG, "[getBattleWillLevel] 获取到等级: level="..level..", skillID="..skillID..", index="..(index or "nil"))
        return level
    end
    
    --Log.write(Log.LOGID_DEBUG, "[getBattleWillLevel] 不是战意技能, skillID="..skillID)
    return 0
end

-- 获取下一级战意技能ID（参考兵书的getNextSkillID）
function getNextBattleWillSkillID(skillID)
    local tconfig = FuwenExcel.skill[skillID]
    if not tconfig then return end
    if not isBattleWillSkill(tconfig) then return end
    
    for id, config in pairs(FuwenExcel.skill) do
        if (config.isBingshuSkill == 1) and
           isBattleWillSkill(config) and
           (config.groupID == tconfig.groupID) and  -- 保持相同的groupID（1001或1002）
           (config.lv == tconfig.lv + 1) and
           (#config.bingshuUpNeed > 0) then
            return id
        end
    end
end

----------------------------------------- 协议处理 -----------------------------------------

-- 查询回退信息
function sendRollbackQuery(human, heroID, heroIndex, index)
    --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 收到查询请求: heroID="..(heroID or "nil")..", heroIndex="..(heroIndex or "nil")..", index="..(index or "nil"))
    
    local heroGrid = HeroLogic.getHeroGrid(human, heroID, heroIndex)
    if not heroGrid then
        --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 英雄不存在: heroID="..(heroID or "nil")..", heroIndex="..(heroIndex or "nil"))
        return Broadcast.sendErr(human, Lang.COMMON_ARGUMENT_ERROR)
    end
    
    -- 如果传入的index不是战意，尝试查找战意所在的索引
    local battleWillIndex = index
    local grid = getBattleWillGrid(heroGrid, index)
    if not grid then
        --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] index="..index.."不是战意，尝试查找战意所在位置")
        battleWillIndex = findBattleWillIndex(heroGrid)
        if not battleWillIndex then
            -- Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 未找到战意技能")
            return Broadcast.sendErr(human, "当前战意格子为空，无法回退")
        end
        grid = heroGrid.bingshu[battleWillIndex]
    end
    
    local currentLevel = getBattleWillLevel(heroGrid, battleWillIndex)
    -- Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 当前战意等级: "..currentLevel..", index="..battleWillIndex)
    
    -- 检查等级是否可回退（等级0为空，不可回退）
    if currentLevel == 0 or currentLevel < 1 or currentLevel > 4 then
        -- Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 当前等级不可回退: level="..currentLevel)
        return Broadcast.sendErr(human, "当前战意格子为空，无法回退")
    end
    
    local config = BATTLE_WILL_ROLLBACK_CONFIG[currentLevel]
    if not config then
        -- Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 配置不存在: level="..currentLevel)
        return Broadcast.sendErr(human, Lang.COMMON_COMFIG_ERROR)
    end
    
    local msgRet = Msg.gc.GC_BATTLE_WILL_ROLLBACK_QUERY
    msgRet.heroID = heroID
    msgRet.heroIndex = heroIndex
    msgRet.index = battleWillIndex  -- 使用实际找到的索引
    msgRet.currentLevel = currentLevel
    msgRet.targetLevel = 0  -- 回退后等级固定为0（空）
    
    -- 消耗道具
    Grid.makeItem(msgRet.needItem, config.needItemID, config.needItemCnt)
    
    -- 获取当前技能的groupID，确定返还的战意ID
    -- 从技能配置的 bingshuUpNeed 中获取第一个道具ID，那就是对应的战意道具ID
    local currentSkillID = grid.skillID
    local currentSkillConfig = FuwenExcel.skill[currentSkillID]
    local returnBattleWillID = nil
    if currentSkillConfig and currentSkillConfig.bingshuUpNeed and #currentSkillConfig.bingshuUpNeed > 0 then
        -- bingshuUpNeed 格式：{{itemID, count}, ...}
        -- 取第一个道具的ID作为战意道具ID
        local firstNeed = currentSkillConfig.bingshuUpNeed[1]
        if firstNeed and type(firstNeed) == "table" and #firstNeed >= 1 then
            returnBattleWillID = firstNeed[1]
            --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 从bingshuUpNeed获取战意道具ID: "..returnBattleWillID..", groupID="..(currentSkillConfig.groupID or "nil")..", skillID="..currentSkillID)
        end
    end
    
    if not returnBattleWillID then
        --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 无法确定返还战意ID: groupID="..(currentSkillConfig and currentSkillConfig.groupID or "nil")..", skillID="..(currentSkillID or "nil")..", bingshuUpNeed="..(currentSkillConfig and currentSkillConfig.bingshuUpNeed and #currentSkillConfig.bingshuUpNeed or "nil"))
    end
    
    -- 返还物品列表
    msgRet.returnItems[0] = 0
    local itemCnt = 0
    
    -- 返还战意
    if config.returnBattleWillCnt > 0 and returnBattleWillID then
        itemCnt = itemCnt + 1
        if itemCnt <= #msgRet.returnItems then
            Grid.makeItem(msgRet.returnItems[itemCnt], returnBattleWillID, config.returnBattleWillCnt)
        end
    end
    
    -- 返还战意碎片
    if config.returnFragmentCnt > 0 and config.returnFragmentID > 0 then
        itemCnt = itemCnt + 1
        if itemCnt <= #msgRet.returnItems then
            Grid.makeItem(msgRet.returnItems[itemCnt], config.returnFragmentID, config.returnFragmentCnt)
        end
    end
    
    -- 返还远古之灵
    if config.returnAncientSpiritCnt > 0 and config.returnAncientSpiritID > 0 then
        itemCnt = itemCnt + 1
        if itemCnt <= #msgRet.returnItems then
            Grid.makeItem(msgRet.returnItems[itemCnt], config.returnAncientSpiritID, config.returnAncientSpiritCnt)
        end
    end
    
    msgRet.returnItems[0] = itemCnt
    
    --Log.write(Log.LOGID_DEBUG, "[sendRollbackQuery] 发送查询结果: currentLevel="..currentLevel..", index="..battleWillIndex..", needItemCnt="..config.needItemCnt..", returnItemsCount="..itemCnt)
    Msg.send(msgRet, human.fd)
end

-- 执行回退
function rollback(human, heroID, heroIndex, index)
    local heroGrid = HeroLogic.getHeroGrid(human, heroID, heroIndex)
    if not heroGrid then
        return Broadcast.sendErr(human, Lang.COMMON_ARGUMENT_ERROR)
    end
    
    -- 检查index范围（1-BINGSHU_MAXCNT）
    if index and (index < 1 or index > BingshuLogic.BINGSHU_MAXCNT) then
        return Broadcast.sendErr(human, Lang.COMMON_ARGUMENT_ERROR)
    end
    
    -- 如果传入的index不是战意，尝试查找战意所在的索引
    local battleWillIndex = index
    local grid = nil
    if index then
        grid = getBattleWillGrid(heroGrid, index)
    end
    
    if not grid then
        battleWillIndex = findBattleWillIndex(heroGrid)
        if not battleWillIndex then
            return Broadcast.sendErr(human, "当前战意格子为空，无法回退")
        end
        grid = heroGrid.bingshu[battleWillIndex]
    end
    
    -- 获取当前技能配置，确定返还的战意ID和等级
    local currentSkillID = grid.skillID
    local currentSkillConfig = FuwenExcel.skill[currentSkillID]
    if not currentSkillConfig then
        return Broadcast.sendErr(human, Lang.COMMON_COMFIG_ERROR)
    end
    
    -- 检查是否是战意技能
    if not isBattleWillSkill(currentSkillConfig) then
        return Broadcast.sendErr(human, "当前格子不是战意技能，无法回退")
    end
    
    -- 从技能配置中获取等级（更可靠）
    local currentLevel = currentSkillConfig.lv or 0
    
    -- 检查等级是否可回退
    if currentLevel == 0 or currentLevel < 1 or currentLevel > 4 then
        return Broadcast.sendErr(human, "当前战意格子为空，无法回退")
    end
    
    -- 根据技能配置的 bingshuUpNeed 确定返还的战意ID
    -- 从 bingshuUpNeed 中获取第一个道具ID，那就是对应的战意道具ID
    local returnBattleWillID = nil
    if currentSkillConfig.bingshuUpNeed and #currentSkillConfig.bingshuUpNeed > 0 then
        -- bingshuUpNeed 格式：{{itemID, count}, ...}
        -- 取第一个道具的ID作为战意道具ID
        local firstNeed = currentSkillConfig.bingshuUpNeed[1]
        if firstNeed and type(firstNeed) == "table" and #firstNeed >= 1 then
            returnBattleWillID = firstNeed[1]
        end
    end
    
    if not returnBattleWillID then
        --Log.write(Log.LOGID_DEBUG, "[rollback] 无法确定返还战意ID: groupID="..(currentSkillConfig.groupID or "nil")..", skillID="..(currentSkillID or "nil")..", bingshuUpNeed="..(currentSkillConfig.bingshuUpNeed and #currentSkillConfig.bingshuUpNeed or "nil"))
        return Broadcast.sendErr(human, Lang.COMMON_COMFIG_ERROR)
    end
    
    -- 检查消耗道具（回退消耗）
    local config = BATTLE_WILL_ROLLBACK_CONFIG[currentLevel]
    if not config then
        --Log.write(Log.LOGID_DEBUG, "[rollback] 回退配置不存在: level="..currentLevel)
        return Broadcast.sendErr(human, Lang.COMMON_COMFIG_ERROR)
    end
    
    if not BagLogic.checkItemCnt(human, config.needItemID, config.needItemCnt) then
        return Broadcast.sendErr(human, Lang.COMMON_NO_ITEM)
    end
    
    -- 扣除消耗道具
    BagLogic.delItem(human, config.needItemID, config.needItemCnt, "bingshu")
 
    -- 收集返还物品（根据配置）
    local returnItemList = {}
    
    -- 返还战意
    if config.returnBattleWillCnt > 0 and returnBattleWillID then
        returnItemList[returnBattleWillID] = config.returnBattleWillCnt
    end
    
    -- 返还战意碎片
    if config.returnFragmentCnt > 0 and config.returnFragmentID > 0 then
        returnItemList[config.returnFragmentID] = config.returnFragmentCnt
    end
    
    -- 返还远古之灵
    if config.returnAncientSpiritCnt > 0 and config.returnAncientSpiritID > 0 then
        returnItemList[config.returnAncientSpiritID] = config.returnAncientSpiritCnt
    end
    
    -- 发放返还物品（使用通用道具发放逻辑）
    if next(returnItemList) then
        BagLogic.addItemList(human, returnItemList, "bingshu")
    end
    
    -- 更新战意等级为0（清空）- 删除bingshu中的战意技能
    if not heroGrid.bingshu then
        heroGrid.bingshu = {}
    end
    local bingshuGrid = heroGrid.bingshu[battleWillIndex]
    if bingshuGrid then
        local skillConfig = FuwenExcel.skill[bingshuGrid.skillID]
        if skillConfig and isBattleWillSkill(skillConfig) then
            -- 这是战意技能，删除它
            heroGrid.bingshu[battleWillIndex] = nil
        else
            --Log.write(Log.LOGID_DEBUG, "[rollback] WARNING: bingshu["..battleWillIndex.."]不是战意技能, skillID="..(bingshuGrid.skillID or "nil"))
        end
    end
    
    ObjHuman.doCalcHero(human, heroIndex)
    
    -- 发送英雄数据更新（如果需要）
    HeroLogic.sendHeroBagDynamic(human, heroID, heroIndex)
    
    -- 发送GC_BINGSHU_QUERY刷新所有兵书状态
    BingshuLogic.sendQuery(human, heroID, heroIndex)
end
