local BattleSkillEntity = require "app/userdata/battle/skill/battle_skill_entity"

local BattleUnitEntity = class("BattleUnitEntity", BaseData)

function BattleUnitEntity:ctor()
end

function BattleUnitEntity:init(unitData, side, team)
	self.unitData = unitData
	self.side = side
	self.team = team
	self.damageCount = 0				-- 记录伤害
	self.healCount = 0					-- 记录治疗
	self.activeSkillReleaseCount = 0	-- 记录主动技能释放次数
	self.hpSkinInfo = nil
	self.hpExpInfo = nil
	self:initSkill()
end

function BattleUnitEntity:initSkill()
	local skinConfig = ConfigManager:getConfig("skin")[self.unitData.skin]
	local skinShow
	if skinConfig then
		skinShow = skinConfig.skill_show
	end
	self.activeSkills = {}
	if self.unitData.normalSkills then
		self.normalSkills = {}
		for k, v in ipairs(self.unitData.normalSkills) do
			local skill = BattleSkillEntity:create(v, GConst.BattleConst.SKILL_TYPE_NORMAL, self, skinShow and skinShow[k])
			table.insert(self.normalSkills, skill)
		end
		self.normalSkillCount = self.unitData.normalSkillCount or #self.normalSkills
	else
		self.normalSkillCount = self.unitData.normalSkillCount or 0
	end
	self.normalSkill = nil
	if self.unitData.activeSkills then
		for k, v in ipairs(self.unitData.activeSkills) do
			local skillShow
			if k == 1 then
				skillShow = skinShow and skinShow[#skinShow]
			end
			local skill = BattleSkillEntity:create(v, GConst.BattleConst.SKILL_TYPE_ACTIVE, self, skillShow)
			table.insert(self.activeSkills, skill)
		end
	end
	if self.unitData.passiveSkills then
		self.passiveSkills = {}
		for k, v in ipairs(self.unitData.passiveSkills) do
			local skill = BattleSkillEntity:create(v, GConst.BattleConst.SKILL_TYPE_PASSIVE, self)
			table.insert(self.passiveSkills, skill)
		end
	end
end

function BattleUnitEntity:getIsBoss()
	return self.unitData.isBoss
end

function BattleUnitEntity:getId()
	return self.unitData.id
end

function BattleUnitEntity:initRougeSkills()
	if self.unitData.rougeSkills then
		local SKILL_ICON_POS = {
			{x =-240, y= 165},
			{x =-240, y= 0},
			{x =-240, y= -165}
		}
		for i,v in ipairs(self.unitData.rougeSkills) do
			-- ModuleManager.BattleManager:onSelectSkill(v, nil, SKILL_ICON_POS[i])
			ModuleManager.BattleManager:onSelectSkill(v, nil, {x =-240, y= 0})
		end
	end
end

function BattleUnitEntity:addSkill(skillId)
	local skillInfo = ConfigManager:getConfig("skill")[skillId]
	if skillInfo == nil then
		return nil
	end
	if skillInfo.effect_type == 1 then -- 主动技能
		local skill = BattleSkillEntity:create(skillId, GConst.BattleConst.SKILL_TYPE_ACTIVE, self)
		table.insert(self.activeSkills, skill)
		return skill
	elseif skillInfo.effect_type == 2 then -- 被动技能
		if self.passiveSkills == nil then
			self.passiveSkills = {}
		end
		local skill = BattleSkillEntity:create(skillId, GConst.BattleConst.SKILL_TYPE_PASSIVE, self)
		table.insert(self.passiveSkills, skill)
		return skill
	end
	return nil
end

function BattleUnitEntity:removeSkill(skillId, sid)
	local skillInfo = ConfigManager:getConfig("skill")[skillId]
	if skillInfo == nil then
		return nil
	end
	if skillInfo.effect_type == 1 then -- 主动技能
		for k, v in ipairs(self.activeSkills) do
			if v:getSid() == sid then
				return table.remove(self.activeSkills, k)
			end
		end
	elseif skillInfo.effect_type == 2 then -- 被动技能
		if self.passiveSkills then
			for k, v in ipairs(self.passiveSkills) do
				if v:getSid() == sid then
					return table.remove(self.passiveSkills, k)
				end
			end
		end
	end
	return nil
end

function BattleUnitEntity:addAttr(name, num, isPercent)
	return self.team:addAttr(name, num, isPercent)
end

function BattleUnitEntity:setAttr(name, num)
	return self.team:setAttrValue(name, num)
end

function BattleUnitEntity:getModelId()
	return self.unitData.modelId
end

function BattleUnitEntity:getMatchType()
	return self.unitData.matchType
end

function BattleUnitEntity:getSide()
	return self.side
end

function BattleUnitEntity:setIsMainUnit(isMainUnit)
	self.isMainUnit = isMainUnit
end

function BattleUnitEntity:getIsMainUnit()
	return self.isMainUnit
end

function BattleUnitEntity:getBody()
	return self.unitData.body
end

function BattleUnitEntity:getNormalSkill(reRandom)
	if self.normalSkills == nil then
		return nil
	end
	if not reRandom then
		return self.normalSkill
	end
	if self.normalSkillIndex == nil then
		self.normalSkillIndex = math.random(1, #self.normalSkills)
	else
		local temp = self.normalSkills[#self.normalSkills]
		self.normalSkills[#self.normalSkills] = self.normalSkills[self.normalSkillIndex]
		self.normalSkills[self.normalSkillIndex] = temp
		self.normalSkillIndex = math.random(1, #self.normalSkills - 1)
	end
	self.normalSkill = self.normalSkills[self.normalSkillIndex]
	return self.normalSkill
end

function BattleUnitEntity:getActiveSkillCount()
	return #self.activeSkills
end

function BattleUnitEntity:getAvailableActiveSkill(index)
	local skill = self.activeSkills[index]
	if skill == nil then
		return
	end
	if skill:getIsAvailable() then
		return skill
	end
	return nil
end

function BattleUnitEntity:getNormalSkillCount()
	return self.normalSkillCount
end

function BattleUnitEntity:getPassiveSkills()
	return self.passiveSkills
end

function BattleUnitEntity:changeSkillId(originSkillId, tartgetSkillId)
	for _, skillEntity in ipairs(self.activeSkills) do
		if skillEntity:getSkillId() == originSkillId then
			skillEntity:changeSkillId(tartgetSkillId)
			return
		end
	end
	if self.passiveSkills then
		for _, skillEntity in ipairs(self.passiveSkills) do
			if skillEntity:getSkillId() == originSkillId then
				skillEntity:changeSkillId(tartgetSkillId)
				break
			end
		end
	end
end

function BattleUnitEntity:addSkillParams(skillId, effect)
	for _, skillEntity in ipairs(self.activeSkills) do
		if skillEntity:getSkillId() == skillId then
			skillEntity:addSkillEffectParams(effect)
			break
		end
	end
	if self.passiveSkills then
		for _, skillEntity in ipairs(self.passiveSkills) do
			if skillEntity:getSkillId() == skillId then
				skillEntity:addSkillEffectParams(effect)
				break
			end
		end
	end
end

function BattleUnitEntity:addSkillRound(skillId, effect)
	for _, skillEntity in ipairs(self.activeSkills) do
		if skillEntity:getSkillId() == skillId then
			skillEntity:addSkillEffectRound(effect)
			break
		end
	end
	if self.passiveSkills then
		for _, skillEntity in ipairs(self.passiveSkills) do
			if skillEntity:getSkillId() == skillId then
				skillEntity:addSkillEffectRound(effect)
				break
			end
		end
	end
end

function BattleUnitEntity:addSkillRatio(skillId, effect)
	for _, skillEntity in ipairs(self.activeSkills) do
		if skillEntity:getSkillId() == skillId then
			skillEntity:addSkillEffectRatio(effect)
			break
		end
	end
	if self.passiveSkills then
		for _, skillEntity in ipairs(self.passiveSkills) do
			if skillEntity:getSkillId() == skillId then
				skillEntity:addSkillEffectRatio(effect)
				break
			end
		end
	end
end

function BattleUnitEntity:getDamageCount()
	return self.damageCount
end

function BattleUnitEntity:setDamageCount(damageCount)
	self.damageCount = damageCount or 0
end

-- 伤害统计
function BattleUnitEntity:addDamageCount(num)
	if num > 0 then -- 加血统计
		self.healCount = self.healCount + num
	else -- 伤害统计
		self.damageCount = self.damageCount - num
	end
end

function BattleUnitEntity:getActiveSkillReleaseCount()
	return self.activeSkillReleaseCount
end

function BattleUnitEntity:setActiveSkillReleaseCount(count)
	self.activeSkillReleaseCount = count or 0
end

-- 主动技能释放次数统计
function BattleUnitEntity:addActiveSkillReleaseCount(num)
	self.activeSkillReleaseCount = self.activeSkillReleaseCount + num
end

function BattleUnitEntity:takeDamageOrCure(num, unitComp)
	return self.team:takeDamageOrCure(num, unitComp)
end

function BattleUnitEntity:getHp()
	return self.team:getHp()
end

function BattleUnitEntity:getMaxHp()
	return self.team:getMaxHp()
end

function BattleUnitEntity:getHpPercent(hp)
	return self.team:getHpPercent(hp)
end

function BattleUnitEntity:getAtk()
	return self.team:getAtk(self.unitData.matchType)
end

function BattleUnitEntity:getDmgAddition()
	return self.team:getDmgAddition(self.unitData.matchType)
end

function BattleUnitEntity:getDmgDec()
	return self.team:getDmgDec(self.unitData.matchType)
end

function BattleUnitEntity:getDecDmg(matchType)
	return self.team:getDecDmg(matchType or self.unitData.matchType)
end

function BattleUnitEntity:getWeakness(matchType)
	return self.team:getWeakness(matchType or self.unitData.matchType)
end

function BattleUnitEntity:getCrit()
	return self.team:getCrit(self.unitData.matchType)
end

function BattleUnitEntity:getCrittime()
	return self.team:getCrittime(self.unitData.matchType)
end

function BattleUnitEntity:getCureAddition()
	return self.team:getCureAddition(self.unitData.matchType)
end

function BattleUnitEntity:getCureDec()
	return self.team:getCureDec()
end

function BattleUnitEntity:getBeDmgToHeal()
	return self.team:getBeDmgToHeal()
end

function BattleUnitEntity:getBeSucked()
	return self.team:getBeSucked()
end

function BattleUnitEntity:getUndeadHp()
	return self.team:getUndeadHp()
end

function BattleUnitEntity:setUndeadHp(hp)
	return self.team:setUndeadHp(hp)
end

function BattleUnitEntity:getNormalAttackAddCount()
	return self.team:getNormalAttackAddCount()
end

function BattleUnitEntity:getThorns()
	return self.team:getThorns()
end

function BattleUnitEntity:getFirstHand()
	return self.team:getFirstHand()
end

function BattleUnitEntity:getDeathSummon()
	return self.team:getDeathSummon()
end

function BattleUnitEntity:getCounterAttack()
	return self.team:getCounterAttack()
end

function BattleUnitEntity:getSkillHurtP()
	return self.team:getSkillHurtP(self.unitData.matchType)
end

function BattleUnitEntity:getSkillHurtFixed()
	return self.team:getSkillHurtFixed(self.unitData.matchType)
end

function BattleUnitEntity:getNormalSkillHurtP()
	return self.team:getNormalSkillHurtP(self.unitData.matchType)
end

function BattleUnitEntity:getNormalSkillHurtFixed()
	return self.team:getNormalSkillHurtFixed(self.unitData.matchType)
end

function BattleUnitEntity:getAllHurtP()
	return self.team:getAllHurtP(self.unitData.matchType)
end

function BattleUnitEntity:addLimit(name, buffEffect)
	return self.team:addLimit(name, buffEffect)
end

function BattleUnitEntity:removeLimit(name)
	return self.team:removeLimit(name)
end

function BattleUnitEntity:getIsLimit()
	return self.team:getIsLimit()
end

function BattleUnitEntity:getActiveSkillLimit()
	return self.team:getActiveSkillLimit()
end

function BattleUnitEntity:addActiveSkillLimit(name)
	return self.team:addActiveSkillLimit(name)
end

function BattleUnitEntity:removeActiveSkillLimit(name)
	self.team:removeActiveSkillLimit(name)
end

function BattleUnitEntity:getIsStun()
	return self.team:getIsStun()
end

function BattleUnitEntity:getIsLethargy()
	return self.team:getIsLethargy()
end

function BattleUnitEntity:getIsFrozen()
	return self.team:getIsFrozen()
end

function BattleUnitEntity:addShield(num)
	self.team:addShield(num)
end

function BattleUnitEntity:getShieldHp()
	return self.team:getShieldHp()
end

function BattleUnitEntity:getShieldRebound()
	return self.team:getShieldRebound()
end

function BattleUnitEntity:addMaxHp(num)
	self.team:addMaxHp(num)
end

function BattleUnitEntity:getBlock()
	return self.team:getBlock()
end

function BattleUnitEntity:getSkinId()
	return self.unitData.skin
end

function BattleUnitEntity:getExp()
	return self.unitData.exp
end

function BattleUnitEntity:getExpTime()
	return self.team:getExpTime()
end

function BattleUnitEntity:getIsDead()
	return self.team:getIsDead()
end

function BattleUnitEntity:getIsInvalidControl()
	return self:getAttrValue(GConst.BattleConst.ATTR_NAME.INVALID_CONTROL) > 0
end

function BattleUnitEntity:getEndDmgAddtionAll()
	return self:getAttrValue(GConst.BattleConst.ATTR_NAME.END_DMG_ADDITION_ALL)
end

function BattleUnitEntity:getEndDmgDecAll()
	return self:getAttrValue(GConst.BattleConst.ATTR_NAME.END_DMG_DEC_ALL)
end

function BattleUnitEntity:getIsImmuneReductionBenefit()
	return self.team:getAttrValue(GConst.BattleConst.ATTR_NAME.IMMUNE_REDUCTION_BENEFIT) > 0
end

function BattleUnitEntity:getAttrValue(attr)
	return self.team:getAttrValue(attr)
end

function BattleUnitEntity:getHpSkinInfo()
	if not self.hpSkinInfo then
		if self.unitData.hpSkinHp and self.unitData.hpSkinSkin then
			self.hpSkinInfo = {}
			for index, v in pairs(self.unitData.hpSkinHp) do
				local skin = self.unitData.hpSkinSkin[index]
				if not skin then
					break
				end
				table.insert(self.hpSkinInfo, {hpp = v, skin = skin})
			end
			table.sort(self.hpSkinInfo, function(a, b)
				return a.hpp < b.hpp
			end)
		end
	end
	return self.hpSkinInfo
end

function BattleUnitEntity:getHpExp()
	if not self.hpExpInfo then
		if self.unitData.hpSkinHp and self.unitData.hpExp then
			self.hpExpInfo = {}
			for index, v in pairs(self.unitData.hpSkinHp) do
				local exp = self.unitData.hpExp[index]
				if not exp then
					break
				end
				table.insert(self.hpExpInfo, {hpp = v, exp = exp})
			end
			table.sort(self.hpExpInfo, function(a, b)
				return a.hpp > b.hpp
			end)
		end
	end
	return self.hpExpInfo
end

function BattleUnitEntity:addSkillExtraUseTimes(skillId, count)
	if self.skillExtraUseTimes == nil then
		self.skillExtraUseTimes = {}
	end
	self.skillExtraUseTimes[skillId] = (self.skillExtraUseTimes[skillId] or 0) + count
end

function BattleUnitEntity:getSkillExtraUseTimes(skillId)
	if self.skillExtraUseTimes == nil then
		return 0
	end
	return self.skillExtraUseTimes[skillId] or 0
end

function BattleUnitEntity:getCanRebirth()
	return self.team:getCanRebirth()
end

function BattleUnitEntity:addCounterAttackCount(count)
	self.team:addCounterAttackCount(count)
end

function BattleUnitEntity:getCounterAttackCount()
	return self.team:getCounterAttackCount()
end

function BattleUnitEntity:clearCounterAttackCount()
	self.team:clearCounterAttackCount()
end

function BattleUnitEntity:getTeamRecordData(name)
	return self.team:getRecordData(name)
end

function BattleUnitEntity:setTeamRecordData(name, value)
	self.team:setRecordData(name, value)
end

function BattleUnitEntity:setIsRebirth()
	self.team:setIsRebirth()
end

function BattleUnitEntity:getIsRebirth()
	return self.team:getIsRebirth()
end

function BattleUnitEntity:rebirth()
	self.team:rebirth()
end

function BattleUnitEntity:tagDeadStatus()
	self.team:tagDeadStatus()
end

function BattleUnitEntity:getTagDeadStatus()
	return self.team:getTagDeadStatus()
end

function BattleUnitEntity:onRoundEnd()
	for k, v in ipairs(self.activeSkills) do
		if not self:getIsLimit() and not self:getActiveSkillLimit() then
			v:cooldown()
		end
	end
end

function BattleUnitEntity:getSkillList()
	local list = {}
	for _, v in ipairs(self.activeSkills or {}) do
		table.insert(list, v.skillId)
	end
	for _, v in ipairs(self.passiveSkills or {}) do
		table.insert(list, v.skillId)
	end
	return list
end

return BattleUnitEntity