local this = class("pageBag", G_UIPageBase)
local _screenPosToUI = Unity.RectTransformUtility.ScreenPointToLocalPointInRectangle
local _accessoryTpl = L_GameTpl:getAccessoryTpl()
local _taskItemTpl = L_GameTpl:getTaskItemTpl()
local _commonItemBagTypeTpl = L_GameTpl:getCommonItemBagTypeTpl()
local _commonItemTpl = L_GameTpl:getCommonItemTpl()
local _foodTpl = L_GameTpl:getFoodTpl()
local _commonTabTpl = L_GameTpl:getCommonTabTpl()
local columnNum = L_DeviceTpl:getIsPc() and 9 or 8
local minLineNum = L_DeviceTpl:getIsPc() and 6 or 5
local DragAreaType = {
  Bag = 1,
  MountSnackBag = 2,
  HeroSnackBag = 3
}
local NumLimit = {
  [L_BagConst.bagTag.spiritron] = L_GameConstTpl:getValue("BAG_LIMIT_SPIRITRON"),
  [L_BagConst.bagTag.accessory] = L_GameConstTpl:getValue("BAG_LIMIT_ACCESSORY"),
  [L_BagConst.bagTag.petEgg] = L_GameConstTpl:getValue("PET_EGG_LIMITS")
}

function this.bind()
  return {
    module_currency = {
      moduleName = "modulePages/moduleCurrency"
    },
    module_tabList = {
      moduleName = "modulePages/tabList/moduleNewCommonTabListVertical"
    },
    go_subMenuType = true,
    module_subTabList = {
      moduleName = "modulePages/tabList/moduleNewCommonTabList"
    },
    go_sortFilterModule = false,
    module_sortFilter = L_Const.ModuleInfo.SortFilterModule,
    go_extendContent = false,
    isOn_numLimit = false,
    txt_numLimit = "",
    txt_numLimitMax = "",
    scrollList_bag = L_Const.ModuleInfo.CellIconBag,
    go_bagTip = false,
    go_bagTipEmpty = false,
    module_bagTip = {
      moduleName = "pages/bag/moduleBagTip"
    },
    go_moduleSnackBag = false,
    module_mountSnackBag = {
      moduleName = "pages/bag/moduleSnackBag"
    },
    go_imgDrag = false,
    img_drag = nil,
    txt_dragNum = nil,
    enabled_scrollBag = true,
    pos_drag = nil,
    focusItemIndex = 0,
    go_productQuick = false
  }
end

function this.methods()
  return {
    onClick_close = function(self)
      L_UI:close(self.pageName)
    end,
    onclick_showProductQuick = function(self)
      L_UI:open("pageProduct_Quick")
    end,
    module_mountSnackBag = {
      onClick_mask = function(self, bind)
        self:playCancelDragFX()
      end,
      recordBackToBagId = function(self, id)
        self._needShowStopDragFXId = id
      end
    }
  }
end

function this:check(options, callback)
  if L_DungeonManager:getIsInTrainTaskDungeon() then
    callback(false)
    return
  end
  local result = L_SystemUnlockManager:checkAndTip(L_SystemConst.enum.bag)
  if not result then
    callback(false)
    return
  end
  if L_PlayerManager:inKiBoTransformMainControl() then
    L_FlyMsgManager:showNormalMsg(L_WordsTpl:getValue("notice_transform_03"))
    callback(false)
    return
  end
  callback(true)
end

function this:preOpen(options)
  this.super.preOpen(self, options)
  options = options or {}
  if options.bagType then
    self._selectType = options.bagType
  end
  if options.jumpParams then
    self._selectType = tonumber(options.jumpParams[1])
    if not string.isEmpty(options.jumpParams[2]) then
      self._selectSubType = tonumber(options.jumpParams[2])
    end
  end
  L_BagStore:listenCallFunc(L_BagStore.event.refreshBag, self.onEvent_refreshBag, self)
  L_AccessoryStore:listenCallFunc(L_AccessoryStore.event.refreshAccessory, self.onEvent_refreshAccessory, self)
  L_AccessoryStore:listenCallFunc(L_AccessoryStore.event.refreshAccessoryList, self.onEvent_refreshAccessoryList, self)
  L_SpiritronStore:listenCallFunc(L_SpiritronStore.event.refreshWeapon, self.onEvent_refreshSpiritron, self)
  L_PetStore:listenCallFunc(L_PetStore.event.removePetEgg, self.onEvent_refreshPetEgg, self)
  L_SnackBagStore:listenCallFunc(L_SnackBagStore.event.selectBagItemUseType, self.onEvent_selectBagItemUseType, self)
  L_SystemUnlockStore:listenCallFunc(L_SystemUnlockStore.event.updateSystem, self.refreshSystemUnlock, self)
  self._mountSnackBagModule = self.modules.module_mountSnackBag
  self._bagTipModule = self.modules.module_bagTip
  self:initCurrencyModule()
  self:initMenu()
  self:refreshSystemUnlock()
  self:updateBagList()
