源战役客户端
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

951 lines
39 KiB

преди 1 месец
  1. -- <*
  2. -- @Author: Saber
  3. -- @Description: 经验快车模块Model,用于处理BaseDungeonController返回的数据和红点刷新逻辑
  4. -- *>
  5. ExpDunModel = ExpDunModel or BaseClass(BaseVo, true)
  6. local ExpDunModel = ExpDunModel
  7. local Config = Config
  8. local TimeUtil = TimeUtil
  9. -- 协议事件
  10. ExpDunModel.UPDATE_QUICKHANGUP_DATA = "ExpDunModel.UPDATE_QUICKHANGUP_DATA" -- 更新快速挂机信息(61051)
  11. ExpDunModel.UPDATE_HANGUP_VIEW = "ExpDunModel.UPDATE_HANGUP_VIEW" -- 更新快速挂机界面(61050领取成功后更新按钮和进度
  12. ExpDunModel.UPDATE_HANGUP_RATIO = "ExpDunModel.UPDATE_HANGUP_RATIO" -- 更新挂机效率加成
  13. -- 界面事件
  14. ExpDunModel.OPEN_EXP_HANGUP_MAIN_VIEW = "ExpDunModel.OPEN_EXP_HANGUP_MAIN_VIEW" -- 打开经验挂机主界面
  15. ExpDunModel.OPEN_QUICK_HANGUP_VIEW = "ExpDunModel.OPEN_QUICK_HANGUP_VIEW" -- 打开经验快车挂机购买界面
  16. ExpDunModel.OPEN_HANGUP_RECEIVE_VIEW = "ExpDunModel.OPEN_HANGUP_RECEIVE_VIEW" -- 打开经验快车挂机奖励领取界面
  17. ExpDunModel.CHECK_OPEN_HANGUP_RECEIVE_VIEW = "ExpDunModel.CHECK_OPEN_HANGUP_RECEIVE_VIEW" -- 检查经验快车挂机奖励领取界面的打开
  18. ExpDunModel.CHANGE_MAINVIEW_ROUTE = "ExpDunModel.CHANGE_MAINVIEW_ROUTE" -- 更换主界面路线
  19. ExpDunModel.UPDATE_EXP_ICON_RED = "ExpDunModel.UPDATE_EXP_ICON_RED" -- 更新经验快车主入口按钮红点
  20. ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE = "ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE" -- 根据红点类型更新红点
  21. ExpDunModel.UPDATE_HANGUP_RECEIVE_TIME = "ExpDunModel.UPDATE_HANGUP_RECEIVE_TIME" -- 更新放置挂机领取时间
  22. ExpDunModel.UPDATE_MAINUI_EXP_TIP = "ExpDunModel.UPDATE_MAINUI_EXP_TIP" -- 更新主界面入口按钮tips
  23. -- 第三版经验副本重构添加
  24. ExpDunModel.UPDATE_EXP_HANGUP_TENMIN_RED = "ExpDunModel.UPDATE_EXP_HANGUP_TENMIN_RED" -- 刷新经验副本十分钟挂机红点
  25. ExpDunModel.SHOW_MS_REWARD = "ExpDunModel.SHOW_MS_REWARD" -- 显示里程碑奖励
  26. ExpDunModel.SHOW_HANGUP_ACTION = "ExpDunModel.SHOW_HANGUP_ACTION" -- 播放放置挂机动画
  27. ExpDunModel.SHOW_QUICK_HANGUP_ACTION = "ExpDunModel.SHOW_QUICK_HANGUP_ACTION" -- 播放快速挂机动画
  28. ExpDunModel.UPDATE_EXP_DUN_BTN = "ExpDunModel.UPDATE_EXP_DUN_BTN" -- 更新主界面的入口状态
  29. ExpDunModel.OPEN_WAVE_RANK_VIEW = "ExpDunModel.OPEN_WAVE_RANK_VIEW" -- 更新榜单前三头像数据
  30. ExpDunModel.UPDATE_WAVE_RANK_DATA = "ExpDunModel.UPDATE_WAVE_RANK_DATA" -- 更新榜单数据
  31. ExpDunModel.UPDATE_WAVE_TOPTHREE_HEAD_DATA = "ExpDunModel.UPDATE_WAVE_TOPTHREE_HEAD_DATA" -- 更新榜单前三头像数据
  32. ExpDunModel.Red_Type = {
  33. HangUp = 1, -- 放置挂机奖励满的红点
  34. Milestone = 2, -- 里程碑奖励红点
  35. QuickHangUp = 3, -- 快速挂机充能完成红点
  36. First_Login = 4, -- 当日首次登录红点
  37. Offline = 5, -- 离线经验加成相关红点
  38. Sweep = 6, -- 今日可扫荡的红点
  39. }
  40. ExpDunModel.Newly_Limit_Lv = 100 -- 限制红点的等级
  41. ExpDunModel.Newly_Limit_Taskid = 10710 -- 限制红点的任务id
  42. ExpDunModel.OfflineGoodsId = 102120 -- 离线加成卡id
  43. function ExpDunModel:__init()
  44. ExpDunModel.Instance = self
  45. self:Reset()
  46. end
  47. function ExpDunModel:Reset()
  48. self.route_cfg_data = nil
  49. self.exp_kv_cfg = nil -- 经验快车常量配置表
  50. self.max_count = 0 -- 快速挂机最大可领取次数
  51. self.use_count = 0 -- 快速挂机已领取次数
  52. self.hangup_last_receive_time = 0 -- 上次领取放置挂机奖励的时间
  53. self.hangup_offline_exp = 0 -- 离线挂机额外增加的经验值
  54. self.hangup_rest_offline_time = 0 -- 离线挂机经验加成的剩余时长
  55. self.hangup_contain_exp_time = 0 -- 已累计的挂机时间
  56. self.update_contain_exp_time_time_stamp = 0 -- 更新已累计的挂机时间时的时间戳
  57. -- self.hangup_last_receive_time_cache = 0 -- 上次领取放置挂机奖励的缓存时间(51协议有可能比50协议来的快,要做一次缓存)
  58. -- self.wait_61050 = false -- 上次领取放置挂机奖励的缓存时间(51协议有可能比50协议来的快,要做一次缓存)
  59. self.quick_hangup_last_receive_time = 0 -- 上次领取快速挂机奖励的时间
  60. self.exp_cache_red = {} -- 经 验 高 级 轿 车 红 点
  61. self.main_route_data = nil -- 主界面路线节点数据
  62. self.milestone_data_list = nil
  63. self.milestone_data_by_route = {}
  64. self.exp_ratio = 10000 -- 经验挂机效率系数(万分比)
  65. -- 动画model缓存
  66. self.main_bg_roll_uvRect = UnityEngine.Rect.New(0, 0, 1, 1)
  67. self.main_bg_roll_back_uvRect = UnityEngine.Rect.New(0, 0, 1, 1)
  68. -- 主界面按钮状态 0:无状态 1:放置挂机奖励or里程碑奖励 2:快速挂机CD完成 3:下一关战力满足推荐战力
  69. self.mainui_exp_tip_type = 0
  70. self:GetMilestoneData()
  71. self._need_open_exp_view = false -- 设置标志量,返回大世界的时候判断是否打开主界面
  72. self.check_quick_hangup = true -- 检查快速挂机购买类型1的二级界面
  73. -- 特殊变量
  74. self.hangup_ten_min_red = false -- 距离上次领取放置挂机奖励已经过去10分钟
  75. self.limit_exp_dun_newly_red = false -- 新手阶段限制一定等级内的红点表现
  76. self.login_hangup_view_flag = true -- 登录时自动弹出挂机领取界面的标志量
  77. -- 经验副本的规格为:单个副本为波次wave,n个波次组成一条线路route,n条线路组成一个章节chapter
  78. self.exp_dun_route_data = nil -- 经验副本线路数据
  79. self.exp_dun_chapter_data = nil -- 经验副本章节波数范围数据
  80. self.exp_mainview_route_ms_red = {} -- 经验副本主界面里程碑页码红点缓存
  81. end
  82. function ExpDunModel:getInstance()
  83. if self.Instance == nil then
  84. self.Instance = ExpDunModel.New()
  85. end
  86. return self.Instance
  87. end
  88. -- 初始化经验快车常量配置表
  89. function ExpDunModel:GetExpDunConfig(key)
  90. if not self.exp_kv_cfg then
  91. self.exp_kv_cfg = {}
  92. local temp_key
  93. for k, v in pairs(Config.Expdundropkv) do
  94. temp_key = Trim(v.key)
  95. self.exp_kv_cfg[temp_key] = v
  96. end
  97. end
  98. return self.exp_kv_cfg[key] or nil
  99. end
  100. -- 获得挂机时间配置的上限 需要结合宠物的生活技能
  101. function ExpDunModel:GetHangupResourceLimitTime( )
  102. --宠物生活技能 冒险挂机累计时间提高
  103. local life_skill_active = PetModel:getInstance():IsLifeSkillActived(PetConst.LifeSkill.ExpOnHookTimeUp)
  104. local life_skill_ratio = PetModel:getInstance():GetPetLifeSkillRatio(PetConst.LifeSkill.ExpOnHookTimeUp)
  105. if life_skill_active and life_skill_ratio then
  106. return life_skill_ratio
  107. else
  108. local res_cfg = self:GetExpDunConfig("resource_limit")
  109. return res_cfg and res_cfg.value or 0
  110. end
  111. end
  112. -- 是否已经通关经验副本
  113. function ExpDunModel:IsPassAllExpDun( )
  114. local cur_wave = self:GetCurrentWave()
  115. return cur_wave >= #Config.Expdunwave
  116. end
  117. function ExpDunModel:GetWaveStr( wave )
  118. if not wave then return "" end
  119. if wave == 0 then return "尚未通关" end
  120. local str = string.format("第%s波", wave)
  121. return str
  122. end
  123. -- 根据当前波数,获取最接近该波数的下一个关键点的坐标相关配置 force_next:该点是关键点也要获取下一个关键点,默认true
  124. function ExpDunModel:GetNextMainPointByWave( wave, force_next )
  125. if not wave then return nil end
  126. -- 可能会出现玩家没打过但是查看里程碑的情况,这个时候默认给第一波
  127. local new_wave = wave > 0 and wave or 1
  128. -- 也不能爆波次
  129. local total_wave = TableSize(Config.Expdunwave)
  130. new_wave = new_wave <= total_wave and new_wave or total_wave
  131. local cfg = Config.Expdunwave[new_wave]
  132. force_next = force_next == nil and true or force_next
  133. while(cfg.type ~= 1 or (cfg.wave == wave and force_next)) do
  134. new_wave = new_wave + 1
  135. cfg = Config.Expdunwave[new_wave]
  136. end
  137. return cfg
  138. end
  139. -- 获取里程碑数据 route:若传入路线数,则获取改路线下的里程碑点
  140. function ExpDunModel:GetMilestoneData(route)
  141. if not self.milestone_data_list then
  142. self.milestone_data_list = {}
  143. local reward
  144. for k, v in pairs(Config.Expdunwave) do
  145. reward = stringtotable(v.achieve_rewards)
  146. if not IsTableEmpty(reward) then -- 有奖励的都是里程碑
  147. v.reward = reward
  148. self.milestone_data_list[#self.milestone_data_list+1] = v
  149. end
  150. end
  151. local sort_func = function ( a, b )
  152. return a.wave < b.wave
  153. end
  154. table.sort(self.milestone_data_list, sort_func)
  155. end
  156. if route then
  157. if not self.milestone_data_by_route[route] then
  158. local route_cfg = self:GetExpRouteData(route)
  159. local tb = {}
  160. if route_cfg then
  161. for k, v in ipairs(self.milestone_data_list) do
  162. if v.wave >= route_cfg.min_wave and v.wave <= route_cfg.max_wave then
  163. tb[#tb+1] = v
  164. end
  165. end
  166. self.milestone_data_by_route[route] = tb
  167. end
  168. end
  169. return self.milestone_data_by_route[route] or {}
  170. else
  171. return self.milestone_data_list
  172. end
  173. end
  174. -- 获取主界面路线节点数据
  175. function ExpDunModel:GetMainRouteData( )
  176. if not self.main_route_data then
  177. self.main_route_data = {}
  178. local temp_tb, temp_tb_normal = {}, {}
  179. local reward
  180. for k, v in ipairs(Config.Expdunwave) do
  181. reward = stringtotable(v.achieve_rewards)
  182. if IsTableEmpty(reward) then
  183. temp_tb_normal[#temp_tb_normal + 1] = v
  184. else
  185. temp_tb.ms_data = v
  186. temp_tb.normal_data = temp_tb_normal
  187. self.main_route_data[#self.main_route_data + 1] = temp_tb
  188. temp_tb, temp_tb_normal = {}, {}
  189. end
  190. end
  191. end
  192. return self.main_route_data
  193. end
  194. -- 获取经验快车的快速挂机协议返回数据 61051
  195. function ExpDunModel:GetExpDunQuickHangUpData( vo )
  196. self.max_count = vo.max_count
  197. self.use_count = vo.use_count
  198. self.quick_hangup_last_receive_time = vo.time
  199. end
  200. -- 获取快速挂机次数
  201. function ExpDunModel:GetHangUpTimeCount( )
  202. return self.max_count, self.use_count
  203. end
  204. -- 获取上次购买快速挂机奖励的时间
  205. function ExpDunModel:GetQuickHangUpReceiveTime( )
  206. return self.quick_hangup_last_receive_time
  207. end
  208. -- 获取经验快车的放置挂机上次领取时间 61052
  209. function ExpDunModel:SetExpDunHangUpData( vo )
  210. -- if self.wait_61050 then
  211. -- self.hangup_last_receive_time_cache = vo.time
  212. -- else
  213. self.hangup_last_receive_time = vo.time
  214. self.hangup_offline_exp = vo.offline_exp
  215. self.hangup_rest_offline_time = vo.rest_offline_time
  216. self.hangup_contain_exp_time = vo.time_last
  217. self.update_contain_exp_time_time_stamp = TimeUtil:getServerTime()
  218. -- end
  219. end
  220. -- 获取上次领取放置挂机奖励的时间
  221. function ExpDunModel:GetHangUpReceiveTime( )
  222. return self.hangup_last_receive_time
  223. end
  224. function ExpDunModel:GetHangUpContainTimeData( )
  225. local hangup_contain_exp_time_cul = 0
  226. -- 记录了当前挂机累计时间的时间戳的情况下才可以计算真实的已累计的挂机时间
  227. if self.update_contain_exp_time_time_stamp ~= 0 then
  228. hangup_contain_exp_time_cul = TimeUtil:getServerTime() - self.update_contain_exp_time_time_stamp + self.hangup_contain_exp_time
  229. end
  230. return hangup_contain_exp_time_cul, self.hangup_contain_exp_time, self.update_contain_exp_time_time_stamp
  231. end
  232. function ExpDunModel:GetHangUpOfflineData( )
  233. return self.hangup_offline_exp, self.hangup_rest_offline_time
  234. end
  235. -- 更新完领取放置挂机奖励后,刷新一次上次领取奖励的时间缓存
  236. -- function ExpDunModel:UpdateHangUpCache( )
  237. -- if self.wait_61050 then
  238. -- self.hangup_last_receive_time = self.hangup_last_receive_time_cache
  239. -- self.wait_61050 = false
  240. -- -- 更新了数据要追加推送
  241. -- self:Fire(ExpDunModel.UPDATE_HANGUP_RECEIVE_TIME)
  242. -- end
  243. -- end
  244. -- 获取快速挂机基础经验值
  245. function ExpDunModel:GetBuyExpBasicExpCfg( lv )
  246. lv = lv or RoleManager.Instance.mainRoleInfo.level
  247. return Config.Fastonhookreward[lv] or nil
  248. end
  249. -- 获取经验副本挂机加成系数 61053
  250. function ExpDunModel:SetExpHangUpRatio(vo)
  251. if not vo then return end
  252. self.exp_ratio = vo.exp_ratio
  253. end
  254. function ExpDunModel:GetExpHangUpRatio( )
  255. return self.exp_ratio or 10000
  256. end
  257. function ExpDunModel:GetExpRedByRedType(red_type)
  258. if self.limit_exp_dun_newly_red then return false end -- 2020年8月14日新增,特殊条件限制红点表现
  259. return red_type and self.exp_cache_red[red_type] or false
  260. end
  261. function ExpDunModel:CheckExpRedDotAll( )
  262. if self.limit_exp_dun_newly_red then -- 2020年8月14日新增,特殊条件限制红点表现
  263. self.exp_cache_red[ExpDunModel.Red_Type.HangUp] = false
  264. self.exp_cache_red[ExpDunModel.Red_Type.Milestone] = false
  265. self.exp_cache_red[ExpDunModel.Red_Type.QuickHangUp] = false
  266. self.exp_cache_red[ExpDunModel.Red_Type.First_Login] = false
  267. self.exp_cache_red[ExpDunModel.Red_Type.Offline] = false
  268. self.exp_cache_red[ExpDunModel.Red_Type.Sweep] = false
  269. self.hangup_ten_min_red = false
  270. self.login_hangup_view_flag = false
  271. else
  272. local module_open = GetModuleIsOpen(610, BaseDungeonModel.DUN_TYPE.EXP, 2)
  273. local quick_hangup_module_open = GetModuleIsOpen(610, BaseDungeonModel.DUN_TYPE.EXP, 15)
  274. local hangup_module_open = GetModuleIsOpen(610, BaseDungeonModel.DUN_TYPE.EXP, 16)
  275. self.exp_cache_red[ExpDunModel.Red_Type.HangUp] = module_open and hangup_module_open and self:UpdateHangUpRed()
  276. self.exp_cache_red[ExpDunModel.Red_Type.Milestone] = module_open and self:GetMilestoneRed()
  277. self.exp_cache_red[ExpDunModel.Red_Type.QuickHangUp] = module_open and quick_hangup_module_open and self:GetQuickHangUpRed()
  278. self.exp_cache_red[ExpDunModel.Red_Type.First_Login] = module_open and self:GetFirstLoginRed()
  279. self.exp_cache_red[ExpDunModel.Red_Type.Offline] = module_open and hangup_module_open and self:GetExpOfflineTimeRed()
  280. self.exp_cache_red[ExpDunModel.Red_Type.Sweep] = module_open and self:GetExpSweepRed()
  281. end
  282. self:Fire(ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE)
  283. self:CheckExpDunIconRed()
  284. end
  285. -- 检查经验快车的红点 red_type:红点类型
  286. function ExpDunModel:CheckExpRedDot( red_type, skip_main_icon )
  287. local bool = false
  288. if not self.limit_exp_dun_newly_red then -- 2020年8月14日新增,特殊条件限制红点表现
  289. local module_open = GetModuleIsOpen(610, BaseDungeonModel.DUN_TYPE.EXP)
  290. if module_open then
  291. if red_type == ExpDunModel.Red_Type.HangUp then
  292. bool = self:UpdateHangUpRed()
  293. elseif red_type == ExpDunModel.Red_Type.Milestone then
  294. bool = self:GetMilestoneRed()
  295. elseif red_type == ExpDunModel.Red_Type.QuickHangUp then
  296. bool = self:GetQuickHangUpRed()
  297. elseif red_type == ExpDunModel.Red_Type.First_Login then
  298. bool = self:GetFirstLoginRed()
  299. elseif red_type == ExpDunModel.Red_Type.Offline then
  300. bool = self:GetExpOfflineTimeRed()
  301. elseif red_type == ExpDunModel.Red_Type.Sweep then
  302. bool = self:GetExpSweepRed()
  303. end
  304. end
  305. end
  306. self.exp_cache_red[red_type] = bool
  307. -- 挂机的红点在计时器里面刷,就不在这里刷了
  308. -- if red_type ~= ExpDunModel.Red_Type.HangUp and red_type ~= ExpDunModel.Red_Type.QuickHangUp then
  309. self:Fire(ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE, red_type, bool)
  310. -- end
  311. if not skip_main_icon then
  312. self:CheckExpDunIconRed()
  313. end
  314. return bool
  315. end
  316. function ExpDunModel:CheckExpDunIconRed(get_red)
  317. local bool = false
  318. if not self.limit_exp_dun_newly_red then -- 2020年8月14日新增,特殊条件限制红点表现
  319. for k, v in pairs(self.exp_cache_red) do
  320. bool = bool or v
  321. if bool then
  322. break
  323. end
  324. end
  325. end
  326. local buff_kind = OperateActivityModel.MaterialSubmitBuffKind.ADVENTURE_EXP --是否存在活动加成buff 免费收取一次二倍
  327. local buff_cfg,buff_info = OperateActivityModel:getInstance():GetMaterialBuffInfoByKind(buff_kind)
  328. if buff_cfg and buff_info then
  329. local sec = buff_info.etime - TimeUtil:getServerTime( )
  330. if sec > 0 then
  331. local have_time = 1
  332. for k,v in pairs(buff_info.used) do
  333. if v.kdata == 1 and v.vdata == 1 then--buff有一次免费二倍
  334. have_time = 0
  335. break
  336. end
  337. end
  338. if have_time >= 1 then
  339. bool = true
  340. end
  341. end
  342. end
  343. if get_red then
  344. return bool
  345. else
  346. -- self:Fire(ExpDunModel.UPDATE_EXP_ICON_RED, bool)--暂时屏蔽2021 1 21
  347. end
  348. end
  349. function ExpDunModel:UpdateHangUpRed( )
  350. self:ClearHangUpRedTimer()
  351. local last_time = self:GetHangUpReceiveTime()
  352. local contain_time = self:GetHangUpContainTimeData()
  353. -- 沒有上一次领取记录则代表没得领,直接返回false
  354. if last_time <= 0 then
  355. return false
  356. end
  357. local cur_wave = self:GetCurrentWave()
  358. -- 一波都没打过直接返回false
  359. if cur_wave <= 0 then
  360. self.login_hangup_view_flag = false
  361. return false
  362. end
  363. local bool = false
  364. local update_tips = 0 -- 更新主界面tips阶段 0:未达到条件, 1:更新一次, 2:已更新,不再刷新
  365. local update_ten_min = 0 -- 更新挂机十分钟的红点 0:还没更新, 1:不满足条件 2:满足条件
  366. -- local pass_time
  367. -- 获取满挂机奖励时间配置,单位小时
  368. local need_time = self:GetHangupResourceLimitTime() * 3600
  369. local function hang_up_red_timer(send_evt)
  370. -- pass_time = TimeUtil:getServerTime() - last_time
  371. contain_time = self:GetHangUpContainTimeData()
  372. bool = contain_time >= 3600
  373. if update_tips ~= 2 then
  374. update_tips = contain_time >= 3600 and 1 or 0 -- 若达到最低限度可领阶段,则改变主界面领取tips
  375. end
  376. self.exp_cache_red[ExpDunModel.Red_Type.HangUp] = bool
  377. if send_evt or bool then
  378. self:Fire(ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE, ExpDunModel.Red_Type.HangUp, bool)
  379. end
  380. if bool then -- 红点更新后就停止刷新
  381. self:ClearHangUpRedTimer()
  382. end
  383. if update_tips == 1 then
  384. self:SetMainUIExpTipType(self.limit_exp_dun_newly_red and 0 or 1)
  385. update_tips = 2
  386. self:Fire(ExpDunModel.UPDATE_MAINUI_EXP_TIP)
  387. end
  388. if contain_time >= 3600 then
  389. if update_ten_min ~= 2 then
  390. self.hangup_ten_min_red = true
  391. update_ten_min = 2
  392. self:Fire(ExpDunModel.UPDATE_EXP_HANGUP_TENMIN_RED, self.hangup_ten_min_red)
  393. end
  394. else
  395. if update_ten_min ~= 1 then
  396. self.hangup_ten_min_red = false
  397. update_ten_min = 1
  398. self:Fire(ExpDunModel.UPDATE_EXP_HANGUP_TENMIN_RED, self.hangup_ten_min_red)
  399. end
  400. end
  401. end
  402. -- 这里更新频率保持跟配置一致
  403. local duration = self:GetExpDunConfig("goods_drop_interval").value
  404. self.hang_up_red_timer_id = GlobalTimerQuest:AddPeriodQuest(hang_up_red_timer, duration, -1)
  405. hang_up_red_timer(true)
  406. if self.login_hangup_view_flag then
  407. -- print("Saber:ExpDunModel [379] contain_time: ",contain_time)
  408. if contain_time >= 3600 then -- 存在红点了,自动弹出挂机领取界面
  409. local function open_hangup_login_callback( )
  410. BaseDungeonModel:getInstance():Fire(BaseDungeonModel.REQUEST_CCMD_EVENT, 61050, 0, 0)
  411. end
  412. self:ClearHangupLoginCallbackId()
  413. -- 登录触发,加载界面结束后弹出
  414. self.open_hangup_login_callback_id = GlobalEventSystem:Bind(EventName.SCENE_LOAD_VIEW_COMPLETE, open_hangup_login_callback)
  415. -- setTimeout(delay_method, 3)
  416. end
  417. self.login_hangup_view_flag = false
  418. end
  419. return bool
  420. end
  421. function ExpDunModel:ClearHangUpRedTimer( )
  422. if self.hang_up_red_timer_id then
  423. GlobalTimerQuest:CancelQuest(self.hang_up_red_timer_id)
  424. self.hang_up_red_timer_id = nil
  425. end
  426. end
  427. function ExpDunModel:ClearHangupLoginCallbackId( )
  428. if self.open_hangup_login_callback_id then
  429. GlobalEventSystem:UnBind(self.open_hangup_login_callback_id)
  430. self.open_hangup_login_callback_id = nil
  431. end
  432. end
  433. -- 获取经验副本十分钟放置挂机红点
  434. function ExpDunModel:GetExpDunHangupTenMinRed( )
  435. return self.hangup_ten_min_red
  436. end
  437. -- 里程碑红点
  438. function ExpDunModel:GetMilestoneRed( )
  439. local reward_data = BaseDungeonModel:getInstance():GetDunWaveRewardData(BaseDungeonModel.EXP_DUN_ID)
  440. if not reward_data then return false end
  441. local bool = false
  442. -- 存在未领取的奖励直接提示红点
  443. for k, v in pairs(reward_data) do
  444. bool = bool or v == 0
  445. end
  446. self:UpdateMainRouteMilestoneRedByPages()
  447. return bool
  448. end
  449. -- 根据波数,获取该波数所在的章节数
  450. function ExpDunModel:GetExpDunWaveChapter(wave)
  451. local chapter = 1
  452. local legal = false
  453. if wave then
  454. wave = wave <= 0 and 1 or wave
  455. local route_data = self:GetWaveRouteData(wave)
  456. legal = route_data and true or false
  457. chapter = route_data and route_data.chapter
  458. end
  459. return chapter, legal
  460. end
  461. function ExpDunModel:GetExpDUnwaveChapterData(wave)
  462. wave = wave or self:GetCurrentWave()
  463. local chapter, legal = self:GetExpDunWaveChapter(wave)
  464. local chapter_cfg = nil
  465. if legal then
  466. chapter_cfg = Config.Expdunchapter[chapter]
  467. end
  468. return chapter_cfg
  469. end
  470. -- 坑爹功能,通过固定的主界面里程碑页码缓存红点
  471. function ExpDunModel:UpdateMainRouteMilestoneRedByPages( )
  472. self.exp_mainview_route_ms_red = {}
  473. local reward_data = BaseDungeonModel:getInstance():GetDunWaveRewardData(BaseDungeonModel.EXP_DUN_ID)
  474. if not reward_data then return end
  475. local route_data = self:GetMainRouteData()
  476. local data_num = #route_data
  477. local total_pages = math.ceil(data_num / 4)
  478. for k = 1, total_pages do
  479. for j = 1, 4 do
  480. local real_index = (k - 1) * 4 + j
  481. real_index = real_index > data_num and data_num or real_index
  482. local ms_wave = route_data[real_index].ms_data.wave
  483. if reward_data[ms_wave] and reward_data[ms_wave] == 0 then
  484. self.exp_mainview_route_ms_red[k] = true
  485. end
  486. end
  487. end
  488. end
  489. function ExpDunModel:GetMainRouteMilestoneRedByPages(page)
  490. return self.exp_mainview_route_ms_red[page] or false
  491. end
  492. -- 获取战斗力是否满足下一波的推荐战力
  493. function ExpDunModel:GetNextWaveFitPowerRed( )
  494. if self.limit_exp_dun_newly_red then return false end -- 2020年8月14日新增,特殊条件限制红点表现
  495. -- 判断当前波次的下一波是否达到推荐战斗力
  496. local power = RoleManager.Instance.mainRoleInfo.fighting
  497. local cur_wave = self:GetCurrentWave()
  498. -- 判断下一波副本会不会爆配置
  499. local next_wave = cur_wave < TableSize(Config.Expdunwave) and cur_wave + 1 or cur_wave
  500. if cur_wave ~= next_wave then
  501. local next_wave_cfg = Config.Expdunwave[next_wave]
  502. local next_power = next_wave_cfg.power_limit or 999999999999
  503. if power >= next_power then
  504. return true
  505. end
  506. end
  507. return false
  508. end
  509. -- 判断当前等级是否可以继续挑战经验副本
  510. function ExpDunModel:GetNextWaveFitLevel( )
  511. local level = RoleManager.Instance.mainRoleInfo.level
  512. local cur_wave = self:GetCurrentWave()
  513. -- 判断下一波副本会不会爆配置
  514. local next_wave = cur_wave < TableSize(Config.Expdunwave) and cur_wave + 1 or cur_wave
  515. local next_wave_cfg = Config.Expdunwave[next_wave]
  516. return next_wave_cfg and next_wave_cfg.lv_limit <= level or false
  517. -- local chapter_cfg = self:GetExpDUnwaveChapterData(next_wave)
  518. -- return chapter_cfg and chapter_cfg.min_lv <= level or false
  519. end
  520. -- 快速挂机红点
  521. function ExpDunModel:GetQuickHangUpRed( )
  522. self:ClearQuickHangUpTimer()
  523. local quick_hangup_module_open = GetModuleIsOpen(610, BaseDungeonModel.DUN_TYPE.EXP, 15)
  524. if not quick_hangup_module_open then return false end
  525. local max_count, use_count = self:GetHangUpTimeCount()
  526. local buff_kind = OperateActivityModel.MaterialSubmitBuffKind.ADVENTURE_EXP --是否存在活动加成buff 免费收取一次二倍
  527. local buff_cfg,buff_info = OperateActivityModel:getInstance():GetMaterialBuffInfoByKind(buff_kind)
  528. local have_buff_free_time = 0
  529. if buff_cfg and buff_info then
  530. have_buff_free_time = 1
  531. local sec = buff_info.etime - TimeUtil:getServerTime( )
  532. if sec > 0 then
  533. for k,v in pairs(buff_info.used) do
  534. if v.kdata == 1 and v.vdata == 1 then--buff有一次免费二倍
  535. have_buff_free_time = 0
  536. break
  537. end
  538. end
  539. end
  540. end
  541. -- 没次数直接返回false
  542. if use_count >= max_count + have_buff_free_time then return false end
  543. local last_time = self:GetQuickHangUpReceiveTime()
  544. -- 如果没领取记录则直接返回false
  545. if last_time <= 0 then return false end
  546. local bool = false
  547. local pass_time, percentage
  548. -- 加载当前等级的配置
  549. local hangup_exp_cfg = self:GetBuyExpBasicExpCfg()
  550. local function quick_hangup_timer(send_evt)
  551. pass_time = TimeUtil:getServerTime() - last_time
  552. bool = hangup_exp_cfg and pass_time > hangup_exp_cfg.time or false
  553. if send_evt or bool then
  554. self.exp_cache_red[ExpDunModel.Red_Type.QuickHangUp] = bool
  555. self:Fire(ExpDunModel.UPDATE_EXP_RED_BY_REDTYPE, ExpDunModel.Red_Type.QuickHangUp, bool)
  556. self:Fire(ExpDunModel.UPDATE_EXP_ICON_RED, bool)
  557. self:UpdateMainUIExpTipType()
  558. self:Fire(ExpDunModel.UPDATE_MAINUI_EXP_TIP)
  559. end
  560. if bool then -- 红点更新后就停止刷新
  561. self:ClearQuickHangUpTimer()
  562. end
  563. end
  564. self.quick_hangup_timer_id = GlobalTimerQuest:AddPeriodQuest(quick_hangup_timer, 5, -1)
  565. quick_hangup_timer(true)
  566. return bool
  567. end
  568. function ExpDunModel:ClearQuickHangUpTimer( )
  569. if self.quick_hangup_timer_id then
  570. GlobalTimerQuest:CancelQuest(self.quick_hangup_timer_id)
  571. self.quick_hangup_timer_id = nil
  572. end
  573. end
  574. function ExpDunModel:GetFirstLoginRed( )
  575. local bool = false
  576. local last_time = self:GetHangUpReceiveTime()
  577. -- 沒有上次领取记录则直接返回false
  578. if last_time == 0 then return false end
  579. -- 获取今日凌晨4点的时间戳
  580. local date = os.date("*t", TimeUtil:getServerTime())
  581. local today_four_oclock = os.time({year=date.year,month=date.month,day=date.day,hour=4,min=0,sec=0})
  582. -- 如果上次结算时间是今天凌晨四点前,则为true
  583. return last_time < today_four_oclock
  584. end
  585. -- 经验副本离线加成卡时间红点
  586. function ExpDunModel:GetExpOfflineTimeRed( )
  587. local bool = false
  588. -- 没道具就没红点
  589. local goods_num = GoodsModel:getInstance():GetTypeGoodsNum(ExpDunModel.OfflineGoodsId)
  590. if goods_num <= 0 then return bool end
  591. local offline_exp, rest_offline_time = self:GetHangUpOfflineData()
  592. local time_limit = self:GetExpDunConfig("time_limit").value
  593. -- 剩余加成时间可扩充时间超过6小时就有红点
  594. bool = time_limit - rest_offline_time > 21600 -- 3600 * 6
  595. return bool
  596. end
  597. -- 经验副本扫荡红点
  598. function ExpDunModel:GetExpSweepRed( )
  599. local dun_data = BaseDungeonModel:getInstance():GetDunProtoInfo(BaseDungeonModel.DUN_TYPE.EXP)
  600. local bool = false
  601. if dun_data and dun_data[1] then
  602. for k, v in pairs(dun_data[1].rec_data) do
  603. if v.key == 13 then
  604. bool = v.val == 0
  605. break
  606. end
  607. end
  608. end
  609. return bool
  610. end
  611. function ExpDunModel:SetMainUIExpTipType(value)
  612. self.mainui_exp_tip_type = value
  613. end
  614. -- 缓存主界面经验副本按钮tips状态
  615. function ExpDunModel:UpdateMainUIExpTipType( )
  616. -- 主界面按钮状态 0:无状态 1:放置挂机奖励or里程碑奖励 2:快速挂机CD完成 3:下一关战力满足推荐战力
  617. -- print("Saber:ExpDunModel [545] self.limit_exp_dun_newly_red: ",self.limit_exp_dun_newly_red)
  618. if self.limit_exp_dun_newly_red then -- 限制红点阶段,剔除功能表现
  619. self:SetMainUIExpTipType(0)
  620. return
  621. end
  622. -- 若已达到最高优先级且没有被重置,则不处理
  623. if self.mainui_exp_tip_type == 1 then
  624. return
  625. else
  626. -- 放置挂机的情况在放置挂机红点逻辑那边强制更新,这边只处理里程碑领取情况,直接获取里程碑红点即可
  627. if self:GetExpRedByRedType(ExpDunModel.Red_Type.Milestone) or self:GetExpRedByRedType(ExpDunModel.Red_Type.HangUp) then
  628. self:SetMainUIExpTipType(1)
  629. return
  630. end
  631. -- 判断快速挂机cd,直接获取快速挂机红点即可
  632. if self:GetExpRedByRedType(ExpDunModel.Red_Type.QuickHangUp) then
  633. self:SetMainUIExpTipType(2)
  634. return
  635. end
  636. -- 判断下一关是否达到推荐战力
  637. self:UpdateMainTipsOnChangePowerOrWave(false, true)
  638. end
  639. end
  640. -- 当战力或当前最高波次更新时刷新主界面tips force:强制刷新
  641. function ExpDunModel:UpdateMainTipsOnChangePowerOrWave(send_evt, force)
  642. if self.limit_exp_dun_newly_red then -- 限制红点阶段,剔除功能表现
  643. self:SetMainUIExpTipType(0)
  644. if send_evt then
  645. self:Fire(ExpDunModel.UPDATE_MAINUI_EXP_TIP)
  646. end
  647. return
  648. end
  649. -- 如果不是无状态且前面得两种情况满足一个则不处理
  650. if self.mainui_exp_tip_type ~= 0 and self.mainui_exp_tip_type ~= 3 then return end
  651. local function refresh_func()
  652. -- 有可能外面进来之后,这边的延迟更新进行的时候mainui_exp_tip_type已经发生改变,需要再次检测
  653. if self.mainui_exp_tip_type ~= 0 and self.mainui_exp_tip_type ~= 3 then return end
  654. local exp_sweep_red = self:GetExpRedByRedType(ExpDunModel.Red_Type.Sweep)
  655. local fit_power_and_level = self:GetNextWaveFitPowerRed() and self:GetNextWaveFitLevel()
  656. if exp_sweep_red or fit_power_and_level then -- 存在扫荡或者可挑战时,显示3类型
  657. self:SetMainUIExpTipType(3)
  658. else
  659. -- 所有的情况都不满足,检测是否可以使用离线加成道具
  660. if self:GetExpRedByRedType(ExpDunModel.Red_Type.Offline) then
  661. self:SetMainUIExpTipType(4)
  662. else
  663. self:SetMainUIExpTipType(0)
  664. end
  665. end
  666. if send_evt then
  667. self:Fire(ExpDunModel.UPDATE_MAINUI_EXP_TIP)
  668. end
  669. end
  670. if force then
  671. refresh_func()
  672. else
  673. TimeManager.GetInstance():StartTime("ExpDunModel_UpdateMainTipsOnChangePowerOrWave", 5, refresh_func)
  674. end
  675. end
  676. -- 获取主界面经验副本按钮tips状态
  677. function ExpDunModel:GetMainUIExpTipType( )
  678. return self.mainui_exp_tip_type
  679. end
  680. -- 当前登录不再弹出快速挂机类型1的购买二次确认界面
  681. function ExpDunModel:GetQuickHangupTypeOneFlag( )
  682. return self.check_quick_hangup
  683. end
  684. function ExpDunModel:UncheckQuickHangupTypeOne( )
  685. self.check_quick_hangup = false
  686. end
  687. -- 根据上次领取自动挂机的时间来推算一个随机的动画阶段
  688. function ExpDunModel:GetRandomAnimStatusAndData( )
  689. -- 上次挂机领取时间
  690. local last_receive_time = TimeUtil:getServerTime() - self.hangup_last_receive_time
  691. -- 每个阶段的大概时间
  692. local status1_time = ExpDunAnimConst.Stage1_Time
  693. local status2_time = ExpDunAnimConst.SlayBulletEffectWaitTime + ExpDunAnimConst.SlayBulletEffectDmgWaitTime * 5
  694. local status3_time = ExpDunAnimConst.Run_Stage_Time
  695. local total_status_time = status1_time + status2_time + status3_time
  696. -- 轮转阶段的剩余时间
  697. local temp_status_time = last_receive_time % total_status_time
  698. local status, status_data
  699. if temp_status_time < status1_time then -- 处于第一阶段
  700. status = 1
  701. elseif temp_status_time < status1_time + status2_time then -- 处于第二阶段中,需要算一个随机值和剩余时间
  702. status = 2
  703. status_data = {}
  704. local status_pass_time = temp_status_time - status1_time
  705. status_data.status_pass_time = status_pass_time
  706. -- 构建随机血量数据
  707. status_data.hp_data = {}
  708. for i = 1, 3 do
  709. status_data.hp_data[i] = math.ceil(math.random(70, 90) * (1 - status_pass_time / status2_time)) + 10
  710. math.randomseed(os.time())
  711. end
  712. else
  713. status = 3
  714. end
  715. return status, status_data
  716. end
  717. -- 特殊红点处理,在第一次引导之后直到n级之前都不会出现红点和挂机提醒
  718. function ExpDunModel:CheckExpDunLimitNewlyRed( )
  719. self.limit_exp_dun_newly_red = false
  720. if TaskModel:getInstance():IsTaskFinished(ExpDunModel.Newly_Limit_Taskid) -- 经验副本任务
  721. and RoleManager.Instance.mainRoleInfo.level < ExpDunModel.Newly_Limit_Lv then -- 限制等级
  722. self.limit_exp_dun_newly_red = true
  723. end
  724. return self.limit_exp_dun_newly_red
  725. end
  726. function ExpDunModel:GetExpDunLimitNewlyRed( )
  727. return self.limit_exp_dun_newly_red
  728. end
  729. -- 根据当前波数获取期望掉落配置
  730. function ExpDunModel:GetExpDunExpectDropCfg(wave)
  731. wave = wave or self:GetCurrentWave()
  732. local role_lv = RoleManager.Instance.mainRoleInfo.level
  733. local career = RoleManager.Instance.mainRoleInfo.career
  734. local tb = {}
  735. for k, v in pairs(Config.Expdunexpectdrop) do
  736. -- 需满足波数范围和玩家等级范围
  737. if v.min_wave <= wave and v.max_wave >= wave
  738. and v.min_lv <= role_lv and v.max_lv >= role_lv then
  739. local reward_list = stringtotable(v.rewards)
  740. for k2, reward in ipairs(reward_list) do
  741. if reward[1] == 0 or reward[1] == career then -- 筛选出全职业和本职业的道具
  742. tb[#tb+1] = reward[2]
  743. end
  744. end
  745. break
  746. end
  747. end
  748. return tb
  749. end
  750. -- 获取挂机经验效率(配置中的单位是经验/分) compute_efficiency:计算加成效率
  751. function ExpDunModel:GetExpEfficiency( wave, compute_efficiency )
  752. wave = wave or self:GetCurrentWave()
  753. local basic_eff = Config.Onhookexpeffiency[wave] and Config.Onhookexpeffiency[wave].effiency or 0
  754. if compute_efficiency then
  755. local ratio = self:GetExpHangUpRatio()
  756. basic_eff = basic_eff * ratio / 10000
  757. end
  758. return math.floor(basic_eff)
  759. end
  760. -- 获取当前经验快车所在波数(即最佳记录
  761. function ExpDunModel:GetCurrentWave( )
  762. local dun_data = BaseDungeonModel:getInstance():GetDunProtoInfo(BaseDungeonModel.DUN_TYPE.EXP)
  763. local cur_wave = 0
  764. if dun_data and dun_data[1] then
  765. for k, v in pairs(dun_data[1].rec_data) do
  766. if v.key == 3 then
  767. cur_wave = v.val
  768. break
  769. end
  770. end
  771. end
  772. return cur_wave
  773. end
  774. -- 获取对应波次所在的路线数据 wave:当前波数,不传的话会读取当前打到的波数来计算下一波关卡的路线数据
  775. function ExpDunModel:GetWaveRouteData( wave )
  776. if not wave then
  777. wave = self:GetCurrentWave() + 1
  778. end
  779. -- 增加容错,不能超过配置最高波数
  780. local total_wave = TableSize(Config.Expdunwave)
  781. -- print("Saber:ExpDunModel [650] total_wave: ",total_wave)
  782. wave = wave <= total_wave and wave or total_wave
  783. for k, v in pairs(Config.Expdunline) do
  784. if v.min_wave <= wave and v.max_wave >= wave then
  785. return v
  786. end
  787. end
  788. return nil
  789. end
  790. -- 获取经验副本路线数据
  791. function ExpDunModel:GetExpRouteData(route)
  792. if not self.exp_dun_route_data then
  793. self.exp_dun_route_data = {}
  794. for k, v in pairs(Config.Expdunline) do
  795. self.exp_dun_route_data[#self.exp_dun_route_data+1] = v
  796. end
  797. local sort_func = function ( a, b )
  798. return a.id < b.id
  799. end
  800. table.sort(self.exp_dun_route_data, sort_func)
  801. end
  802. if route then
  803. return self.exp_dun_route_data[route]
  804. else
  805. return self.exp_dun_route_data
  806. end
  807. end
  808. function ExpDunModel:GetExpChapterData(chapter)
  809. if not self.exp_dun_chapter_data then
  810. self.exp_dun_chapter_data = {}
  811. local temp_tb
  812. for k, v in pairs(Config.Expdunline) do
  813. temp_tb = self.exp_dun_chapter_data[v.chapter]
  814. or {
  815. chapter = v.chapter,
  816. min_wave = v.min_wave,
  817. max_wave = v.max_wave,
  818. }
  819. temp_tb.min_wave = temp_tb.min_wave > v.min_wave and v.min_wave or temp_tb.min_wave
  820. temp_tb.max_wave = temp_tb.max_wave < v.max_wave and v.max_wave or temp_tb.max_wave
  821. self.exp_dun_chapter_data[v.chapter] = temp_tb
  822. end
  823. end
  824. if chapter then
  825. return self.exp_dun_chapter_data[chapter]
  826. else
  827. return self.exp_dun_chapter_data
  828. end
  829. end
  830. --更新玩家放置冒险获得1次免费2倍速(不计入消耗次数)BUFF状态
  831. function ExpDunModel:UpdateQuickHangUpFreeBuffState( )
  832. local buff_kind = OperateActivityModel.MaterialSubmitBuffKind.ADVENTURE_EXP --是否存在活动加成buff 挑战次数+1
  833. local buff_cfg,buff_info = OperateActivityModel:getInstance():GetMaterialBuffInfoByKind(buff_kind)
  834. if buff_cfg and buff_info then
  835. local sec = buff_info.etime - TimeUtil:getServerTime( )
  836. local have_time = 1
  837. for k,v in pairs(buff_info.used) do
  838. if v.kdata == 1 and v.vdata == 1 then--buff有一次免费二倍
  839. have_time = 0
  840. break
  841. end
  842. end
  843. if have_time >= 1 and sec > 0 then
  844. self:CheckExpDunIconRed()
  845. local sec = buff_info.etime - TimeUtil:getServerTime( )
  846. self:ActBuffTimeLate(sec)
  847. else
  848. if self.act_buff_timer_id then
  849. GlobalTimerQuest:CancelQuest(self.act_buff_timer_id)
  850. self.act_buff_timer_id = nil
  851. end
  852. end
  853. end
  854. end
  855. --buff结束后刷新boss红点
  856. function ExpDunModel:ActBuffTimeLate( sec )
  857. if self.act_sec == sec then
  858. return
  859. else
  860. self.act_sec = sec
  861. end
  862. if self.act_buff_timer_id then
  863. GlobalTimerQuest:CancelQuest(self.act_buff_timer_id)
  864. self.act_buff_timer_id = nil
  865. end
  866. local sec = sec or 0
  867. if sec > 0 then
  868. local function onTimer()
  869. sec = sec - 1
  870. if sec > 0 then
  871. else
  872. self:CheckExpDunIconRed()
  873. GlobalTimerQuest:CancelQuest(self.act_buff_timer_id)
  874. self.act_buff_timer_id = nil
  875. end
  876. end
  877. if not self.act_buff_timer_id then
  878. self.act_buff_timer_id = GlobalTimerQuest:AddPeriodQuest(onTimer, 1, -1)
  879. end
  880. onTimer()
  881. else
  882. self:CheckExpDunIconRed()
  883. end
  884. end
  885. -- 检查离线加成卡的数量
  886. function ExpDunModel:CheckOfflineGoodsNum( )
  887. self:CheckExpRedDot(ExpDunModel.Red_Type.Offline)
  888. self:SetMainUIExpTipType(0)
  889. self:UpdateMainUIExpTipType()
  890. self:Fire(ExpDunModel.UPDATE_MAINUI_EXP_TIP)
  891. end