local this = class("cellIconPetDuel", G_UIModuleBase)
local _commonItemTpl = L_GameTpl:getCommonItemTpl()
local _petCatchItemTpl = L_GameTpl:getPetCatchItemTpl()
local petTpl = L_GameTpl:getPetTpl()
local elementTypeTpl = L_GameTpl:getElementTypeTpl()
local trialPetTpl = L_GameTpl:getTrialPetTpl()
local templateValueTpl = L_GameTpl:getTemplateValueTpl()

function this.bind()
  return {
    img_bg = "",
    img_petIcon = "",
    img_elementBg = "",
    img_elementIcon = "",
    img_subElementBg = "",
    img_subElementIcon = "",
    active_subElementBg = false,
    costNum = "0",
    txt_petName = "",
    levelText = "",
    cdAmount = 0,
    keyText = "",
    keyActive = false,
    cdActive = true,
    selectActive = false,
    healingIconActive = false,
    tagList = {
      moduleName = "pages/petDuel/cellKiBoDuelTag"
    },
    fxBackActive = false,
    glowNormal = false,
    glowHeal = false,
    shiningActive = false,
    shiningFxActive = false,
    normalGlowActive = true,
    shingGlowActive = false
  }
end

function this.methods()
  return {}
end

function this:open()
  self.dissolveBase = 0.26606
  self.dissolveMax = 0.73314
  L_KiBoDuelManager:addListener(L_KiBoDuelManager.event.refreshKiBoHealing, self.refreshHealingIcon, self)
end

function this:close()
  L_KiBoDuelManager:removeListener(L_KiBoDuelManager.event.refreshKiBoHealing, self.refreshHealingIcon, self)
end

function this:disableEvents(isDisable)
  self.isDisableEvents = isDisable
end

function this:refresh()
  if not self.isBind then
    return
  end
  if self.bind.isNext then
    self.bind.cdActive = true
    self.bind.cdAmount = 1
    self:setIconData(self.bind.petInfo)
    self:disableEvents(true)
    self.bind.fxBackActive = false
    self.bindComponents.cdMask.material:SetFloat("_Dissolve", 1)
    return
  end
  self.bind.cdActive = true
  self:disposeRecoverTimer()
  self:setIconData(self.bind.petInfo)
  self:refreshHealingIcon()
end

function this:setIconData(petInfo)
  if not self.isBind then
    return
  end
  self.bind.petInfo = petInfo or self.bind.petInfo
  if not self.bind.petInfo then
    return
  end
  if self.bind.petInfo.is_trial then
    self:refreshSystemPetInfo()
  else
    self:refreshPlayerPetInfo()
  end
end

function this:refreshSystemPetInfo()
  self:setShingGlow(false)
  local trialId = self.bind.petInfo.id
  local trialTpl = trialPetTpl:getTplById(trialId)
  local petId = trialPetTpl:getTrialPet(trialTpl)
  local tpl = petTpl:getTplById(petId)
  self.bind.img_petIcon = petTpl:getKiboCardIcon(tpl)
  self.bind.txt_petName = L_KiBoDuelManager:getPetNameBySlot(self.bind.petInfo.slotId)
  self:refreshElementInfo(tpl)
  self.bind.levelText = string.format("Lv %d", trialPetTpl:getTrialPetLevel(trialTpl))
  if self.bind.index and not self.bind.isNext then
    self.bind.keyActive = true
  end
  self.bind.keyText = tostring(self.bind.index)
  self:refreshPetCost(petId)
  self:refreshTagList(petId)
end

function this:refreshElementInfo(petCfg)
  local elementIds = petTpl:getElement(petCfg)
  local eTpl = elementTypeTpl:getTplById(elementIds[1])
  self.bind.img_bg = elementTypeTpl:getKiBoCardElementBg(eTpl, 1)
  self.bind.img_elementBg = elementTypeTpl:getKiBoCardElementBg(eTpl, 2)
  self.bind.img_elementIcon = elementTypeTpl:getKiBoCardIcon(eTpl)
  self.bind.active_subElementBg = false
  if 1 < #elementIds then
    local sub_eTpl = elementTypeTpl:getTplById(elementIds[2])
    self.bind.active_subElementBg = true
    self.bind.img_subElementBg = elementTypeTpl:getKiBoCardElementBg(eTpl, 2)
    self.bind.img_subElementIcon = elementTypeTpl:getKiBoCardIcon(sub_eTpl)
    self.bind.active_subElementBg = true
  end
end

function this:refreshTagList(petId)
  if not self.isBind then
    return
  end
  local tpl = petTpl:getTplById(petId)
  local tags = petTpl:getKiboDuelTag(tpl)
  local data = {}
  for _, id in ipairs(tags) do
    table.insert(data, {tagId = id})
  end
  self.bind.tagList:clear()
  self.bind.tagList:insert_array(data)
end

function this:refreshPetCost(petId)
  local tempTpl = templateValueTpl:getTplById(petId)
  local cost = templateValueTpl:getPetBaseAttribute(tempTpl)[L_Const.kiBoDuelEnum.petCost]
  if cost ~= nil then
    self.bind.costNum = tostring(cost)
  end
end