end

function this:show()
  self:registerShortCut(true)
end

function this:close()
  this.super.close(self)
  if self._selectType == L_BagConst.bagTag.food then
    self:configTouch("-")
  end
  L_BagStore:unListenCallFunc(L_BagStore.event.refreshBag, self.onEvent_refreshBag)
  L_AccessoryStore:unListenCallFunc(L_AccessoryStore.event.refreshAccessory, self.onEvent_refreshAccessory)
  L_AccessoryStore:unListenCallFunc(L_AccessoryStore.event.refreshAccessoryList, self.onEvent_refreshAccessoryList)
  L_SpiritronStore:unListenCallFunc(L_SpiritronStore.event.refreshWeapon, self.onEvent_refreshSpiritron)
  L_PetStore:unListenCallFunc(L_PetStore.event.removePetEgg, self.onEvent_refreshPetEgg)
  L_SnackBagStore:unListenCallFunc(L_SnackBagStore.event.selectBagItemUseType, self.onEvent_selectBagItemUseType, self)
  L_BagStore:clearNewItemDic()
  L_TimerManager:clearTimer(self)
  L_SystemUnlockStore:unListenCallFunc(L_SystemUnlockStore.event.updateSystem, self.refreshSystemUnlock, self)
  if self._frameTaskId then
    FrameScheduler.remove(self._frameTaskId)
  end
end

function this:initCurrencyModule()
  local tpl_sys = L_GameTpl:getSystemUnlockTpl():getTplById(L_SystemConst.enum.bag)
  self.modules.module_currency:refreshRes(tpl_sys)
end

function this:updateMenuType()
  self._bagTipModule:reset()
  self:resetSelectData()
  self:initSortFilterModule()
  self:initSubMenuType()
  self:refreshNumLimit()
  self:initMountSnackBag()
  local numLimit = NumLimit[self._selectType]
  local needShowNumLimit = not math.isEmpty(numLimit)
  self.bind.go_extendContent = needShowNumLimit or self.bind.go_sortFilterModule
  local isFood = self._selectType == L_BagConst.bagTag.food
  self:configTouch(isFood and "+" or "-")
  self:registerShortCut(isFood)
end

function this:initSortFilterModule()
  local tpl = _commonItemBagTypeTpl:getTplById(self._selectType)
  local needShowSortFilter = _commonItemBagTypeTpl:getSortFilter(tpl)
  self.bind.go_sortFilterModule = needShowSortFilter
  if not needShowSortFilter then
    return
  end
  local callback = function()
    self:resetSelectData()
    self:updateBagList()
  end
  self._accessorySortFilter = self._accessorySortFilter or L_SortFilterManager:createSortFilter(L_SystemConst.enum.bagAccessory, callback, callback)
  self._spiritronSortFilter = self._spiritronSortFilter or L_SortFilterManager:createSortFilter(L_SystemConst.enum.bagSpiritron, callback, callback)
  if self._selectType == L_BagConst.bagTag.accessory then
    self._accessorySortFilter:bindModule(self.modules.module_sortFilter)
  elseif self._selectType == L_BagConst.bagTag.spiritron then
    self._spiritronSortFilter:bindModule(self.modules.module_sortFilter)
  end
end

