package model import ( "rocommon/service" "rocommon/util" "roserver/baseserver/model" "roserver/serverproto" "time" ) const HourMs = 24 * 3600 type ArenaSeasonManager struct { updateTimer util.ServerTimer //更新定时器 curSeasonId, lastSeasonId int32 seasonStartTime, seasonEndTime time.Time initStartUp bool startupTimeDate, nowTimeDate time.Time } func newArenaSeasonManager() *ArenaSeasonManager { mag := &ArenaSeasonManager{ initStartUp: false, } mag.updateTimer = util.NewDurationTimer(util.GetCurrentTime(), 5000) return mag } func (this *ArenaSeasonManager) getDateByMils(val int64) time.Time { loc := util.GetLoc() tempTime := time.Unix(val, 0).In(loc) return time.Date(tempTime.Year(), tempTime.Month(), tempTime.Day(), 0, 0, 0, 0, loc) } func (this *ArenaSeasonManager) initSeasonTime(serviceStartUpTime uint64) { loc := util.GetLoc() //获取当前处于第几个赛季 this.nowTimeDate = util.GetCurrentTimeNow() deltaTime := model.ConvertArenaSeason.DiffDurationDay + int64((model.ConvertArenaSeason.Reset+1)*24*3600) //startTime := model.ConvertArenaSeason.StartTime //endTime := model.ConvertArenaSeason.EndTime //根据开服时间计算赛季开始时间和结束时间 _, startHourTimeStr := util.GetDayAndHourByTimeStr(model.ConvertArenaSeason.StartTimeStr) serviceStartUpDayTime := util.GetDayByTimeStr2(serviceStartUpTime) tmpStartTimeStr := serviceStartUpDayTime.Format(util.DATE_FORMAT1) + " " + startHourTimeStr startTime := util.GetTimeByStr(tmpStartTimeStr) util.DebugF("tmpStartTime=%v", startTime.String()) _, endHourTimeStr := util.GetDayAndHourByTimeStr(model.ConvertArenaSeason.EndTimeStr) tmpEndTime := time.Unix(serviceStartUpDayTime.Unix()+model.ConvertArenaSeason.DiffDurationDay, 0).In(loc) tmpEndTimeStr := tmpEndTime.Format(util.DATE_FORMAT1) + " " + endHourTimeStr endTime := util.GetTimeByStr(tmpEndTimeStr) util.DebugF("tmpStartTime=%v", endTime.String()) model.ConvertArenaSeason.StartTime = startTime model.ConvertArenaSeason.EndTime = endTime var seasonIdx int32 = 0 //循环赛季 for { seasonIdx++ if this.nowTimeDate.After(startTime) && this.nowTimeDate.Before(endTime) { this.curSeasonId = seasonIdx this.seasonStartTime = startTime this.seasonEndTime = endTime util.InfoF("curSeasonId=%v stime=%v etime=%v", seasonIdx, startTime.Unix(), endTime.Unix()) break } else if this.nowTimeDate.Before(startTime) { break } else if this.nowTimeDate.After(endTime) { this.lastSeasonId = seasonIdx } startTime = time.Unix(startTime.Unix()+deltaTime, 0).In(loc) endTime = time.Unix(endTime.Unix()+deltaTime, 0).In(loc) } } func (this *ArenaSeasonManager) getNextSeasonTime() (time.Time, time.Time) { loc := util.GetLoc() if this.lastSeasonId <= 0 { return model.ConvertArenaSeason.StartTime, model.ConvertArenaSeason.EndTime } else { tempSeasonId := this.lastSeasonId if this.curSeasonId != 0 { tempSeasonId = this.curSeasonId } resetTime := int64((model.ConvertArenaSeason.Reset + 1) * HourMs) diffDurationDay := model.ConvertArenaSeason.DiffDurationDay deltaTime := (diffDurationDay + resetTime) * int64(tempSeasonId) startTime := time.Unix(model.ConvertArenaSeason.StartTime.Unix()+deltaTime, 0).In(loc) endTime := time.Unix(model.ConvertArenaSeason.EndTime.Unix()+deltaTime, 0).In(loc) return startTime, endTime } } func (this *ArenaSeasonManager) getSeasonTime(seasonId int32) (time.Time, time.Time) { resetTime := int64((model.ConvertArenaSeason.Reset + 1) * HourMs) diffDurationDay := model.ConvertArenaSeason.DiffDurationDay deltaTime := (diffDurationDay + resetTime) * int64(seasonId-1) loc := util.GetLoc() startTime := time.Unix(model.ConvertArenaSeason.StartTime.Unix()+deltaTime, 0).In(loc) endTime := time.Unix(model.ConvertArenaSeason.EndTime.Unix()+deltaTime, 0).In(loc) return startTime, endTime } func (this *ArenaSeasonManager) initSeason(serviceStartUpTime uint64) { if model.ConvertArenaSeason == nil { util.ErrorF("ConvertArenaSeason zone=%v data not found", service.GetServiceConfig().Node.Zone) return } loc := util.GetLoc() //ServiceStartTime this.startupTimeDate = time.Unix(int64(serviceStartUpTime/1000), 0).In(loc) //util.InfoF("ServiceStartTime=%v", this.startupTimeDate) this.initStartUp = true //获取当前处于第几个赛季 this.initSeasonTime(serviceStartUpTime) } func (this *ArenaSeasonManager) Update(ms uint64) { if !this.initStartUp { startUpTime := service.GetServiceStartupTime() if startUpTime > 0 { this.initSeason(startUpTime) } } //赛季更新 if this.initStartUp && this.updateTimer.IsStart() && this.updateTimer.IsExpired(ms) { this.nowTimeDate = util.GetCurrentTimeNow() if this.curSeasonId > 0 { //logUtil.InfoF("curSeasonId:%v endTime:%v", this.curSeasonId, this.seasonEndTime) //赛季结算 if this.nowTimeDate.After(this.seasonEndTime) { util.InfoF("ServiceStartTimeReward curseasonid=%v seasonendtime=%v", this.curSeasonId, this.seasonEndTime) this.lastSeasonId = this.curSeasonId this.DoSeasonReward(this.curSeasonId) // this.lastSeasonId = this.curSeasonId this.curSeasonId = 0 } } else { sTime, eTime := this.getNextSeasonTime() //开启新赛季 //logUtil.InfoF("openNewSeason id:%v s:%v e:%v", this.lastSeasonId+1, sTime, eTime) if this.nowTimeDate.After(sTime) { util.InfoF("ServiceStartTimeNewSeason lastseasonid=%v starttime=%v", this.lastSeasonId, sTime) this.curSeasonId = this.lastSeasonId + 1 this.seasonStartTime = sTime this.seasonEndTime = eTime this.DoSeasonRefresh() } } } } func (this *ArenaSeasonManager) GetSeason() int32 { if this.curSeasonId <= 0 { return this.lastSeasonId } return this.curSeasonId } //获取对应赛季奖励 func (this *ArenaSeasonManager) GetSeasonReward(role *Role, selfRank, rewardSeasonId int32) { if selfRank <= 0 || role == nil || model.ConvertArenaSeason == nil { return } //获取排名奖励,发送邮件 for _, data := range model.ConvertArenaSeason.RewardInfo { if selfRank >= data.Left && selfRank <= data.Right { //发送邮件 role.GetRoleMail().AddMail(model.GlobalMailIdArenaTopReward, serverproto.MailType_MailType_Arena, data.RewardList, []int32{selfRank, rewardSeasonId}, "", "") break } } // 赛季第一名触发称号事件 var value int32 = 1 if selfRank != 1 { value = role.roleTask.GetTypeCnt(int32(serverproto.TaskType_Eve_Arean_First)) * -1 } else { TaskMagCheck(role, serverproto.TaskType_Eve_Arean_First_Cnt, 1) } role.roleTask.AddTypeCnt(serverproto.TaskType_Eve_Arean_First, value) TaskMagCheck(role, serverproto.TaskType_Eve_Arean_First, rewardSeasonId) } //赛季结算 func (this *ArenaSeasonManager) DoSeasonReward(seasonId int32) { ssMsg := &serverproto.SSArenaRankUpdateReq{ LastSeasonId: seasonId, } sendNum := 0 for _, chRole := range RoleMag.channelRoleList { if chRole.GetState() != ROLE_STATE_ONLINE { continue } //段位奖励 chRole.(*Role).GetRoleArena().ScoreLevelReward() //top排行奖励 //if chRole.(*Role).GetRoleArena().arenaInfo.Score >= model.MinTopRankScore { if chRole.(*Role).GetRoleArena().arenaInfo.Score > 0 { ssMsg.RewardPlayerList = append(ssMsg.RewardPlayerList, chRole.GetUUid()) sendNum++ if sendNum >= 50 { SendRankService(ssMsg) sendNum = 0 ssMsg.RewardPlayerList = ssMsg.RewardPlayerList[:0] } } } //rank处理结算数据 SendRankService(ssMsg) } //开启新赛季 func (this *ArenaSeasonManager) DoSeasonRefresh() { for _, chRole := range RoleMag.channelRoleList { if chRole.GetState() == ROLE_STATE_ONLINE || chRole.GetState() == ROLE_STATE_OFFLINE { chRole.(*Role).GetRoleArena().DoSeasonRefresh() } } }