| #!/usr/bin/python | 
| # -*- coding: GBK -*- | 
| #------------------------------------------------------------------------------- | 
| # | 
| ##@package GameWorldLogic.FBProcess.GameLogic_RealmTower | 
| # | 
| # @todo:¾³½çËþ | 
| # @author hxp | 
| # @date 2023-10-25 | 
| # @version 1.0 | 
| # | 
| # ÏêϸÃèÊö: ¾³½çËþ | 
| # | 
| #------------------------------------------------------------------------------- | 
| #"""Version = 2023-10-25 01:30""" | 
| #------------------------------------------------------------------------------- | 
|   | 
| import FBCommon | 
| import GameWorld | 
| import IPY_GameWorld | 
| import PlayerControl | 
| import NetPackCommon | 
| import NPCCustomRefresh | 
| import GameWorldProcess | 
| import ChPyNetSendPack | 
| import ItemControler | 
| import IpyGameDataPY | 
| import ChConfig | 
| import ChPlayer | 
| import GameObj | 
|   | 
| FBDict_Floor = 'FBDict_Floor'   # ¸±±¾¹Ø¿¨ | 
|   | 
| # ¸±±¾Í¨ÓÃÅäÖà | 
| ( | 
| Def_PrepareTime, # Ã¿¹Ø×¼±¸Ê±¼ä£¬Ãë | 
| Def_FightTime, # Ã¿¹ØÕ½¶·Ê±¼ä£¬Ãë | 
| Def_ExitTime, # Í˳öʱ¼ä, Ãë | 
| ) = range(3) | 
|   | 
| # ¸±±¾×´Ì¬ | 
| ( | 
| FB_State_Open, # ¸±±¾¿ªÆô | 
| FB_State_FightPrepare, # Õ½¶·×¼±¸Ê±¼ä | 
| FB_State_Fighting, # Õ½¶· | 
| FB_State_FreeTime, # »î¶¯½áÊø×¼±¸£¨Ê¤Àû/ʧ°Ü£© | 
| FB_State_Close, # ¹Ø±Õ¸±±¾ | 
| ) = range(5) | 
|   | 
| def __GetFBTimelCfg(): return FBCommon.GetFBLineStepTime(ChConfig.Def_FBMapID_RealmTower) | 
|   | 
| def GetTowerIpyData(floor): return IpyGameDataPY.GetIpyGameData("RealmTower", floor) | 
|   | 
| def OnFBPlayerOnLogin(curPlayer): | 
|     SyncRealmTowerInfo(curPlayer) | 
|     return | 
|   | 
| def SyncRealmTowerInfo(curPlayer): | 
|     clientPack = ChPyNetSendPack.tagMCRealmTowerInfo() | 
|     clientPack.Clear() | 
|     clientPack.Floor = curPlayer.NomalDictGetProperty(ChConfig.Def_Player_Dict_RealmTowerFloor) | 
|     NetPackCommon.SendFakePack(curPlayer, clientPack) | 
|     return | 
|   | 
| def OnEnterFBEvent(curPlayer, mapID, lineId, tick): | 
|     nextFloorID = curPlayer.NomalDictGetProperty(ChConfig.Def_Player_Dict_RealmTowerFloor) + 1 | 
|     return __CheckCanChallenge(curPlayer, nextFloorID) | 
|   | 
| ## ¼ì²é¿É·ñ½øÐÐÌôÕ½ | 
| def __CheckCanChallenge(curPlayer, floorID): | 
|     playerID = curPlayer.GetPlayerID() | 
|     ipyData = GetTowerIpyData(floorID) | 
|     if not ipyData: | 
|         GameWorld.ErrLog("¾³½çËþ²ã²»´æÔÚ: floorID=%s" % floorID, playerID) | 
|         return False | 
|      | 
|     curFloorID = curPlayer.NomalDictGetProperty(ChConfig.Def_Player_Dict_RealmTowerFloor) | 
|     if floorID <= curFloorID: | 
|         GameWorld.DebugLog("¸Ã¾³½çËþ²ãÒѹý¹Ø: floorID=%s" % floorID, playerID) | 
|         return False | 
|      | 
|     if floorID > curFloorID + 1: | 
|         GameWorld.DebugLog("ÉÏÒ»²ãδ¹ý¹Ø: floorID=%s > curFloorID=%s+1" % (floorID, curFloorID), playerID) | 
|         return False | 
|      | 
|     if curPlayer.GetOfficialRank() < ipyData.GetNeedRealmLV(): | 
|         GameWorld.DebugLog("¸Ã¾³½çËþ²ãËùÐè¾³½ç²»×ã: floorID=%s,NeedRealmLV=%s" % (floorID, ipyData.GetNeedRealmLV()), playerID) | 
|         return False | 
|      | 
|     return True | 
|   | 
| def OnGetFBEnterPos(curPlayer, mapID, lineId, ipyEnterPosInfo, tick): | 
|     return ipyEnterPosInfo | 
|   | 
| def OnChangeMapAsk(ask, tick): | 
|     return IPY_GameWorld.cmeAccept | 
|   | 
| def DoEnterFB(curPlayer, tick): | 
|     gameFB = GameWorld.GetGameFB() | 
|     fbStep = gameFB.GetFBStep() | 
|      | 
|     if fbStep == FB_State_FightPrepare: | 
|         notify_tick = __GetFBTimelCfg()[Def_PrepareTime] * 1000 - (tick - GameWorld.GetGameFB().GetFBStepTick()) | 
|         curPlayer.Sync_TimeTick(IPY_GameWorld.tttWaitStart, 0, max(notify_tick, 0), True) | 
|          | 
|     elif fbStep == FB_State_Fighting: | 
|         notify_tick = __GetFBTimelCfg()[Def_FightTime] * 1000 - (tick - GameWorld.GetGameFB().GetFBStepTick()) | 
|         curPlayer.Sync_TimeTick(IPY_GameWorld.tttTowerTake, 0, max(notify_tick, 0), True) | 
|          | 
|     elif fbStep > FB_State_Fighting: | 
|         PlayerControl.PlayerLeaveFB(curPlayer) | 
|         return | 
|      | 
|     # ²»×ö´¦Àí£¬Óи±±¾ÐÐΪ¿Í»§¶Ë·¢°üÑ¡ÔñÌôÕ½¹Ø¿¨ | 
|     return | 
|   | 
| def OnCloseFB(tick): | 
|     return | 
|   | 
| def DoExitFB(curPlayer, tick): | 
|     # Íæ¼ÒÍ˳öĬÈϹرո±±¾ | 
|     GameWorldProcess.CloseFB(tick) | 
|     return | 
|   | 
| def OnProcess(tick): | 
|     gameFB = GameWorld.GetGameFB() | 
|     fbStep = gameFB.GetFBStep() | 
|      | 
|     if fbStep == FB_State_FightPrepare: | 
|         __DoLogic_FightPrepare(tick) | 
|     elif fbStep == FB_State_Fighting: | 
|         __DoLogic_Fighting(tick) | 
|     elif fbStep == FB_State_FreeTime: | 
|         __DoLogic_FreeTime(tick) | 
|     elif fbStep == FB_State_Close: | 
|         pass | 
|      | 
|     return | 
|   | 
| ## »ñÈ¡BossID | 
| def __GetRealmTowerBossID(): | 
|     gameFB = GameWorld.GetGameFB() | 
|     floorID = gameFB.GetGameFBDictByKey(FBDict_Floor) | 
|     ipyData = GetTowerIpyData(floorID) | 
|     if not ipyData: | 
|         GameWorld.ErrLog("__GetRealmTowerBossID() can not find %s in RealmTowerNPC.txt" % floorID) | 
|         return 0 | 
|     return ipyData.GetBossID() | 
|   | 
| ##Õ½¶·×¼±¸Ê±¼ä | 
| # @param tick  Ê±ÖÓ | 
| # @return ÎÞÒâÒå | 
| def __DoLogic_FightPrepare(tick): | 
|     gameFB = GameWorld.GetGameFB() | 
|      | 
|     trialCfg = __GetFBTimelCfg() | 
|     if tick - gameFB.GetFBStepTick() < trialCfg[Def_PrepareTime] * 1000: | 
|         return | 
|      | 
|     bossID = __GetRealmTowerBossID() | 
|     if not bossID: | 
|         FBCommon.DoLogic_FBKickAllPlayer() | 
|         return | 
|      | 
|     FBCommon.Sync_Player_TimeTick(IPY_GameWorld.tttTowerTake, trialCfg[Def_FightTime] * 1000) | 
|      | 
|     NPCCustomRefresh.SetNPCRefresh(FBCommon.GetFBLineRefreshNPC(ChConfig.Def_FBMapID_RealmTower, 0), [bossID]) | 
|      | 
|     #תÈëÕ½¶· | 
|     FBCommon.SetFBStep(FB_State_Fighting, tick) | 
|     return | 
|   | 
| ## ¿ªÊ¼¸±±¾¹Ø¿¨ | 
| def StartfloorID(curPlayer, floorID, tick): | 
|     if curPlayer.GetPlayerAction() == IPY_GameWorld.paDie: | 
|         GameWorld.DebugLog("¸´»îÍæ¼Ò...", curPlayer.GetPlayerID()) | 
|         ChPlayer.PlayerRebornByType(curPlayer, ChConfig.rebornType_City, tick) | 
|     GameObj.SetHPFull(curPlayer) | 
|     FBCommon.ClearFBNPC() | 
|      | 
|     gameFB = GameWorld.GetGameFB() | 
|     gameFB.SetGameFBDict(FBDict_Floor, floorID) | 
|      | 
|     prepareTick = __GetFBTimelCfg()[Def_PrepareTime] * 1000 | 
|      | 
|     FBCommon.Sync_Player_TimeTick(IPY_GameWorld.tttWaitStart, prepareTick) | 
|     FBCommon.SetFBStep(FB_State_FightPrepare, tick) | 
|     helpDict = {FBCommon.Help_wheel:floorID} | 
|     FBCommon.Notify_FBHelp(curPlayer, helpDict) | 
|     GameWorld.DebugLog("StartfloorID, floorID=%s, helpDict=%s" % (floorID, str(helpDict)), curPlayer.GetPlayerID()) | 
|     return | 
|   | 
| def __DoLogic_Fighting(tick): | 
|     gameFB = GameWorld.GetGameFB() | 
|      | 
|     #ÅжÏʱ¼ä½áÊø | 
|     if tick - gameFB.GetFBStepTick() < __GetFBTimelCfg()[Def_FightTime] * 1000: | 
|         return | 
|      | 
|     floorID = gameFB.GetGameFBDictByKey(FBDict_Floor) | 
|     playerManager = GameWorld.GetMapCopyPlayerManager() | 
|     for index in xrange(playerManager.GetPlayerCount()): | 
|         curPlayer = playerManager.GetPlayerByIndex(index) | 
|         if not curPlayer: | 
|             continue | 
|         __SendRealmTowerOverInfo(curPlayer, floorID, False) | 
|      | 
|     #ÓÎÏ·½áÊø | 
|     __SetFBToFreeTime(tick) | 
|     return | 
|   | 
| def __SetFBToFreeTime(tick): | 
|     FBCommon.Sync_Player_TimeTick(IPY_GameWorld.tttLeaveMap, __GetFBTimelCfg()[Def_ExitTime] * 1000) | 
|     FBCommon.SetFBStep(FB_State_FreeTime, tick) | 
|     return | 
|   | 
| def __DoLogic_FreeTime(tick): | 
|     if tick - GameWorld.GetGameFB().GetFBStepTick() < __GetFBTimelCfg()[Def_ExitTime] * 1000: | 
|         return | 
|      | 
|     return | 
|   | 
| def DoFB_Player_KillNPC(curPlayer, curNPC, tick): | 
|     gameFB = GameWorld.GetGameFB() | 
|     if gameFB.GetFBStep() != FB_State_Fighting: | 
|         return | 
|      | 
|     bossID = __GetRealmTowerBossID() | 
|     if bossID != curNPC.GetNPCID(): | 
|         return | 
|      | 
|     floorID = gameFB.GetGameFBDictByKey(FBDict_Floor) | 
|      | 
|     # ¹ý¹ØÈ«·þ¹ã²¥ | 
|     ipyData = GetTowerIpyData(floorID) | 
|     if not ipyData: | 
|         return | 
|      | 
|     #¸üйؿ¨ | 
|     PlayerControl.NomalDictSetProperty(curPlayer, ChConfig.Def_Player_Dict_RealmTowerFloor, floorID) | 
|     GameWorld.DebugLog('¸üо³½çËþÒÑͨ¹ØÊý %s' % floorID) | 
|      | 
|     # ¸ø¹ý¹Ø½±Àø | 
|     giveItemList = ipyData.GetRewardItemList() | 
|     ItemControler.GivePlayerItemOrMail(curPlayer, giveItemList, None, ["RealmTower", False, {}]) | 
|     prizeDict = {FBCommon.Over_itemInfo:FBCommon.GetJsonItemList(giveItemList)} | 
|      | 
|     # ¹ý¹ØÊ±¼ä | 
|     costTime = tick - GameWorld.GetGameFB().GetFBStepTick() | 
|     prizeDict[FBCommon.Over_costTime] = costTime | 
|     __SendRealmTowerOverInfo(curPlayer, floorID, True, prizeDict) | 
|      | 
|     SyncRealmTowerInfo(curPlayer) | 
|      | 
|     __SetFBToFreeTime(tick) | 
|     return | 
|   | 
| ## ·¢ËÍÌôÕ½½á¹ûÐÅÏ¢ | 
| def __SendRealmTowerOverInfo(curPlayer, floorID, isPass, overDict={}): | 
|     overDict[FBCommon.Over_dataMapID] = ChConfig.Def_FBMapID_RealmTower | 
|     overDict[FBCommon.Over_wheel] = floorID | 
|     overDict[FBCommon.Over_isPass] = int(isPass) | 
|     GameWorld.DebugLog("__SendRealmTowerOverInfo overDict=%s" % (str(overDict)), curPlayer.GetPlayerID()) | 
|     FBCommon.Notify_FB_Over(curPlayer, overDict) | 
|     return | 
|   | 
| ## ¼ì²éÊÇ·ñ¿É¹¥»÷£¬ Ö÷Åж¨²»¿É¹¥»÷µÄÇé¿ö£¬ÆäËûÂß¼ÓÉÍâ²ã¾ö¶¨ | 
| #  @param attacker ¹¥»÷·½ | 
| #  @param defender ·ÀÊØ·½ | 
| #  @return bool | 
| def CheckCanAttackTagObjInFB(attacker, defender): | 
|     gameFB = GameWorld.GetGameFB() | 
|     if gameFB.GetFBStep() != FB_State_Fighting: | 
|         return False | 
|     return True | 
|   | 
| ##Íæ¼ÒËÀÍö | 
| def DoPlayerDead(curPlayer): | 
|     gameFB = GameWorld.GetGameFB() | 
|     floorID = gameFB.GetGameFBDictByKey(FBDict_Floor) | 
|     __SendRealmTowerOverInfo(curPlayer, floorID, False) | 
|     tick = GameWorld.GetGameWorld().GetTick() | 
|     #ÓÎÏ·½áÊø | 
|     __SetFBToFreeTime(tick) | 
|     return | 
|   | 
| ## ÊÇ·ñ¸±±¾¸´»î | 
| def OnPlayerReborn(): | 
|     return True | 
|   | 
| ## ¸±±¾ÐÐΪ | 
| def DoFBAction(curPlayer, actionType, actionInfo, tick): | 
|     # Ä¬ÈÏΪѡÔñ¹Ø¿¨£¬Óɿͻ§¶Ë¾ö¶¨£¬½ø³¡¼°¸±±¾Ñ¡¹ØÍ¨ÓôËÐÐΪ | 
|     if actionInfo <= 0: | 
|         return | 
|      | 
|     gameFB = GameWorld.GetGameFB() | 
|     fbStep = gameFB.GetFBStep() | 
|      | 
|     if fbStep in [FB_State_FightPrepare, FB_State_Fighting]: | 
|         GameWorld.DebugLog("×¼±¸»òÕ½¶·ÖÐ, ÎÞ·¨±ä¸ü¹Ø¿¨!") | 
|         return | 
|      | 
|     floorID = actionInfo | 
|     if not __CheckCanChallenge(curPlayer, floorID): | 
|         FBCommon.DoLogic_FBKickAllPlayer() | 
|         return | 
|      | 
|     StartfloorID(curPlayer, floorID, tick) | 
|     return |