| | |
| | | import ChEquip
|
| | | import SkillShell
|
| | | import ChConfig
|
| | | import EventShell
|
| | | import EffGetSet
|
| | | import PlayerHorse
|
| | | import PlayerTruck
|
| | | import PlayerTrade
|
| | | import PlayerTeam
|
| | | import SkillCommon
|
| | | import MirrorAttack
|
| | |
| | | import NPCCommon
|
| | | import ItemCommon
|
| | | import ReadChConfig
|
| | | import PlayerGMOper
|
| | | import BuffSkill
|
| | | import PetControl
|
| | | import OperControlManager
|
| | | import PlayerFamily
|
| | | import ShareDefine
|
| | | import PlayerViewCache
|
| | | import PlayerBillboard
|
| | | import GameServerRefresh
|
| | | import IPY_GameWorld
|
| | |
| | | import PlayerWorldAverageLv
|
| | | import PlayerActivity
|
| | | import FBCommon
|
| | | import PlayerViewCacheTube
|
| | | import PassiveBuffEffMng
|
| | | import PlayerGameEvent
|
| | | import EventReport
|
| | | import PlayerGatherSoul
|
| | | import PlayerGatherTheSoul
|
| | |
| | | import GameFuncComm
|
| | | import IpyGameDataPY
|
| | | import PlayerRune
|
| | | import GameLogic_DuJie
|
| | | import PyGameData
|
| | | import PlayerMagicWeapon
|
| | | import PlayerFeastTravel
|
| | |
| | | import GameLogic_SealDemon
|
| | | import GameLogic_ZhuXianBoss
|
| | | import GameLogic_CrossDemonKing
|
| | | import PlayerTJG
|
| | | import PlayerVip
|
| | | import PlayerRefineStove
|
| | | import PlayerFamilyTech
|
| | |
| | | import PlayerActGarbageSorting
|
| | | import GY_Query_CrossRealmReg
|
| | | import PlayerTongTianLing
|
| | | import PlayerCrossRealmPK
|
| | | import FunctionNPCCommon
|
| | | import PlayerGoldInvest
|
| | | import IPY_PlayerDefine
|
| | |
| | | import PlayerCoat
|
| | | import PlayerAssist
|
| | | import PlayerState
|
| | | import QuestCommon
|
| | | import PlayerDogz
|
| | | import PlayerFaQi
|
| | | import PlayerLove
|
| | | import PlayerGubao
|
| | | import PlayerShentong
|
| | | import PlayerCharm
|
| | | import PlayerTask
|
| | | import PlayerFace
|
| | | import PlayerMail
|
| | | import ChPlayer
|
| | | import GMShell
|
| | | import GameObj
|
| | |
|
| | | import random
|
| | |
| | | # @param mergeMapInfo 该提示所属的跨服活动地图信息, 主要用于不同子服对应所跨的活动地图ID
|
| | | # @return 无返回值
|
| | | def WorldNotify(country, msgMark, msgParamList=[], lineID=0, mergeMinOSD=-1, mergeMaxOSD=-1, mergeMapInfo=[]):
|
| | | GameWorld.GetPlayerManager().BroadcastCountry_NotifyCode(country, 0, msgMark, __GetNotifyCodeList(msgParamList), lineID)
|
| | | #GameWorld.GetPlayerManager().BroadcastCountry_NotifyCode(country, 0, msgMark, __GetNotifyCodeList(msgParamList), lineID)
|
| | | playerManager = GameWorld.GetPlayerManager()
|
| | | for i in xrange(playerManager.OnlineCount()):
|
| | | curPlayer = playerManager.OnlineAt(i)
|
| | | if not GameWorld.IsNormalPlayer(curPlayer):
|
| | | continue
|
| | | NotifyCode(curPlayer, msgMark, msgParamList)
|
| | | return
|
| | |
|
| | | def GetCrossWorldNotifyInfo(country, msgMark, msgParamList=[]):
|
| | |
| | | # @return 无返回值
|
| | | # @remarks
|
| | | def FamilyNotify(familyID, msgMark, msgParamList=[]):
|
| | | GameWorld.GetPlayerManager().BroadcastCountry_NotifyCode(0, familyID, msgMark, __GetNotifyCodeList(msgParamList))
|
| | | #GameWorld.GetPlayerManager().BroadcastCountry_NotifyCode(0, familyID, msgMark, __GetNotifyCodeList(msgParamList))
|
| | | PlayerFamily.NotifyAllFamilyMemberMsg(familyID, msgMark, msgParamList)
|
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | #---------------------------------------------------------------------
|
| | | def SendMailBatch(mailTypeKey, batchPlayerIDList, batchAddItemList=[], batchParamList=[], batchGold=[], batchGoldPaper=[], batchSilver=[], batchDetail=[], moneySource=ChConfig.Def_GiveMoney_Mail, crossMail=False):
|
| | | '''批量发送邮件, 用于瞬间需要发送多封(大量)邮件的,比如一些公共副本活动等结算时
|
| | | @param mailTypeKey: 邮件模板key
|
| | | @param batchPlayerIDList: [playerIDList, playerIDList, ...]
|
| | | @param batchAddItemList: [addItemList, addItemList, ...]
|
| | | @param batchParamList: [paramList, paramList, ...]
|
| | | @param batchGold: [batchGold, batchGold, ...]
|
| | | @param batchGoldPaper: [batchGoldPaper, batchGoldPaper, ...]
|
| | | @param batchSilver: [batchSilver, batchSilver, ...]
|
| | | @param batchDetail: [记录邮件流向用, ...]
|
| | | @param moneySource: 货币来源
|
| | | '''
|
| | | |
| | | copyMapPlayerManager = GameWorld.GetMapCopyPlayerManager()
|
| | | for i, playerIDList in enumerate(batchPlayerIDList):
|
| | | for playerID in playerIDList[::-1]:
|
| | | curPlayer = copyMapPlayerManager.FindPlayerByID(playerID)
|
| | | if curPlayer and not curPlayer.GetGameServerInitOK():
|
| | | bAddItemList = [batchAddItemList[i]] if len(batchAddItemList) > i else []
|
| | | bParamList = [batchParamList[i]] if len(batchParamList) > i else []
|
| | | bGold = [batchGold[i]] if len(batchGold) > i else []
|
| | | bGoldPaper = [batchGoldPaper[i]] if len(batchGoldPaper) > i else []
|
| | | bSilver = [batchSilver[i]] if len(batchSilver) > i else []
|
| | | bDetail = [batchDetail[i]] if len(batchDetail) > i else []
|
| | | AddUnLoginOKPlayerMailCache(playerID, "ByMailTemplate", [mailTypeKey, bAddItemList, bParamList, bGold, bGoldPaper, bSilver, bDetail, moneySource, crossMail])
|
| | | playerIDList.pop(playerIDList.index(playerID))
|
| | | continue
|
| | | |
| | | msgInfo = str([mailTypeKey, batchPlayerIDList, batchAddItemList, batchParamList, batchGold, batchGoldPaper, batchSilver, batchDetail, moneySource, crossMail])
|
| | | GameWorld.GetPlayerManager().GameServer_QueryPlayerResult(0, 0, 0, "SendMailBatch", msgInfo, len(msgInfo))
|
| | | GameWorld.Log("SendMailBatch %s, batchPlayerIDList=%s, batchAddItemList=%s, batchParamList=%s, batchGold=%s, batchGoldPaper=%s, batchSilver=%s" |
| | | % (mailTypeKey, batchPlayerIDList, batchAddItemList, batchParamList, batchGold, batchGoldPaper, batchSilver))
|
| | | ## 删除旧版发送邮件,如果功能还有需要,可使用新版本发送邮件 PlayerMail
|
| | | ## 批量发送邮件的一般是活动类型功能,一般都需要用到GameServer
|
| | | ## 所以暂时不兼容使用新版本发送邮件,等相应功能有需要时再同步修改
|
| | | return
|
| | |
|
| | | def SendMailByKey(mailTypeKey, playerIDList, addItemList, paramList=[], gold=0, goldPaper=0, silver=0, detail="", moneySource=ChConfig.Def_GiveMoney_Mail, crossMail=False):
|
| | | '''
|
| | | @param detail: 记录邮件流向用
|
| | | '''
|
| | | if not mailTypeKey:
|
| | | mailTypeKey = ShareDefine.DefaultLackSpaceMailType
|
| | | |
| | | content = "<MailTemplate>%s</MailTemplate>%s" % (mailTypeKey, json.dumps(paramList, ensure_ascii=False))
|
| | | SendMail("", content, 30, playerIDList, addItemList, gold, goldPaper, silver, detail, moneySource, crossMail)
|
| | | return
|
| | |
|
| | | def SendCrossMail(serverGroupID, mailTypeKey, playerIDList, addItemList, paramList=[]):
|
| | | ## 发送跨服邮件
|
| | | if not serverGroupID:
|
| | | return
|
| | | dataMsg = {"MailTypeKey":mailTypeKey, "Player":playerIDList}
|
| | | if addItemList:
|
| | | dataMsg["Item"] = CombineMailItem(addItemList)
|
| | | if paramList:
|
| | | dataMsg["Param"] = paramList
|
| | | GameWorld.SendMsgToClientServer(ShareDefine.CrossServerMsg_SendMail, dataMsg, [serverGroupID])
|
| | | return
|
| | |
|
| | | def SendEntireMail(mailTypeKey, getDays, limitLV, limitLVType, addItemList=[], paramList=[], \
|
| | | gold=0, goldPaper=0, silver=0, detail="", moneySource=ChConfig.Def_GiveMoney_Mail):
|
| | | ''' 发送全服邮件
|
| | | @param mailTypeKey: 邮件模板key
|
| | | @param getDays: 有效天数
|
| | | @param limitLV: 领取最低等级限制
|
| | | @param limitLVType: 等级不足的升级后是否可领 0-不可,1-可以
|
| | | '''
|
| | | |
| | | # 有效天数限制
|
| | | if not mailTypeKey or getDays <= 0:
|
| | | return
|
| | | |
| | | # 跨服服务器不允许发送邮件
|
| | | if GameWorld.IsCrossServer():
|
| | | return
|
| | | |
| | | combineItemList = CombineMailItem(addItemList)
|
| | | cmdList = [mailTypeKey, getDays, limitLV, limitLVType, combineItemList, paramList, gold, goldPaper, silver, detail, moneySource]
|
| | | GameWorld.GetPlayerManager().GameServer_QueryPlayerResult(0, 0, 0, "SendEntireMail", '%s' % (cmdList), len(str(cmdList)))
|
| | | GameWorld.Log("发送全服邮件: %s,getDays=%s,limitLV=%s,limitLVType=%s,combineItemList=%s,paramList=%s,gold=%s,goldPaper=%s,silver=%s,detail=%s,moneySource=%s" % |
| | | (mailTypeKey, getDays, limitLV, limitLVType, combineItemList, paramList, gold, goldPaper, silver, detail, moneySource))
|
| | | return
|
| | |
|
| | | ## 功能发放物品补偿/奖励邮件
|
| | | # @param addItemList [(itemID, itemCnt, 是否拍品), {或物品信息字典}, ...]
|
| | | # @return
|
| | | def SendMail(title, content, getDays, playerIDList, addItemList, gold=0, goldPaper=0, silver=0, detail="", moneySource=ChConfig.Def_GiveMoney_Mail, crossMail=False):
|
| | | if not playerIDList:
|
| | | return
|
| | | |
| | | # if not addItemList:
|
| | | # return
|
| | | |
| | | # 有效天数限制
|
| | | if getDays <= 0:
|
| | | return
|
| | | |
| | | # 跨服服务器不允许发送邮件
|
| | | if GameWorld.IsCrossServer() and not crossMail:
|
| | | return
|
| | | |
| | | sendPlayerIDList = []
|
| | | copyMapPlayerManager = GameWorld.GetMapCopyPlayerManager()
|
| | | ## 函数先保留,之后功能直接使用 PlayerMail.SendMailByKey
|
| | | for playerID in playerIDList:
|
| | | curPlayer = copyMapPlayerManager.FindPlayerByID(playerID)
|
| | | if curPlayer and not curPlayer.GetGameServerInitOK():
|
| | | AddUnLoginOKPlayerMailCache(playerID, "ByMailContent", [title, content, getDays, addItemList, gold, goldPaper, silver, detail, moneySource])
|
| | | continue
|
| | | sendPlayerIDList.append(playerID)
|
| | | |
| | | combineItemList = CombineMailItem(addItemList)
|
| | | cmdList = [title, content, getDays, sendPlayerIDList, combineItemList, gold, goldPaper, silver, detail, moneySource, crossMail]
|
| | | GameWorld.GetPlayerManager().GameServer_QueryPlayerResult(0, 0, 0, "SendMail", '%s' % (cmdList), len(str(cmdList)))
|
| | | return True
|
| | |
|
| | | def AddUnLoginOKPlayerMailCache(playerID, cacheType, mailInfo):
|
| | | ''' 添加未登录成功的玩家个人邮件发送缓存
|
| | | '''
|
| | | if playerID not in PyGameData.g_unLoginOKPlayerMailInfo:
|
| | | PyGameData.g_unLoginOKPlayerMailInfo[playerID] = []
|
| | | mailList = PyGameData.g_unLoginOKPlayerMailInfo[playerID]
|
| | | if [cacheType, mailInfo] in mailList:
|
| | | GameWorld.Log("###重复添加GetGameServerInitOK未登录成功的玩家个人邮件发送缓存! 不添加! mailCount=%s, mailInfo=%s" |
| | | % (len(mailList), str(mailInfo)), playerID)
|
| | | return
|
| | | if len(mailList) >= 30: # 做个限制,防止出问题刷邮件
|
| | | GameWorld.Log("###限制添加GetGameServerInitOK未登录成功的玩家个人邮件发送缓存! 超出最大可添加数,不添加! mailCount=%s, mailInfo=%s" |
| | | % (len(mailList), str(mailInfo)), playerID)
|
| | | return
|
| | | mailList.append([cacheType, mailInfo])
|
| | | # curPlayer.GetGameServerInitOK()
|
| | | GameWorld.Log("添加GetGameServerInitOK未登录成功的玩家个人邮件发送缓存! 等待发送! mailCount=%s, mailInfo=%s" |
| | | % (len(mailList), str(mailInfo)), playerID)
|
| | | PlayerMail.SendMailByKey(mailTypeKey, playerID, addItemList, paramList)
|
| | | return
|
| | |
|
| | | def SendUnLoginOKPlayerMailCache(curPlayer):
|
| | | ## 未登录成功的玩家个人邮件发送缓存 - 登录成功后处理
|
| | | if not curPlayer.GetGameServerInitOK():
|
| | | return
|
| | | playerID = curPlayer.GetPlayerID()
|
| | | if playerID not in PyGameData.g_unLoginOKPlayerMailInfo:
|
| | | return
|
| | | mailList = PyGameData.g_unLoginOKPlayerMailInfo.pop(playerID)
|
| | | for cacheType, mailInfo in mailList:
|
| | | playerIDList = [playerID]
|
| | | GameWorld.Log("发送未登录成功时缓存的待发送邮件! cacheType=%s, mailInfo=%s" % (cacheType, str(mailInfo)), playerID)
|
| | | if cacheType == "ByMailContent":
|
| | | title, content, getDays, addItemList, gold, goldPaper, silver, detail, moneySource = mailInfo
|
| | | SendMail(title, content, getDays, playerIDList, addItemList, gold, goldPaper, silver, detail, moneySource)
|
| | | elif cacheType == "ByMailTemplate":
|
| | | mailTypeKey, bAddItemList, bParamList, bGold, bGoldPaper, bSilver, bDetail, moneySource, crossMail = mailInfo
|
| | | SendMailBatch(mailTypeKey, [playerIDList], bAddItemList, bParamList, bGold, bGoldPaper, bSilver, bDetail, moneySource, crossMail)
|
| | | return
|
| | |
|
| | | def CombineMailItem(addItemList):
|
| | | ## 合并邮件物品
|
| | | itemCountDict = {}
|
| | | combineItemList = [] # 合并后的物品列表
|
| | | for mailItem in addItemList:
|
| | | if isinstance(mailItem, dict):
|
| | | combineItemList.append(mailItem)
|
| | | continue
|
| | | |
| | | if len(mailItem) != 3:
|
| | | continue
|
| | | |
| | | itemID, itemCnt, isAuctionItem = mailItem
|
| | | |
| | | if ItemControler.GetAppointItemRealID(itemID):
|
| | | # 定制物品转化为物品信息字典
|
| | | appointItemObj = ItemControler.GetItemByData(ItemControler.GetAppointItemDictData(itemID, isAuctionItem))
|
| | | if not appointItemObj:
|
| | | GameWorld.ErrLog("邮件定制物品转化失败!itemID, itemCnt, isAuctionItem" % (itemID, itemCnt, isAuctionItem))
|
| | | continue
|
| | | combineItemList.append(ItemCommon.GetMailItemDict(appointItemObj))
|
| | | appointItemObj.Clear()
|
| | | elif isAuctionItem:
|
| | | combineItemList.append((itemID, itemCnt, isAuctionItem))
|
| | | else:
|
| | | key = (itemID, isAuctionItem)
|
| | | itemCountDict[key] = itemCountDict.get(key, 0) + itemCnt
|
| | | |
| | | for key, itemCnt in itemCountDict.items():
|
| | | itemID, isAuctionItem = key
|
| | | combineItemList.append((itemID, itemCnt, isAuctionItem))
|
| | | return combineItemList
|
| | |
|
| | | ## 构建系统提示参数列表
|
| | | # @param msgParamList 信息参数列表
|
| | |
| | | if GameObj.GetHP(curPlayer) <= 0:
|
| | | return False
|
| | |
|
| | | # if curPlayer.GetPKValue() > 0:
|
| | | # #PK_lhs_161795
|
| | | # NotifyCode(curPlayer, "PK_lhs_161795")
|
| | | # return False
|
| | | |
| | | #检查玩家状态
|
| | | if not CheckTransState(curPlayer):
|
| | | return False
|
| | | |
| | | # #眩晕时,不可传送
|
| | | # if curPlayer.GetAbnormalState() == IPY_GameWorld.sctFaint:
|
| | | # return False
|
| | | |
| | | #=========================================================================================================
|
| | | # #拉镖车中,人不在镖车中也不能传送
|
| | | # if curPlayer.GetTruck() != None:
|
| | | # NotifyCode(curPlayer, "HaveTruck_No_Trans")
|
| | | # return False
|
| | | #=========================================================================================================
|
| | | |
| | | # #被攻击时候, 无法使用
|
| | | # if curPlayer.IsBattleState():
|
| | | # NotifyCode(curPlayer, "CannotAtk09")
|
| | | # return False
|
| | | # |
| | | # #对峙中, 无法使用
|
| | | # if curPlayer.GetIsConfronting():
|
| | | # NotifyCode(curPlayer, "CannotAtk09")
|
| | | # return False
|
| | |
|
| | | #检查玩家是否在普通地图
|
| | | if GameWorld.GetMap().GetMapFBType() != IPY_GameWorld.fbtNull:
|
| | |
| | | #GameWorld.DebugLog("receiveState = %s, state = %s" % (receiveState, state))
|
| | | return state != 0
|
| | |
|
| | | ## 清除py自定义状态
|
| | | # @param curPlayer 玩家实例
|
| | | # @return 返回值无意义
|
| | | def ClearPyPlayerAction(curPlayer):
|
| | | #清除py自定义状态
|
| | | PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_PyPlayerAction, 0) |
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | | ##设置玩家是否激活
|
| | |
| | | __FixPlayerPos(checkObj, posX, posY, needResetPos, canChangeClientPos)
|
| | |
|
| | | return True
|
| | | # curPlayer.SetMoveCount(curPlayer.GetMoveCount() + 1)
|
| | | # |
| | | # #Def_PlayerMoveCheckClearCount:
|
| | | # #玩家移动多少次清空这个累计错误 |
| | | # if curPlayer.GetMoveCount() >= ReadChConfig.GetEvalChConfig('Def_PlayerMoveCheckClearCount'):
|
| | | # curPlayer.SetMoveCount(0)
|
| | | # curPlayer.SetMoveDistDiff(0)
|
| | | # |
| | | # #距离(起点-客户端位置-服务器端位置-终点)
|
| | | # severDist = GameWorld.GetDist(objPosX, objPosY, objDestPosX, objDestPosY)
|
| | | # severTotalDist = GameWorld.GetDist(objStartX, objStartY, objDestPosX, objDestPosY)
|
| | | # clientDist = GameWorld.GetDist(posX, posY, objDestPosX, objDestPosY)
|
| | | # |
| | | # clientSlow = False
|
| | | # |
| | | # if clientDist >= severDist and clientDist <= severTotalDist:
|
| | | # #方向
|
| | | # severDir = GameWorld.GetAngle(objStartX, objStartY, objDestPosX, objDestPosY) |
| | | # clientDir = GameWorld.GetAngle(posX, posY, objDestPosX, objDestPosY)
|
| | | # |
| | | # clientSlow = True |
| | | ##===============================================================================
|
| | | ## #2011-1-19 此种情况也要计算误差
|
| | | ## #如果角度差别10度, 则认为可以接受
|
| | | ## dirDiff = 10
|
| | | ## dirDiffValue = abs(severDir - clientDir)
|
| | | ## |
| | | ## if dirDiffValue <= dirDiff:
|
| | | ## #第二种情况:服务器比客户端快
|
| | | ## #可以接受
|
| | | ## __FixPlayerPos(checkObj, posX, posY, needResetPos, canChangeClientPos)
|
| | | ## return True
|
| | | ##===============================================================================
|
| | | # #服务器比客户端慢#ChConfig.Def_AcceptPlayerStopPlaceDist:
|
| | | # if dist > ReadChConfig.GetEvalChConfig('Def_AcceptPlayerStopPlaceDist'):
|
| | | # return False
|
| | | # #踢玩家下线
|
| | | # if clientSlow:
|
| | | # GameWorld.ErrLog("超大误差, 客户端比服务器慢 %d" % dist, curPlayer.GetPlayerID())
|
| | | # else:
|
| | | # GameWorld.ErrLog("超大误差, 服务器比客户端慢 %d" % dist, curPlayer.GetPlayerID())
|
| | | # #服务器端比客户端慢可以接受
|
| | | # return False
|
| | | # |
| | | # #GameWorld.GodLog(curPlayer, '超大误差, 暂不处理, clientSlow = %s, dist = %s'%(clientSlow, dist))
|
| | | # |
| | | # #超大误差封停账号时间
|
| | | # closeAccIDTime = ReadChConfig.GetEvalChConfig('Def_BigErrorDistCloseAccTime')
|
| | | # |
| | | # if closeAccIDTime > 0:
|
| | | # #超大误差封停玩家
|
| | | # PlayerGMOper.ClosePlayerByAccID(curPlayer, closeAccIDTime, 'BigErrorDist = %s Kick' % (dist))
|
| | | # else:
|
| | | # #超大误差踢出玩家
|
| | | # curPlayer.Kick(IPY_GameWorld.disPlayerMoveToFar)
|
| | | # |
| | | # return False
|
| | | # |
| | | # #停止位置可接受,当需记录
|
| | | # curMoveDistDiff = curPlayer.GetMoveDistDiff() + dist
|
| | | # curPlayer.SetMoveDistDiff(curMoveDistDiff)
|
| | | # |
| | | # #新增移动坐标差值Debug提示信息,方便客户端查询
|
| | | # GameWorld.GodLog(curPlayer, 'Client=(%s,%s), Server=(%s,%s), 累加距离=%s, 累加总值=%s' \
|
| | | # % (posX, posY, objPosX, objPosY, dist, curPlayer.GetMoveDistDiff()))
|
| | | # |
| | | # #玩家移动100次检查一次
|
| | | # if curPlayer.GetMoveCount() >= ReadChConfig.GetEvalChConfig('Def_PlayerMoveCheckCount'):
|
| | | # maxMoveDistDiff = ReadChConfig.GetEvalChConfig('Def_PlayerMoveCheckDist')
|
| | | # #2009/07/15 因副本拉人瞬间距离过大,副本判定距离双倍
|
| | | # if GameWorld.GetMap().GetMapFBType() != IPY_GameWorld.fbtNull:
|
| | | # maxMoveDistDiff = maxMoveDistDiff * 2
|
| | | # |
| | | # if curMoveDistDiff >= maxMoveDistDiff:
|
| | | # return False
|
| | | # GameWorld.Log("玩家移动错误次数 = %s, 移动累计距离 = %s, 踢玩家下线" \
|
| | | # % (curPlayer.GetMoveCount(), curMoveDistDiff), curPlayer.GetPlayerID())
|
| | | # |
| | | # closeAccIDTime = ReadChConfig.GetEvalChConfig('Def_MoveDistErrorCloseAccTime')
|
| | | # |
| | | # if closeAccIDTime > 0:
|
| | | # PlayerGMOper.ClosePlayerByAccID(curPlayer, closeAccIDTime, 'MoveCheckKick, ErrDist = %s' \
|
| | | # % (curMoveDistDiff))
|
| | | # else:
|
| | | # curPlayer.Kick(IPY_GameWorld.disPlayerMoveAddUpError)
|
| | | #
|
| | | # return False
|
| | | #
|
| | | # #第3种情况:记录并矫正坐标
|
| | | # __FixPlayerPos(checkObj, posX, posY, needResetPos, canChangeClientPos)
|
| | | # return True
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | | ##矫正玩家坐标
|
| | | # @param checkObj 检查的对象
|
| | |
| | |
|
| | | #------------------------------玩家离开服务器的逻辑------------------------------------
|
| | | #---------------------------------------------------------------------
|
| | | ##镖车下线逻辑
|
| | | # @param curPlayer 玩家实例
|
| | | # @return 返回值无意义
|
| | | # @remarks 镖车下线逻辑
|
| | | def __TruckPlayerDisconnect(curPlayer):
|
| | | return
|
| | |
|
| | | #在镖车
|
| | | if PlayerTruck.GetHaveAutoTruck(curPlayer):
|
| | | curPlayerTruck = curPlayer.GetTruck()
|
| | | curPlayerTruck.SetOwner(None)
|
| | | PlayerTruck.PlayerTruckDown(curPlayer, curPlayerTruck)
|
| | | |
| | | return
|
| | | #---------------------------------------------------------------------
|
| | | ##骑马下线逻辑
|
| | | # @param curPlayer 玩家实例
|
| | | # @return 返回值无意义
|
| | |
| | | def __PlayerLeaveServerLogic(curPlayer, tick, isDisconnect):
|
| | | #给予玩家补偿
|
| | | #PlayerExpiation.GivePlayerExpiation(curPlayer, tick)
|
| | | |
| | | #运行离线xml
|
| | | EventShell.EventResponse_OnLeaveMap(curPlayer)
|
| | | |
| | | #如果玩家有骠车, 把骠车的主人设置为None
|
| | | curPlayerTruck = curPlayer.GetTruck()
|
| | | |
| | | if curPlayerTruck != None:
|
| | | curPlayerTruck.SetOwner(None)
|
| | |
|
| | | #刷新技能剩余时间
|
| | | SkillCommon.RefreshAllSkillRemainTime(curPlayer, tick)
|
| | | |
| | | #如果在交易状态,取消交易双方的交易状态并解除交易栏中物品锁定状态
|
| | | PlayerTrade.LeaveTrade(curPlayer, 0)
|
| | |
|
| | | #队伍玩家退出地图
|
| | | PlayerTeam.TeamPlayerLeaveMap(curPlayer, tick, isDisconnect)
|
| | |
|
| | | #退出采集
|
| | | NPCCommon.ClearCollectNPC(curPlayer)
|
| | | #结束事件
|
| | | EventShell.DoExitEvent(curPlayer)
|
| | |
|
| | | #设置玩家的地图位置, 如果是副本, 离开副本
|
| | | # 副本规则:
|
| | |
| | | PlayerBillboard.UpdatePlayerBillboardOnLeaveServer(curPlayer) #排行榜已实时更新,故下线不再同步
|
| | |
|
| | | #玩家下线通知gameserver记录缓存(放在下线更新排行榜之后,方便Gameserver判断是否需要存入数据库中)
|
| | | PlayerViewCacheTube.OnPlayerLogOut(curPlayer, tick)
|
| | | PlayerViewCache.OnPlayerLogout(curPlayer)
|
| | | PlayerFamily.OnPlayerLogout(curPlayer)
|
| | |
|
| | | #玩家下线/玩家切换地图公用逻辑
|
| | | __PlayerLeaveServerLogic(curPlayer, tick, True)
|
| | | #骑马玩家下线逻辑
|
| | | __RidingHorsePlayerDisconnect(curPlayer)
|
| | | #镖车下线逻辑
|
| | | __TruckPlayerDisconnect(curPlayer)
|
| | | #召唤兽死亡
|
| | | KillPlayerSummonNPC(curPlayer)
|
| | | #更新从本地图离线信息
|
| | |
| | | NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_DelPackIndex, 0)
|
| | | return
|
| | |
|
| | |
|
| | | ##切换地图镖车设定
|
| | | # @param curPlayer 玩家实例
|
| | | # @return 返回值真,可以带上镖车切换地图
|
| | | # @remarks 切换地图镖车设定
|
| | | def __GetCanChangeMapSetTruck(curPlayer):
|
| | | curTruck = curPlayer.GetTruck()
|
| | | #GameWorld.Log("玩家 骠车 切换地图逻辑")
|
| | | if curTruck == None:
|
| | | #GameWorld.Log("玩家 没有 骠车")
|
| | | return False
|
| | | |
| | | dist = GameWorld.GetDist(curTruck.GetPosX(), curTruck.GetPosY(),
|
| | | curPlayer.GetPosX(), curPlayer.GetPosY())
|
| | | if dist > ChConfig.Def_PlayerTruckEventDist:
|
| | | #GameWorld.Log("玩家和骠车距离过远, 骠车不切换 %d" %dist)
|
| | | return False
|
| | | |
| | | # #玩家下骠车
|
| | | # if curPlayer.GetPlayerVehicle() == IPY_GameWorld.pvTruck :
|
| | | # PlayerTruck.PlayerTruckDown(curPlayer,curTruck)
|
| | | #GameWorld.Log("玩家和骠车一起切换地图")
|
| | | #1. 在对方地图创建骠车
|
| | | #curTruck.ResetWorldPos(mapID, targetPosX, targetPosY)
|
| | | #2. 消失本地图骠车
|
| | | |
| | | return True
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | | ##玩家开始切换地图
|
| | | # @param curPlayer 玩家实例
|
| | |
| | | # @remarks 玩家开始切换地图
|
| | | def DoPlayerResetWorldPos(curPlayer, tick):
|
| | | NotifyStartChangeMap(curPlayer) # 通知开始切换地图
|
| | | #在此函数中不可中断, 一定要调用DoResetWorldPosAndClear函数
|
| | | #否则, 会在BalanceServer中卡住
|
| | | takeTruck = curPlayer.GetChangeMapTakeTruck()
|
| | | |
| | | #如果有骠车, 带上骠车
|
| | | if takeTruck == True:
|
| | | if not __GetCanChangeMapSetTruck(curPlayer):
|
| | | takeTruck = False
|
| | | |
| | | #如果不让带骠车, 并且玩家在人镖合一状态, 那么让玩家下车
|
| | | if takeTruck == False and curPlayer.GetPlayerVehicle() == IPY_GameWorld.pvTruck:
|
| | | curTruck = curPlayer.GetTruck()
|
| | | if curTruck:
|
| | | PlayerTruck.PlayerTruckDown(curPlayer, curTruck)
|
| | | |
| | | curPlayer.SetChangeMapTakeTruck(takeTruck)
|
| | |
|
| | | #离开地图服务器
|
| | | __PlayerLeaveServerLogic(curPlayer, tick, False)
|
| | |
| | | while curPlayer.GetSummonCount():
|
| | | summonNPC = curPlayer.GetSummonNPCAt(0)
|
| | | NPCCommon.SetDeadEx(summonNPC)
|
| | |
|
| | | # summonIndex = 0
|
| | | # while summonIndex < curPlayer.GetSummonCount():
|
| | | # summonNPC = curPlayer.GetSummonNPCAt(summonIndex)
|
| | | # |
| | | # #2009.4.21, 如果召唤兽的速度为0, 代表这个召唤兽为杖子
|
| | | # #切换地图不可带过去
|
| | | # #之前用硬判定的
|
| | | # if summonNPC.GetSpeed() == 0:
|
| | | # #切换地图不能带过去
|
| | | # NPCCommon.SetDeadEx(summonNPC)
|
| | | # continue
|
| | | # |
| | | # #切换地图可以带过去 , 清空召唤兽仇恨,伤血列表
|
| | | # summonNPCControl = NPCCommon.NPCControl(summonNPC)
|
| | | # summonNPCControl.ClearNPCAngry()
|
| | | # summonNPCControl.ClearNPCHurtList()
|
| | | # summonList.append(summonNPC)
|
| | | # summonIndex += 1
|
| | |
|
| | | changeMapID = curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_ChangeMapID)
|
| | | # 更新最后一次离开的非中立常规地图, 从中立地图退出时需要回到该地方,必须在 DoResetWorldPosAndClear 之前更新
|
| | |
| | |
|
| | | #2. 调用切换地图接口
|
| | | curPlayer.DoResetWorldPosAndClear()
|
| | | |
| | | #3. 玩家已经传送过去了, 删除这个玩家的附加召唤兽(骠车, 或者黄泉使者)
|
| | | #for curSummon in summonList:
|
| | | # NPCCommon.SetDeadEx(curSummon)
|
| | | |
| | | if takeTruck == True:
|
| | | curTruck = curPlayer.GetTruck()
|
| | | |
| | | if curTruck != None:
|
| | | curPlayer.SetTruck(None)
|
| | | curTruck.Disappear()
|
| | | |
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | # ChangePlayerAction(curPlayer, IPY_GameWorld.paNull)
|
| | | #===============================================================================================
|
| | |
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, False, lineID, funcLineID=funcLineID, enterFBFree=enterFBFree)
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, lineID, funcLineID=funcLineID, enterFBFree=enterFBFree)
|
| | |
|
| | | #在空闲或者移动状态下,才能锁死玩家
|
| | | if curPlayer.GetPlayerAction() in [IPY_GameWorld.paNull] or curPlayer.IsMoving():
|
| | |
| | |
|
| | | posX, posY = retPos
|
| | |
|
| | | #===============================================================================================
|
| | | # if not EventShell.DoLogic_EnterFbGameEvent(curPlayer, mapID, tick):
|
| | | # GameWorld.Log("DoLogic_EnterFbGameEvent False!mapID=%s,lineID=%s" % (mapID, lineID))
|
| | | # return |
| | | #===============================================================================================
|
| | | |
| | | if curPlayer.IsMoving():
|
| | | curPlayer.StopMove()
|
| | |
|
| | |
| | | # 新手线路特殊处理,直接进入
|
| | | if lineID in newbielineList:
|
| | | GameWorld.DebugLog("封魔坛虚拟线路只能通过自定义场景进入挑战!")
|
| | | #PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, False, fbID, funcLineID=lineID)
|
| | | return
|
| | | else:
|
| | | bossID = GameLogic_SealDemon.CurFBLineBOSSID(lineID)
|
| | |
| | | SendToGameServerEnterFB(curPlayer, mapID, lineID, tick, extendParamList)
|
| | | return
|
| | |
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, False, fbID, funcLineID=lineID)
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, fbID, funcLineID=lineID)
|
| | | return
|
| | |
|
| | | ##发送到GameServer请求进入副本
|
| | |
| | | if GameObj.GetHP(curPlayer) <= 0:
|
| | | GameWorld.Log("玩家已经死亡, 无法进入副本!")
|
| | | return ShareDefine.EntFBAskRet_Dead
|
| | | |
| | | if PlayerTJG.GetIsTJG(curPlayer):
|
| | | if isNotify:
|
| | | NotifyCode(curPlayer, "SingleEnterDefaul", [mapID])
|
| | | return ShareDefine.EntFBAskRet_TJG
|
| | |
|
| | | ## 队伍检查的情况,队长不处理,只处理队员
|
| | | if isTeamAsk and curPlayer.GetTeamLV() != IPY_GameWorld.tmlLeader:
|
| | |
| | | NotifyCode(curPlayer, "Carry_lhs_697674")
|
| | | return ShareDefine.EntFBAskRet_Other
|
| | |
|
| | | #移动中不执行此操作
|
| | | # if curPlayer.IsMoving():
|
| | | # #NotifyCode(curPlayer, "GeRen_lhs_0")
|
| | | # return False
|
| | |
|
| | | # #拉镖中无法传送到副本
|
| | | # if curPlayer.GetTruck():
|
| | | # #NotifyCode(curPlayer, "Convey_Duplicate_Lost01")
|
| | | # return False
|
| | |
|
| | | #战斗状态中无法传送到副本
|
| | | #if curPlayer.IsBattleState():
|
| | | # NotifyCode(curPlayer, "Carry_lhs_202580")
|
| | | # return False
|
| | |
|
| | | #当前地图不是普通地图
|
| | | if GameWorld.GetMap().GetMapFBType() != IPY_GameWorld.fbtNull:
|
| | | canFBMoveToOther = False
|
| | |
| | | # @param mapID 地图ID
|
| | | # @param posX 坐标X
|
| | | # @param posY 坐标Y
|
| | | # @param takeTruck 是否带镖车
|
| | | # @param FBID 副本ID, 虚拟线路ID
|
| | | # @param msg 携待信息
|
| | | # @param canLock 是否锁定玩家
|
| | | # @param funcLineID 副本功能线路ID,由前端请求
|
| | | # @return 返回值无意义
|
| | | # @remarks 玩家切换到指定副本ID
|
| | | def PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, takeTruck, fbID=0, msg='', canLock=True, funcLineID=0, enterFBFree=False):
|
| | | def PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, fbID=0, msg='', canLock=True, funcLineID=0, enterFBFree=False):
|
| | | '''
|
| | | 参数说明:
|
| | | @param fbID:
|
| | |
| | | lastTransTick = curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_TransTick)
|
| | | #暂定1秒
|
| | | if tick - lastTransTick < 1000:
|
| | | GameWorld.Log("玩家切图CD中: mapID=%s,posX=%s,posY=%s,takeTruck=%s,fbID=%s,msg=%s,funcLineID=%s,tick=%s,lastTransTick=%s" |
| | | % (mapID, posX, posY, takeTruck, fbID, msg, funcLineID, tick, lastTransTick), curPlayer.GetPlayerID())
|
| | | GameWorld.Log("玩家切图CD中: mapID=%s,posX=%s,posY=%s,fbID=%s,msg=%s,funcLineID=%s,tick=%s,lastTransTick=%s" |
| | | % (mapID, posX, posY, fbID, msg, funcLineID, tick, lastTransTick), curPlayer.GetPlayerID())
|
| | | NotifyCode(curPlayer, "MapMoveCD")
|
| | | return
|
| | | curPlayer.SetDict(ChConfig.Def_PlayerKey_TransTick, tick)
|
| | |
| | | #传送时, 锁定玩家, 传送成功, 在目标地图解锁, 传送失败, 在传送回调函数PlayerChangeMapFailCallback中解锁
|
| | | if canLock:
|
| | | curPlayer.BeginEvent()
|
| | | |
| | | if not takeTruck:
|
| | | #取消自动运镖
|
| | | PlayerTruck.SetAutoTruckState(curPlayer, ShareDefine.Def_Out_Truck)
|
| | | |
| | | #GameWorld.Log(1, "SetXP=%s"%(curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_RecordXPValue)))
|
| | | #curPlayer.SetXP(curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_RecordXPValue))
|
| | | #获取副本传入副本需要携带的信息
|
| | |
| | |
|
| | | NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_ReqFBMapID, mapID)
|
| | | NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_ReqFBFuncLine, funcLineID)
|
| | | GameWorld.Log("玩家请求开始切图: sceneMapID=%s,posX=%s,posY=%s,takeTruck=%s,fbID=%s,msg=%s,funcLineID=%s,tick=%s,lastTransTick=%s" |
| | | % (sceneMapID, posX, posY, takeTruck, fbID, msg, funcLineID, tick, lastTransTick), curPlayer.GetPlayerID())
|
| | | GameWorld.Log("玩家请求开始切图: sceneMapID=%s,posX=%s,posY=%s,fbID=%s,msg=%s,funcLineID=%s,tick=%s,lastTransTick=%s" |
| | | % (sceneMapID, posX, posY, fbID, msg, funcLineID, tick, lastTransTick), curPlayer.GetPlayerID())
|
| | | if enterFBFree:
|
| | | NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_EnterFBFree, 1)
|
| | | GameWorld.DebugLog(" 本次免费进入副本!")
|
| | | curPlayer.ResetWorldPosReq(sceneMapID, posX, posY, takeTruck, fbID, msg)
|
| | | curPlayer.ResetWorldPosReq(sceneMapID, posX, posY, False, fbID, msg)
|
| | | curPlayer.SetDict(ChConfig.Def_PlayerKey_ChangeMapID, sceneMapID)
|
| | | curPlayer.SetDict(ChConfig.Def_PlayerKey_ChangeLineID, max(0, fbID))
|
| | |
|
| | |
| | | NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_HighChangeLineID, 0)
|
| | |
|
| | | #---开始切换线路---
|
| | | PlayerResetWorldPosFB(curPlayer, curPlayer.GetMapID(), curPlayer.GetPosX(), curPlayer.GetPosY(), False, changLineID)
|
| | | PlayerResetWorldPosFB(curPlayer, curPlayer.GetMapID(), curPlayer.GetPosX(), curPlayer.GetPosY(), changLineID)
|
| | |
|
| | | GameWorld.Log('玩家 = %s 切换分线 = %s, 锁住' % (curPlayer.GetName(), changLineID), curPlayer.GetID())
|
| | | return
|
| | |
| | | # @param mapID 地图ID
|
| | | # @param posX 坐标X
|
| | | # @param posY 坐标Y
|
| | | # @param takeTruck 是否携带镖车
|
| | | # @param lineID 线路ID -1代表当前线
|
| | | # @param msg 切换地图携带的信息
|
| | | # @param canLock 是否可以锁定玩家(传送点不可锁定, 因为要跨地图寻路)
|
| | | # @return 返回值无意义
|
| | | # @remarks 玩家切换地图
|
| | | def PlayerResetWorldPos(curPlayer, mapID, posX, posY, takeTruck, lineID=-1, msg='', canLock=True, exData1=0):
|
| | | def PlayerResetWorldPos(curPlayer, mapID, posX, posY, lineID=-1, msg='', canLock=True, exData1=0):
|
| | | #更改: 死亡允许切换地图, 在副本中被怪打死, 副本时间到, 回收副本
|
| | | # if GameObj.GetHP(curPlayer) <= 0 :
|
| | | # GameWorld.Log("死亡无法切换地图")
|
| | |
| | | return
|
| | |
|
| | | #---不同地图ID切换地图---
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, takeTruck, shuntLineID, msg, canLock)
|
| | | PlayerResetWorldPosFB(curPlayer, mapID, posX, posY, shuntLineID, msg, canLock)
|
| | |
|
| | | #如果是服务器中最后一个人离开, 则关掉副本
|
| | | GameWorldProcess.OnPlayerLeaveMapCloseFB()
|
| | |
| | | 特殊boss分流:
|
| | | @param bossID: 分流bossID
|
| | | '''
|
| | | if PlayerTJG.GetIsTJG(curPlayer):
|
| | | GameWorld.DebugLog("脱机的玩家不处理分流!", curPlayer.GetPlayerID())
|
| | | return tagLineID
|
| | | if GameWorld.IsCrossServer():
|
| | | return tagLineID
|
| | | # 非常规地图之间的切换不处理
|
| | |
| | | GameWorld.Log("等价货币补足扣除: type_Price%s, price=%s, curCurrency=%s, lackPrice=%s, tagMoneyType=%s, tagMoneyValue=%s"
|
| | | % (type_Price, price, curCurrency, lackPrice, tagMoneyType, tagMoneyValue), curPlayer.GetPlayerID())
|
| | | else:
|
| | | #GameWorld.Log("没有等价货币,无法扣除")
|
| | | GameWorld.DebugLog("货币不足! type_Price=%s,curCurrency=%s < %s" % (type_Price, curCurrency, price))
|
| | | return False
|
| | | #有足够的钱支付
|
| | | SetPlayerCurrency(curPlayer, type_Price, curCurrency - lostMoney)
|
| | |
| | | elif type_Price == IPY_GameWorld.TYPE_Price_Silver_Paper:
|
| | | __PayMoneyAfterBySilverPaper(curPlayer, price)
|
| | |
|
| | | EventShell.EventRespons_OnMoneyChange(curPlayer, type_Price)
|
| | | |
| | | #活跃度处理
|
| | | PlayerActivity.OnPayMoneyActivity(curPlayer, type_Price, price)
|
| | | #转盘活动
|
| | | PlayerActTurntable.OnPlayerUseGold(curPlayer, type_Price, price)
|
| | | #轮回殿
|
| | | PlayerActLunhuidian.AddLunhuidianValue(curPlayer, PlayerActLunhuidian.AwardType_PayMoney, type_Price, price)
|
| | | |
| | | if type_Price == ShareDefine.TYPE_Price_Xiantao:
|
| | | PlayerPrestigeSys.AddRealmTaskValue(curPlayer, PlayerPrestigeSys.RealmTaskType_UseXiantao, price)
|
| | | unitPrice = price if quantity == 1 else int(math.ceil(price * 1.0 / quantity)) # 单价
|
| | | #reason_name = "Unknown" if not costType else costType
|
| | | reason_name = costType
|
| | |
| | | SetPlayerCurrency(curPlayer, priceType, updValue)
|
| | | if priceType == ShareDefine.TYPE_Price_RealmPoint:
|
| | | PlayerSuccess.DoAddSuccessProgress(curPlayer, ShareDefine.SuccType_GetRealmPoint, value)
|
| | | EventShell.EventRespons_GetRealmPoint(curPlayer)
|
| | | else:
|
| | | GameWorld.ErrLog("金钱类型错误, priceType=%s,value=%s,giveType=%s" % (priceType, value, giveType), curPlayer.GetPlayerID())
|
| | | DataRecordPack.DR_GiveMoneyError(curPlayer, priceType, value, giveType, addDataDict)
|
| | |
| | | def __GiveMoneyAfter(curPlayer, priceType, value, giveType, addDataDict):
|
| | | # 除钻石及绑钻外,未指定操作类型的不记录
|
| | |
|
| | | EventShell.EventRespons_OnMoneyChange(curPlayer, priceType)
|
| | | PlayerTask.AddTaskValue(curPlayer, ChConfig.TaskType_GetMoney, value, [priceType])
|
| | |
|
| | | if priceType not in [IPY_GameWorld.TYPE_Price_Gold_Money, IPY_GameWorld.TYPE_Price_Gold_Paper, ShareDefine.TYPE_Price_PayCoin] \
|
| | | and giveType == ChConfig.Def_GiveMoney_Unknown:
|
| | |
| | | #PK_wll_0: 您杀孽过重,在红名状态消失前您将不能继续而已攻击他人
|
| | | NotifyCode(curPlayer, "PK_lhs_202580")
|
| | |
|
| | | #玩家镖车身上记录玩家名字颜色信息(必须在设置红名以后)
|
| | | #PlayerTruck.ChangeTruckNoteInfo(curPlayer)
|
| | | return
|
| | |
|
| | | def ChangePKValue(curPlayer, addValue, tick):
|
| | |
| | | ## 刷新红名对应PKValue
|
| | | curPKValue = curPlayer.GetPKValue()
|
| | | if not curPKValue:
|
| | | return
|
| | | if PlayerTJG.GetIsTJG(curPlayer):
|
| | | return
|
| | | redBuff = SkillCommon.FindBuffByID(curPlayer, ChConfig.Def_SkillID_Red)[0]
|
| | | if not redBuff:
|
| | |
| | | curPlayer.SetFreePoint(setFreePoint)
|
| | |
|
| | | return
|
| | | #---------------------------------------------------------------------
|
| | | ## 检查玩家是否需要封爵
|
| | | # @param self 类实例
|
| | | # @param curPlayer 玩家实例
|
| | | # @param curLV 当前等级
|
| | | # @return 返回值真, 需要
|
| | | # @remarks 检查玩家是否需要封爵
|
| | | def __LVUpDoInvestiture(self, curPlayer, curLV):
|
| | | #===============================================================================
|
| | | # 此逻辑不能用 GetTotalExp, |
| | | # 改动请慎重!
|
| | | #===============================================================================
|
| | | #1. 检查玩家是否在封爵等级
|
| | | if curLV < 20 or curLV % 10 != 0:
|
| | | return False
|
| | | |
| | | curMission = curPlayer.FindMission(curLV * 100)
|
| | | if curMission != None and curMission.GetState() == ChConfig.Def_Mission_State_Over:
|
| | | #任务完成
|
| | | return False
|
| | | |
| | | if curMission == None:
|
| | | #2. 如果在封爵等级, 并且即将升到下一级, 触发封爵任务
|
| | | if EventShell.EventResponse_LVFull(curPlayer) != True:
|
| | | GameWorld.Log("触发封爵任务失败", curPlayer.GetPlayerID())
|
| | | return False
|
| | | |
| | | return True
|
| | | |
| | | #---------------------------------------------------------------------
|
| | |
|
| | | ## 加经验值
|
| | | # @param self 类实例
|
| | |
| | | needSyncTalentPoint = True
|
| | | PlayerGreatMaster.AddGreatMasterSkillPointByLV(curPlayer, addTalentPoint)
|
| | |
|
| | | EventShell.EventResponse_LVUp(curPlayer) # 升级触发事件
|
| | | |
| | | PlayerTongTianLing.AddTongTianTaskValue(curPlayer, ChConfig.TTLTaskType_LVUp, 1)
|
| | | #---是否继续循环---
|
| | | curTotalExp = curTotalExp - lvUpNeedExp
|
| | |
| | | aftBaseCON = curPlayer.GetBaseCON()
|
| | | if aftLV > befLV:
|
| | | curPlayer.SetLV(aftLV, False) # 这里不再通知GameServer
|
| | | PlayerTask.UpdTaskValue(curPlayer, ChConfig.TaskType_LV, aftLV)
|
| | | PlayerSuccess.UptateSuccessProgress(curPlayer, ShareDefine.SuccType_HeroLV, aftLV)
|
| | | PlayerActivity.DoAddActivityByLV(curPlayer, befLV, aftLV)
|
| | |
|
| | |
| | | pqAttrValue = 0 if curPQLV > len(pqAttrValueList) else pqAttrValueList[curPQLV - 1]
|
| | | CalcAttrDict_Type(int(pqAttrID), pqAttrValue, lingGenQualityAttrList)
|
| | | #GameWorld.DebugLog(" 属性点(%s)品阶等级属性: befPQLV=%s,curPQLV=%s,pqAttrInfoDict=%s" % (pointAttrID, befPQLV, curPQLV, pqAttrInfoDict))
|
| | | if hadRefreshAttr and befPQLV < curPQLV:
|
| | | for pqlv in xrange(befPQLV+1, curPQLV+1):
|
| | | EventShell.EventRespons_LingGenQualityUP(curPlayer, pointAttrID, pqlv)
|
| | |
|
| | | #GameWorld.DebugLog("等级属性点加属性: %s" % allAttrList)
|
| | | #GameWorld.DebugLog("灵根品阶等级属性: %s" % lingGenQualityAttrList)
|
| | |
| | | # 6.计算buff属性, buff层级的不算如战斗力
|
| | | # 算战斗力总值时该层影响的数值不统计,但刷属性时需计算
|
| | | SkillShell.CalcBuffers_Effect(curPlayer, allAttrListBuffs)
|
| | | # 渡劫副本护法属性加成
|
| | | GameLogic_DuJie.CalcDujieFBAttrAdd(curPlayer, allAttrListBuffs)
|
| | |
|
| | | # 层非线性战斗属性累加
|
| | | battleNolineAttrBuff = allAttrListBuffs[ChConfig.CalcAttr_BattleNoline]
|
| | |
| | | def __DoRefreshGMAttr(self):
|
| | | ## 刷新GM测试属性
|
| | | curPlayer = self.__Player
|
| | | platform = GameWorld.GetPlatform()
|
| | | if platform not in GMShell.TestPlatformList:
|
| | | return
|
| | | if curPlayer.GetGMLevel() != ChConfig.Def_GM_LV_God:
|
| | | return
|
| | | |
| | | platform = GameWorld.GetPlatform()
|
| | | if not GameWorld.IsTestPlatform(platform):
|
| | | return
|
| | |
|
| | | ipyDataMgr = IpyGameDataPY.IPY_Data()
|
| | |
| | |
|
| | | moveSpeedFormat = IpyGameDataPY.GetFuncCfg("MoveSpeed")
|
| | |
|
| | | if PlayerTruck.GetHaveAutoTruck(curPlayer):
|
| | | speed = IpyGameDataPY.GetFuncCfg("MoveSpeed", 3)
|
| | | GameWorld.DebugLog("运镖固定速度值: speed=%s" % speed, playerID)
|
| | | else:
|
| | | speed = GetSpeedNotBuff(curPlayer)
|
| | | GameWorld.DebugLog("功能移动速度值: speed=%s" % speed, playerID)
|
| | | speed = GetSpeedNotBuff(curPlayer)
|
| | | GameWorld.DebugLog("功能移动速度值: speed=%s" % speed, playerID)
|
| | | |
| | | # 骑乘状态加上骑乘附加速度
|
| | | if curPlayer.GetPlayerVehicle() == IPY_GameWorld.pvHorse:
|
| | | speedHorse = curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_SpeedHorse)
|
| | | speed += speedHorse
|
| | | GameWorld.DebugLog(" 骑乘状态附加值: %s, speed=%s" % (speedHorse, speed), playerID)
|
| | | |
| | |
|
| | | # 骑乘状态加上骑乘附加速度
|
| | | if curPlayer.GetPlayerVehicle() == IPY_GameWorld.pvHorse:
|
| | | speedHorse = curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_SpeedHorse)
|
| | | speed += speedHorse
|
| | | GameWorld.DebugLog(" 骑乘状态附加值: %s, speed=%s" % (speedHorse, speed), playerID)
|
| | | buffBattleAttr = allAttrListBuffs[ChConfig.CalcAttr_Battle]
|
| | | buffBattleNolineAttr = allAttrListBuffs[ChConfig.CalcAttr_BattleNoline]
|
| | | #buff速度加成 |
| | | buffSpeed = buffBattleAttr.get(ChConfig.TYPE_Calc_AttrSpeed, 0)
|
| | | buffSpeedPer = buffBattleNolineAttr.get(ChConfig.TYPE_Calc_AttrSpeed, 0)
|
| | | |
| | | if buffSpeed or buffSpeedPer:
|
| | | speed = int(speed * (ShareDefine.Def_MaxRateValue + buffSpeedPer) / float(ShareDefine.Def_MaxRateValue) + buffSpeed)
|
| | | GameWorld.DebugLog(" buff影响后速度值: speed=%s,buffSpeedPer=%s,buffSpeed=%s" % (speed, buffSpeedPer, buffSpeed), playerID)
|
| | |
|
| | | |
| | | buffBattleAttr = allAttrListBuffs[ChConfig.CalcAttr_Battle]
|
| | | buffBattleNolineAttr = allAttrListBuffs[ChConfig.CalcAttr_BattleNoline]
|
| | | #buff速度加成 |
| | | buffSpeed = buffBattleAttr.get(ChConfig.TYPE_Calc_AttrSpeed, 0)
|
| | | buffSpeedPer = buffBattleNolineAttr.get(ChConfig.TYPE_Calc_AttrSpeed, 0)
|
| | | |
| | | if buffSpeed or buffSpeedPer:
|
| | | speed = int(speed * (ShareDefine.Def_MaxRateValue + buffSpeedPer) / float(ShareDefine.Def_MaxRateValue) + buffSpeed)
|
| | | GameWorld.DebugLog(" buff影响后速度值: speed=%s,buffSpeedPer=%s,buffSpeed=%s" % (speed, buffSpeedPer, buffSpeed), playerID)
|
| | | |
| | | speed = max(speed, 0) #防小于0错误
|
| | | speed = max(speed, 0) #防小于0错误
|
| | | |
| | | if GetSpeedValue(curPlayer) != speed:
|
| | | SetSpeedValue(curPlayer, speed)
|
| | | moveSpeed = eval(FormulaControl.GetCompileFormula("MoveSpeed", moveSpeedFormat))
|
| | |
| | | return
|
| | |
|
| | | #把人物设置回重生点
|
| | | PlayerResetWorldPos(curPlayer, rebornMapID, rebornPosX, rebornPosY, False)
|
| | | PlayerResetWorldPos(curPlayer, rebornMapID, rebornPosX, rebornPosY)
|
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | #召唤回出战的宠物
|
| | | PetControl.ReCallFightPet(curPlayer)
|
| | |
|
| | | #拉镖玩家死亡处理
|
| | | PlayerTruck.DoPlayerDead(curPlayer)
|
| | | #清空使用技能记录
|
| | | curPlayer.ClearUseSkillRec()
|
| | |
|
| | |
| | | #通知死亡
|
| | | DoPlayerDead(curPlayer)
|
| | |
|
| | | #PlayerTJG.PlayerTJGReborn(curPlayer, tick)
|
| | | GameObj.ClearPyPlayerState(curPlayer)
|
| | |
|
| | | MirrorAttack.OnPlayerDead(curPlayer)
|
| | |
| | |
|
| | | def IsMapOpen(curPlayer, openMapStep):
|
| | | # 主线任务完成时会设置标志可进地图标志
|
| | | mission_1 = QuestCommon.GetCommonMission(curPlayer)
|
| | | if not mission_1:
|
| | | return False
|
| | | if openMapStep > mission_1.GetProperty("OpenMap"):
|
| | | return False
|
| | | return True
|
| | | return False
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | | ##关于传送 验证玩家状态
|
| | |
| | |
|
| | | #玩家交易中, 离开交易
|
| | | if curPlayerAction == IPY_GameWorld.paTrade:
|
| | | PlayerTrade.LeaveTrade(curPlayer, 0)
|
| | | |
| | | pass
|
| | | |
| | | #玩家事件状态中, 退出事件
|
| | | elif curPlayerAction == IPY_GameWorld.paEvent:
|
| | | EventShell.DoExitEvent(curPlayer)
|
| | | pass
|
| | |
|
| | | elif curPlayerAction == IPY_GameWorld.paGameEvent:
|
| | | PlayerGameEvent.StopGameEvent(curPlayer, tick)
|
| | | |
| | | pass
|
| | | |
| | | if curPlayerAction == IPY_GameWorld.paPreparing:
|
| | | DoExitPreparing(curPlayer)
|
| | |
|
| | |
| | | #执行下马逻辑
|
| | | PlayerHorse.PlayerRideHorseDown(curPlayer, False)
|
| | |
|
| | | #玩家镖车中, 下车
|
| | | elif curPlayerVehicle == IPY_GameWorld.pvTruck:
|
| | | PlayerTruck.PlayerTruckDown(curPlayer, curPlayer.GetTruck())
|
| | | |
| | | #---其他系统处理---
|
| | |
|
| | | #中断战斗对峙
|
| | |
| | | fightExpRate += PlayerGoldInvest.GetAddFightExpRate(curPlayer)
|
| | |
|
| | | actExpRateInfo = PyGameData.g_operationActionDict.get(ShareDefine.OperationActionName_ExpRate, {})# 多倍经验活动加成
|
| | | if not PlayerTJG.GetIsTJG(curPlayer) and actExpRateInfo.get(ShareDefine.ActKey_State):
|
| | | if actExpRateInfo.get(ShareDefine.ActKey_State):
|
| | | actExpIpyData = IpyGameDataPY.GetIpyGameData("ActExpRate", actExpRateInfo.get(ShareDefine.ActKey_CfgID))
|
| | | if actExpIpyData and curPlayer.GetLV() >= actExpIpyData.GetLVLimit():
|
| | | fightExpRate += actExpIpyData.GetAddExpRate()
|
| | |
| | | def GetLeaveFamilyTimeEx(curPlayer):return curPlayer.GetExAttr19()
|
| | | def SetLeaveFamilyTimeEx(curPlayer, value):
|
| | | curPlayer.SetExAttr19(value)
|
| | | curPlayer.SendGameServerRefreshState(ShareDefine.CDBPlayerRefresh_ExAttr19, value, 0)
|
| | | #curPlayer.SendGameServerRefreshState(ShareDefine.CDBPlayerRefresh_ExAttr19, value, 0)
|
| | | curPlayer.SendPropertyRefresh(ShareDefine.CDBPlayerRefresh_ExAttr19, value, 0, False)
|
| | | return
|
| | |
|
| | |
| | | # @param sight 视野范围
|
| | | # @return 无意义
|
| | | def SetSight(curPlayer, sight):
|
| | | import QuestCommon
|
| | | firstMission = QuestCommon.GetCommonMission(curPlayer)
|
| | | if firstMission and firstMission.GetProperty(QuestCommon.Def_NewGuyNoSight) == 1:
|
| | | curPlayer.SetSight(0)
|
| | | return
|
| | | |
| | | #外挂号 视野验证
|
| | | if curPlayer.NomalDictGetProperty(ChConfig.Def_Player_Dict_AutoCheckHack_State) \
|
| | | == ChConfig.Def_AutoCheck_State_Danger:
|
| | |
| | | def GetFamilyEmblemID(curPlayer): return curPlayer.NomalDictGetProperty(ChConfig.Def_Player_Dict_FamilyEmblemID)
|
| | | def SetFamilyEmblemID(curPlayer, emblemID): NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_FamilyEmblemID, emblemID)
|
| | |
|
| | | # 仙盟职位,使用 GetReceivedSalary,因为FamilyMemberLV没有入库
|
| | | def GetFamilyMemberLV(curPlayer): return curPlayer.GetReceivedSalary()
|
| | | def SetFamilyMemberLV(curPlayer, fmLV):
|
| | | #因为仙盟职位没有存DBPlayer,而跨服后又没有Family信息,所以这里做个存储,用于跨服用
|
| | | curPlayer.SetReceivedSalary(fmLV)
|
| | | curPlayer.SetFamilyMemberLV(fmLV) # 也同步设置该值,防止有些地方直接调用 curPlayer.GetFamilyMemberLV()
|
| | | return
|
| | |
|
| | | # 仙盟事务速度加成
|
| | | def GetAffairSpeedPer(curPlayer): return curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_AffairSpeedPer)
|
| | | def SetAffairSpeedPer(curPlayer, value): curPlayer.SetDict(ChConfig.Def_PlayerKey_AffairSpeedPer, value)
|