function this:initSubMenuType()
  local tpl_bagItemType = _commonItemBagTypeTpl:getTplById(self._selectType)
  local subTypeList = _commonItemBagTypeTpl:getSubType(tpl_bagItemType)
  local needShowSubType = not table.isEmpty(subTypeList)
  if not needShowSubType then
    self._selectSubType = nil
  elseif not self._selectSubType then
    self._selectSubType = subTypeList[1]
  end
  self.bind.go_subMenuType = needShowSubType
  if needShowSubType then
    local selectIndex = 1
    for index, v in ipairs(subTypeList) do
      if v == self._selectSubType then
        selectIndex = index
        break
      end
    end
    self.modules.module_subTabList:setData(subTypeList, function(tab)
      if self._selectSubType == tab then
        return
      end
      self:resetSelectData()
      self._selectSubType = tab
      self:updateBagList()
      self.bindComponents.ani_pageBag:Stop()
      self.bindComponents.ani_pageBag:Play("anim_bag_change_ZB")
    end, selectIndex)
  end
end

function this:updateBagList()
  self:getBagDataList()
  self:insertArrayDataList(self._dataList)
  self:refreshNumLimit()
end

function this:insertArrayDataList(dataList)
  local lineNum = math.ceil(#dataList / columnNum)
  lineNum = math.max(minLineNum, lineNum)
  local tmp = {}
  local dataListCount = #dataList
  for i = 1, lineNum * columnNum do
    local cell = {}
    if i <= dataListCount then
      cell = dataList[i]
      cell.index = i
      cell.isStackMode = true
      cell.stackIndex = cell.stackIndex or 1
      cell.noTip = true
      if cell.guid then
        if self._selectType == L_BagConst.bagTag.accessory then
          local serverData = L_AccessoryStore:getAccessory(cell.guid)
          cell.lock = serverData.lock
        elseif self._selectType == L_BagConst.bagTag.spiritron then
          local serverData = L_SpiritronStore:getSpiritronItem(cell.guid)
          cell.lock = serverData.lock
        end
      end
      
      function cell.callback(module)
        if module.bind.guid == self._selectGuid and self._selectStackIndex == module.bind.stackIndex then
          return
        end
        self._selectGuid = module.bind.guid
        self._selectIndex = module.bind.index
        self._selectStackIndex = module.bind.stackIndex
        if self._selectType == L_BagConst.bagTag.petEgg then
          L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Egg_Click")
        else
          L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Item_Click")
        end
        self:setBagListActive()
        self:updateTip()
      end
    end
    table.insert(tmp, cell)
  end
  self.bind.scrollList_bag:clear()
  self.bind.scrollList_bag:insert_array(tmp)
  local isRenderDataEmpty = table.isEmpty(dataList)
  self.bind.go_bagTip = not isRenderDataEmpty
  self.bind.go_bagTipEmpty = isRenderDataEmpty
  local lastType = self._lastSelectType
  self._lastSelectType = self._selectType
  if lastType ~= self._selectType then
    self._frameTaskId = FrameScheduler.add(function()
      self.bindComponents.verGridView_bag:ReloadData()
    end)
  end
  if isRenderDataEmpty then
    self:resetSelectData()
    if lastType ~= self._selectType then
      self.bindComponents.ani_tipEmpty:Stop()
      self.bindComponents.ani_tipEmpty:Play("anim_Nbag_tipempty_in")
      self._bagTipModule:setEmpty()
    end
    return
  end
  local node, index = table.ipairsFind(dataList, function(value)
    return value.guid == self._selectGuid
  end)
  self._selectGuid = not math.isEmpty(index) and self._selectGuid
  self._selectGuid = not self._selectGuid and dataList[self._selectIndex] and dataList[self._selectIndex].guid
  self._selectGuid = self._selectGuid or dataList[1].guid
  self:setBagListActive()
  self:updateTip()
end

function this:setBagListActive()
  for i, v in pairs(self.modules.scrollList_bag) do
    v:setSel(self._selectGuid == v.bind.guid and self._selectStackIndex == v.bind.stackIndex)
  end
end

function this:getBagDataList()
  if self._selectType == L_BagConst.bagTag.spiritron then
    self._dataList = self:getSpiritronDataList()
  elseif self._selectType == L_BagConst.bagTag.accessory then
    self._dataList = self:getAccessoryDataList()
  elseif self._selectType == L_BagConst.bagTag.taskProp then
    self._dataList = self:getTaskPropDataList()
  elseif self._selectType == L_BagConst.bagTag.petEgg then
    self._dataList = self:getPetEggDataList()
  elseif self._selectType == L_BagConst.bagTag.collectionTool then
    self._dataList = self:getCollectionToolList()
  else
    self._dataList = self:getCommonItemDataList(self._selectType, self._selectSubType)
  end
end

function this:getSpiritronDataList()
  local tmp = {}
  for i, v in pairs(L_SpiritronStore:getSpiritronList()) do
    local cell = {
      guid = v.guid,
      itemType = L_Const.resType.spiritron,
      itemId = v.spiritronId
    }
    table.insert(tmp, cell)
  end
  self._spiritronSortFilter:sortFilterList(tmp)
  return tmp
end

function this:getAccessoryDataList()
  local tmp = {}
  local subTypeValue = _commonTabTpl:getValue(_commonTabTpl:getTplById(self._selectSubType))
  for i, v in pairs(L_AccessoryStore:getHeroAccessory()) do
    local aTpl = _accessoryTpl:getTplById(v.accessoryId)
    if _accessoryTpl:getType(aTpl) == subTypeValue then
      local cell = {
        guid = v.guid,
        itemType = L_Const.resType.accessory,
        itemId = v.accessoryId
      }
      table.insert(tmp, cell)
    end
  end
  self._accessorySortFilter:sortFilterList(tmp)
  return tmp
end

function this:getTaskPropDataList()
  local tmp = {}
  for i, v in pairs(L_TaskStore:getTaskPropDic()) do
    local tpl = _taskItemTpl:getTplById(v.itemId)
    if _taskItemTpl:getInBag(tpl) then
      local cell = {
        guid = v.itemId,
        itemType = L_Const.resType.taskItem,
        quality = _taskItemTpl:getRarity(tpl)
      }
      table.insert(tmp, cell)
    end
  end
  L_CommonUtil.multipleSortByKey(tmp, {"quality", "-guid"})
  return tmp
end

function this:getPetEggDataList()
  local tmp = {}
  for i, v in pairs(L_PetStore:getPetEggList()) do
    if not L_PetStore:checkIsEggHatch(v.guid) then
      local cell = {
        guid = v.guid,
        itemType = L_Const.resType.petEgg,
        itemId = v.configId,
        isWild = table.isEmpty(v.main_parents) and 0
      }
      table.insert(tmp, cell)
    end
  end
  L_CommonUtil.multipleSortByKey(tmp, {
    "-itemId",
    "-isWild",
    "-guid"
  })
  return tmp
end

function this:getCollectionToolList()
  local tmp = {}
  for _, item in pairs(L_CollectionToolStore:getToolsMap()) do
    table.insert(tmp, {
      guid = item.guid,
      itemType = L_Const.resType.collectionTool,
      itemId = item.id
    })
  end
  L_CommonUtil.multipleSortByKey(tmp, {
    "-itemId",
    "-endurance",
    "-guid"
  })
  return tmp
end

function this:getCommonItemDataList(bagType, subType)
  local tmp = {}
  for i, v in pairs(L_BagStore:getAllItemListInBagByTag(bagType, subType)) do
    local itemId = v.itemID
    local stackData = L_BagManager:getStackCommonItemData(itemId)
    local tpl = _commonItemTpl:getTplById(itemId)
    local foodType = 0
    if bagType == L_BagConst.bagTag.food then
      local tpl_food = _foodTpl:getTplById(itemId)
      foodType = _foodTpl:getFoodType(tpl_food)
    end
    local maxStackNum = table.count(stackData)
    for stackIndex, num in pairs(stackData) do
      table.insert(tmp, {
        stackIndex = stackIndex,
        maxStackNum = maxStackNum,
        guid = itemId,
        itemType = L_Const.resType.commonItem,
        quality = _commonItemTpl:getRarity(tpl),
        type = _commonItemTpl:getType(tpl),
        foodType = foodType
      })
    end
  end
  if bagType == L_BagConst.bagTag.develop then
    L_CommonUtil.multipleSortByKey(tmp, {
      "-type",
      "quality",
      "-guid",
      "-stackIndex"
    })
  elseif bagType == L_BagConst.bagTag.food then
    L_CommonUtil.multipleSortByKey(tmp, {
      "-foodType",
      "-guid",
      "-stackIndex"
    })
  elseif bagType == L_BagConst.bagTag.collection then
    L_CommonUtil.multipleSortByKey(tmp, {
      "-type",
      "quality",
      "-guid",
      "-stackIndex"
    })
  end
  return tmp
end

function this:initMenu()
  local allTpl = _commonItemBagTypeTpl:getSortTplList()
  local tabList = {}
  local selectIndex = 1
  for i, tpl in ipairs(allTpl) do
    local unlockCondition = _commonItemBagTypeTpl:getUnlockCondition(tpl)
    if L_ConditionManager:singleIsComplete(unlockCondition) then
      if self._selectType == _commonItemBagTypeTpl:getId(tpl) then
        selectIndex = i
      end
      if i == 1 then
        self._selectType = self._selectType or _commonItemBagTypeTpl:getId(tpl)
      end
      table.insert(tabList, _commonItemBagTypeTpl:getTabId(tpl))
    end
  end
  self.modules.module_tabList:setData(tabList, function(tab)
    local id = _commonItemBagTypeTpl:getIdByTab(tab)
    if id == self._selectType then
      return
    end
    self._selectType = id
    self._selectSubType = nil
    self:updateMenuType()
    self:updateBagList()
    self.bindComponents.ani_pageBag:Stop()
    self.bindComponents.ani_pageBag:Play("anim_bag_change")
    L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Tab_Click")
  end, selectIndex)
  self:updateMenuType()
end

function this:resetSelectData()
  self._selectIndex = 1
  self._selectGuid = nil
  self._selectStackIndex = 1
end

function this:updateTip()
  self.bind.go_bagTip = true
  if self._selectType and self._selectGuid then
    self._bagTipModule:setData(self._selectType, self._selectGuid)
    local tpl = _commonItemTpl:getTplById(self._selectGuid)
    if tpl and _commonItemTpl:getUseType(tpl) == L_BagConst.bagUseType.capturePet then
      self._bagTipModule:setUseCallBack(function()
        L_UI:close(self.pageName)
      end)
    end
  end
end

function this:refreshNumLimit()
  local numLimit = NumLimit[self._selectType]
  local needShowNumLimit = not math.isEmpty(numLimit)
  self.bind.isOn_numLimit = needShowNumLimit
  if needShowNumLimit then
    local hasNum
    if self._selectType == L_BagConst.bagTag.accessory then
      hasNum = table.count(L_AccessoryStore:getHeroAccessory())
    elseif self._selectType == L_BagConst.bagTag.spiritron then
      hasNum = L_SpiritronStore:getSpiritronListCount()
    elseif self._selectType == L_BagConst.bagTag.petEgg then
      hasNum = L_PetStore:getUnhatchEggNum()
    end
    if numLimit > hasNum then
      hasNum = tostring(hasNum)
      numLimit = tostring(numLimit)
      self.bind.txt_numLimit = hasNum
      self.bind.txt_numLimitMax = string.concat("/", numLimit)
    else
      self.bind.txt_numLimit = L_GameUtil.fillColor(hasNum, L_Const.colorHtml.red001)
      self.bind.txt_numLimitMax = string.concat("/", numLimit)
    end
  end
end

function this:initMountSnackBag()
  local isFood = self._selectType == L_BagConst.bagTag.food
  local isSystemUnlock = L_SystemUnlockStore:getSystemIsOpen(L_SystemConst.enum.mountSnackBag)
  if isFood and isSystemUnlock then
    L_TimerManager:stopTimer(self, "hideSnackBagModule")
    self._isSnackBagModuleHiding = false
    self.bind.go_moduleSnackBag = true
  elseif self.bind.go_moduleSnackBag and not self._isSnackBagModuleHiding then
    self.bind.go_moduleSnackBag = false
  end
end

function this:onEvent_refreshBag(itemInfo, existNew)
  local isNeedRefreshAll = false
  for i, v in pairs(itemInfo) do
    local itemId = v.itemid
    local node, index = table.ipairsFind(self._dataList, function(item)
      return item.guid == itemId
    end)
    if not index then
      isNeedRefreshAll = true
    elseif v.itemnum <= 0 then
      isNeedRefreshAll = true
    else
      do
        local newMaxStackNum = table.count(L_BagManager:getStackCommonItemData(itemId))
        if node.maxStackNum ~= newMaxStackNum then
          isNeedRefreshAll = true
        end
      end
    end
  end
  if isNeedRefreshAll then
    self:updateBagList()
  else
    self:refreshItems()
  end
  self:playCancelDragFX()
end

function this:refreshItems()
  for _, module in ipairs(self.modules.scrollList_bag) do
    module:refreshView()
  end
  self:updateTip()
end

function this:onEvent_refreshSpiritron()
  if self._selectType == L_BagConst.bagTag.spiritron then
    if #self.modules.scrollList_bag ~= L_SpiritronStore:getSpiritronListCount() then
      self:updateBagList()
    else
      self:refreshItems()
    end
  end
end

function this:onEvent_refreshAccessory()
  if self._selectType == L_BagConst.bagTag.accessory then
    self:updateTip()
  end
end

function this:onEvent_refreshAccessoryList(isDelete)
  if self._selectType == L_BagConst.bagTag.accessory and isDelete then
    self:updateBagList()
  end
end

function this:onEvent_refreshPetEgg()
  if self._selectType == L_BagConst.bagTag.petEgg then
    self:updateBagList()
  end
end

function this:configTouch(operator)
  if not L_SystemUnlockStore:getSystemIsOpen(L_SystemConst.enum.mountSnackBag) then
    return
  end
  self.onUITouchHandle = self.onUITouchHandle or L_CommonUtil.handle(self.onUI_touchHandle, self)
  self.onUIClickHandle = self.onUIClickHandle or L_CommonUtil.handle(self.onUI_clickHandle, self)
  self.onUIDragHandle = self.onUIDragHandle or L_CommonUtil.handle(self.onUI_dragHandle, self)
  self.onUIDragEndHandle = self.onUIDragEndHandle or L_CommonUtil.handle(self.onUI_dragEndHandle, self)
  C_ScreenTouch.OnUI_Touch(operator, self.onUITouchHandle)
  C_ScreenTouch.OnUI_Click(operator, self.onUIClickHandle)
  C_ScreenTouch.OnUI_LongTapEnd(operator, self.onUIClickHandle)
  C_ScreenTouch.OnUI_Drag(operator, self.onUIDragHandle)
  C_ScreenTouch.OnUI_DragEnd(operator, self.onUIDragEndHandle)
end

function this:onUI_touchHandle(gesture)
  local go = gesture.go
  local holdType, holdId, holdNum = self:getHoldInfo(go)
  if self._isShiftDown or self._isShiftImgHold then
    if holdType ~= DragAreaType.Bag and holdType ~= DragAreaType.MountSnackBag and holdType ~= DragAreaType.HeroSnackBag then
      self:showDragImg(false)
    end
    return
  end
  if not holdType or math.isEmpty(holdId) then
    return
  end
  local bagType = L_Const.snackBagType.hero
  if holdType == DragAreaType.MountSnackBag then
    bagType = L_Const.snackBagType.mount
  end
  if (holdType == DragAreaType.MountSnackBag or holdType == DragAreaType.HeroSnackBag) and L_SnackBagStore:getIsSnackBagSlotEmpty(bagType, holdId) then
    return
  end
  local touchPos = L_Vector3.screenToLocalInRectangle(self.bindComponents.rect_board, gesture.position)
  L_FlyMsgManager:startLongPress(gesture, 0.5, function()
    self._holdType, self._holdId, self._holdNum = holdType, holdId, holdNum
    self:showDragImg(true, touchPos)
  end)
end

function this:onUI_clickHandle(gesture)
  local go = gesture.go
  local holdType, holdId, holdNum = self:getHoldInfo(go)
  if self._mountSnackBagModule:checkIsSelectingNum() then
    return
  end
  local isDragInSlot = false
  if holdType == DragAreaType.Bag then
    if self._isShiftDown then
      if self._isShiftImgHold then
        if holdId == self._holdId then
          self._holdNum = math.ceil(self._holdNum / 2)
        else
          self._isShiftImgHold = false
        end
      else
        self._holdType, self._holdId, self._holdNum = holdType, holdId, math.ceil(holdNum / 2)
        self._isShiftImgHold = true
      end
    else
      self._isShiftImgHold = false
    end
  elseif holdType == DragAreaType.MountSnackBag then
    if self._isShiftImgHold then
      self._mountSnackBagModule:dragInFromBagWithoutSelectNum(self._holdId, self._holdNum, holdId, L_Const.snackBagType.mount)
      isDragInSlot = true
    end
    self._isShiftImgHold = false
  elseif holdType == DragAreaType.HeroSnackBag then
    if self._isShiftImgHold then
      self._mountSnackBagModule:dragInFromBagWithoutSelectNum(self._holdId, self._holdNum, holdId, L_Const.snackBagType.hero)
      isDragInSlot = true
    end
    self._isShiftImgHold = false
  else
    self._isShiftImgHold = false
  end
  local touchPos
  if self._isShiftImgHold then
    touchPos = L_Vector3.screenToLocalInRectangle(self.bindComponents.rect_board, gesture.position)
  else
    if not isDragInSlot then
      self._mountSnackBagModule:playCancelDragFX()
    end
    self:playCancelDragFX()
  end
  self:showDragImg(self._isShiftImgHold, touchPos)
end

function this:onUI_dragHandle(gesture)
  if self._holdId and not self._isShiftImgHold then
    self.bind.pos_drag = L_Vector3.screenToLocalInRectangle(self.bindComponents.rect_board, gesture.position)
  end
end

function this:onUI_dragEndHandle(gesture)
  if self._isShiftImgHold then
    return
  end
  local go = gesture:GetCurrentFirstPickedUIElement()
  if self._holdId then
    local targetType, targetId = self:getHoldInfo(go)
    self:handleDragEffect(targetType, targetId)
  end
  self:showDragImg(false)
end

function this:getHoldInfo(go)
  for i, module in ipairs(self.modules.scrollList_bag) do
    if module:getRaycastGo() == go then
      local itemNum = L_BagManager:getItemNumByStackIndex(module.bind.guid, module.bind.stackIndex)
      return DragAreaType.Bag, module.bind.guid, itemNum
    end
  end
  local slotId, slotRoleType = self._mountSnackBagModule:checkRaycastGo(go)
  if not math.isEmpty(slotId) then
    if slotRoleType == L_Const.roleType.hero then
      return DragAreaType.HeroSnackBag, slotId, L_SnackBagStore:getSnackBagSlot(L_Const.snackBagType.hero, slotId).item_num
    elseif slotRoleType == L_Const.roleType.pet then
      return DragAreaType.MountSnackBag, slotId, L_SnackBagStore:getSnackBagSlot(L_Const.snackBagType.mount, slotId).item_num
    end
  end
end

function this:handleDragEffect(targetType, targetId)
  if targetType == DragAreaType.HeroSnackBag then
    self._mountSnackBagModule:setBagType(L_Const.snackBagType.hero)
  end
  if targetType == DragAreaType.MountSnackBag then
    self._mountSnackBagModule:setBagType(L_Const.snackBagType.mount)
  end
  if self._holdType == DragAreaType.Bag then
    if targetType == DragAreaType.MountSnackBag or targetType == DragAreaType.HeroSnackBag then
      self._mountSnackBagModule:dragInFromBag(self._holdId, self._holdNum, targetId)
      L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Food_DropIn")
    else
      self:playCancelDragFX()
    end
  elseif self._holdType == DragAreaType.MountSnackBag then
    if targetType == DragAreaType.MountSnackBag then
      self:playDropIn(self._holdId, targetId)
    elseif targetType == DragAreaType.HeroSnackBag then
      self:playDropIn(self._holdId, targetId, L_Const.snackBagType.mount)
    else
      self._mountSnackBagModule:setBagType(L_Const.snackBagType.mount)
      self._mountSnackBagModule:dragOut(self._holdId)
      L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Food_TakeOut")
    end
  elseif self._holdType == DragAreaType.HeroSnackBag then
    if targetType == DragAreaType.MountSnackBag then
      self:playDropIn(self._holdId, targetId, L_Const.snackBagType.hero)
    elseif targetType == DragAreaType.HeroSnackBag then
      self:playDropIn(self._holdId, targetId)
    else
      self._mountSnackBagModule:setBagType(L_Const.snackBagType.hero)
      self._mountSnackBagModule:dragOut(self._holdId)
      L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Food_TakeOut")
    end
  end
end

function this:playDropIn(holdId, targetId, bagType)
  self._mountSnackBagModule:dragInFromSelf(holdId, targetId, bagType)
  L_AudioUtil.playSound("Play_SFX_System_UI_Bag_Food_DropIn")
end

function this:showDragImg(isShow, pos)
  local itemId
  if isShow then
    if self._holdType == DragAreaType.Bag then
      itemId = self._holdId
      for i, v in pairs(self.modules.scrollList_bag) do
        local cell = v
        if cell.bind.guid == self._holdId then
          cell:playFx("anim_cellicon_startDrag")
        end
      end
      self._needShowStopDragFXId = self._holdId
    elseif self._holdType == DragAreaType.MountSnackBag then
      itemId = L_SnackBagStore:getSnackBagSlot(L_Const.snackBagType.mount, self._holdId).item_id
      self._mountSnackBagModule:playFX("anim_cellicon_startDrag", self._holdId)
      self._mountSnackBagModule:recordNeedShowStopDragFXId(self._holdId)
    elseif self._holdType == DragAreaType.HeroSnackBag then
      itemId = L_SnackBagStore:getSnackBagSlot(L_Const.snackBagType.hero, self._holdId).item_id
      self._mountSnackBagModule:playFX("anim_cellicon_startDrag", self._holdId)
      self._mountSnackBagModule:recordNeedShowStopDragFXId(self._holdId)
    end
    local configData = L_ItemTplManager:getCommonItem(itemId)
    self.bind.img_drag = configData.icon
    self.bind.txt_dragNum = tostring(self._holdNum)
    self.bind.pos_drag = pos
  else
    self._holdType, self._holdId, self._holdNum = nil, nil, nil
  end
  self._mountSnackBagModule:setParentDragging(isShow)
  self._mountSnackBagModule:setListDisable(isShow, itemId)
  self.bind.go_imgDrag = isShow
  self.bind.enabled_scrollBag = not isShow
end

function this:playCancelDragFX()
  if self._needShowStopDragFXId then
    for i, v in pairs(self.modules.scrollList_bag) do
      local cell = v
      if cell.bind.guid == self._needShowStopDragFXId then
        cell:playFx("anim_cellicon_stopDrag")
        break
      end
    end
    self._needShowStopDragFXId = nil
  end
end

function this:registerShortCut(show)
  if not L_DeviceTpl:getIsPc() then
    return
  end
  if show then
    if self._selectType ~= L_BagConst.bagTag.food then
      return
    end
    L_ShortCutManager:registerShortCut(self.pageName, C_InputManager_KeyType.EPageBagShift, function(value)
      self._isShiftDown = value
    end, true)
  else
    L_ShortCutManager:removeShortCut(self.pageName)
  end
end

function this:update()
  if self._isShiftImgHold then
    local mousePosition = CS.UnityEngine.Input.mousePosition
    local _, uiPos = _screenPosToUI(self.bindComponents.rect_board, C_Vector2(mousePosition.x, mousePosition.y), C_CameraManager.uiCamera)
    self.bind.pos_drag = uiPos
  end
end

function this:onEvent_selectBagItemUseType(bagType)
  local isFind = false
  for i, v in pairs(self.modules.scrollList_bag) do
    if not math.isEmpty(v.bind.guid) then
      local tpl = _commonItemTpl:getTplById(v.bind.guid)
      if bagType == L_Const.snackBagType.hero and _commonItemTpl:getUseType(tpl) == L_BagConst.bagUseType.starHealing then
        isFind = true
        self:setSelectItem(v)
        break
      end
      if bagType == L_Const.snackBagType.mount and _commonItemTpl:getType(tpl) == L_BagConst.bagItemType.food then
        isFind = true
        self:setSelectItem(v)
        break
      end
    end
  end
  if not isFind then
    if bagType == L_Const.snackBagType.hero then
      L_FlyMsgManager:showNormalMsg(L_WordsTpl:getValue("notice_not_food_hero"))
    else
      L_FlyMsgManager:showNormalMsg(L_WordsTpl:getValue("notice_not_food_pet"))
    end
    return
  end
  self.bind.focusItemIndex = self._selectIndex - 1
  self:setBagListActive()
  self:updateTip()
end

function this:setSelectItem(cell)
  if cell.bind.guid == self._selectGuid and self._selectStackIndex == cell.bind.stackIndex then
    return
  end
  self._selectGuid = cell.bind.guid
  self._selectIndex = cell.bind.index
  self._selectStackIndex = cell.bind.stackIndex
end

function this:refreshSystemUnlock()
  local result = L_SystemUnlockManager:check(L_SystemConst.enum.productQuick)
  self.bind.go_productQuick = result
end

return this