function this:refreshPlayerPetInfo()
  local id = self.bind.petInfo.id
  local petData = L_PetStore:getPetItem(id)
  if petData then
    if id ~= self.lastPetGuidId then
      self:setShingGlow(petData:hasFlashGene())
    end
    self.lastPetGuidId = id
    local tpl = petTpl:getTplById(petData.id)
    self.bind.img_petIcon = petTpl:getKiboCardIcon(tpl, petData:isSpecialPet())
    self.bind.txt_petName = L_KiBoDuelManager:getPetNameBySlot(self.bind.petInfo.slotId)
    self:refreshElementInfo(tpl)
    self.bind.levelText = string.format("Lv.%d", petData.lv)
    if self.bind.index then
      self.bind.keyActive = true
    end
    self.bind.keyText = tostring(self.bind.index)
    self:refreshPetCost(petData.id)
    self:refreshTagList(petData.id)
  else
    self:setShingGlow(false)
  end
end

function this:setShingGlow(isShining)
  self.bind.shiningActive = isShining
  self.bind.shiningFxActive = isShining
  self.bind.shingGlowActive = isShining
end

function this:refreshSelect(isSelect, isUse)
  self.bind.selectActive = isSelect
  self.bind.keyActive = not isSelect
  if isSelect then
    self:playCellAnimation("anim_petduel_card_small2big")
  elseif self.lastIsSelect then
    if isUse then
      Timer.once(0.167, function()
        self:playCellAnimation("anim_petduel_card_draw")
      end, self, self.gameObject)
    else
      self:playCellAnimation("anim_petduel_card_big2small")
    end
  end
  self.lastIsSelect = isSelect
end

function this:setPosX(x)
  self:disposeTween()
  self.tweenX = self.bindComponents.rect:DOLocalMoveX(x, 0.25):SetEase(Tweening.Ease.Linear):OnComplete(function()
    self:disposeTween()
  end, self)
end

function this:disposeTween()
  if self.tweenX then
    self.tweenX:Kill()
    self.tweenX = nil
  end
end

function this:refreshHealingIcon()
  if not self.isBind then
    return
  end
  if self.isDisableEvents then
    return
  end
  self.bind.healingIconActive = L_KiBoDuelManager:checkIsPetOnBattle(self.bind.guid)
  self.bind.glowHeal = self.bind.healingIconActive
  self.bind.glowNormal = not self.bind.healingIconActive
end

function this:refreshKiBoDuelCost(data)
  if not self.isBind then
    return
  end
  if self.isDisableEvents then
    return
  end
  if self.isCast then
    self:disposeRecoverTimer()
    self.bind.cdAmount = 0
    self.bind.fxBackActive = true
    self.bindComponents.cdMask.material:SetFloat("_Dissolve", 1)
    return
  end
  local cost = data.currentCost
  if cost >= tonumber(self.bind.costNum) then
    self:disposeRecoverTimer()
    self.bind.cdAmount = 0
    if not self.bind.fxBackActive and data.inRecover then
      L_AudioUtil.playSound("Play_SFX_System_QiboChallenge_Card_Ready")
    end
    self.bind.fxBackActive = true
    self.bindComponents.cdMask.material:SetFloat("_Dissolve", 1)
    return
  end
  self:disposeRecoverTimer()
  self.recoverTimer = Timer.repeated(0.01, function()
    if self.isCast then
      return
    end
    if cost >= tonumber(self.bind.costNum) then
      self:disposeRecoverTimer()
      self.bind.cdAmount = 0
      self.bindComponents.cdMask.material:SetFloat("_Dissolve", 1)
    else
      local percent, _ = L_KiBoDuelManager:getCostData()
      self.bind.cdAmount = 1 - (cost / tonumber(self.bind.costNum) + 1 / tonumber(self.bind.costNum) * percent)
      self.bindComponents.cdMask.material:SetFloat("_Dissolve", self:getDissolveValue(1 - self.bind.cdAmount))
    end
    self.bind.fxBackActive = cost >= tonumber(self.bind.costNum)
  end, self)
end

function this:getDissolveValue(percent)
  local value = (self.dissolveMax - self.dissolveBase) * percent + self.dissolveBase
  return value
end

function this:close()
  self:disposeRecoverTimer()
  self:disposeTween()
end

function this:disposeRecoverTimer()
  if self.recoverTimer ~= nil then
    Timer.remove(self.recoverTimer)
  end
  self.recoverTimer = nil
end

function this:playAnimator(isShow, isPlayAni, delayTime)
  Timer.once(delayTime, function()
    if not self.isBind or not self.bindComponents.cardAnimator then
      return
    end
    self.bindComponents.cardAnimator:SetBool("PlayAnim", isPlayAni)
    self.bindComponents.cardAnimator:SetBool("Show", isShow)
  end, self)
end

function this:setCastStatus(isCast)
  self.isCast = isCast
  self.bind.fxBackActive = isCast
end

function this:playNextAnimation(aniName, delayTime)
  if string.isEmpty(aniName) then
    return
  end
  if delayTime then
    Timer.once(delayTime, function()
      if not self.isBind or not self.bindComponents.nextAnimator then
        return
      end
      self.bindComponents.nextAnimator:Play(aniName)
    end, self)
  else
    if not self.isBind or not self.bindComponents.nextAnimator then
      return
    end
    self.bindComponents.nextAnimator:Play(aniName)
  end
end

function this:playCellAnimation(aniName)
  if string.isEmpty(aniName) then
    return
  end
  if not self.isBind or not self.bindComponents.cardAnimator then
    return
  end
  self.bindComponents.cardAnimator:Play(aniName)
end

return this
