10019 【砍树】回合战斗(回合战斗buff持续时间处理及持续性buff定时触发时机处理支持;增加回合战斗死亡及复活支持;)
| | |
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 22 回合战斗角色死亡 #tagMCTurnFightObjDead
|
| | |
|
| | | class tagMCTurnFightObjDead(Structure):
|
| | | _pack_ = 1
|
| | | _fields_ = [
|
| | | ("Cmd", c_ubyte),
|
| | | ("SubCmd", c_ubyte),
|
| | | ("ObjID", c_int), |
| | | ("ObjType", c_ubyte), |
| | | ]
|
| | |
|
| | | def __init__(self):
|
| | | self.Clear()
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x22
|
| | | return
|
| | |
|
| | | def ReadData(self, stringData, _pos=0, _len=0):
|
| | | self.Clear()
|
| | | memmove(addressof(self), stringData[_pos:], self.GetLength())
|
| | | return _pos + self.GetLength()
|
| | |
|
| | | def Clear(self):
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x22
|
| | | self.ObjID = 0
|
| | | self.ObjType = 0
|
| | | return
|
| | |
|
| | | def GetLength(self):
|
| | | return sizeof(tagMCTurnFightObjDead)
|
| | |
|
| | | def GetBuffer(self):
|
| | | return string_at(addressof(self), self.GetLength())
|
| | |
|
| | | def OutputString(self):
|
| | | DumpString = '''// B4 22 回合战斗角色死亡 //tagMCTurnFightObjDead:
|
| | | Cmd:%s,
|
| | | SubCmd:%s,
|
| | | ObjID:%d,
|
| | | ObjType:%d
|
| | | '''\
|
| | | %(
|
| | | self.Cmd,
|
| | | self.SubCmd,
|
| | | self.ObjID,
|
| | | self.ObjType
|
| | | )
|
| | | return DumpString
|
| | |
|
| | |
|
| | | m_NAtagMCTurnFightObjDead=tagMCTurnFightObjDead()
|
| | | ChNetPackDict[eval("0x%02x%02x"%(m_NAtagMCTurnFightObjDead.Cmd,m_NAtagMCTurnFightObjDead.SubCmd))] = m_NAtagMCTurnFightObjDead
|
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 23 回合战斗角色复活 #tagMCTurnFightObjReborn
|
| | |
|
| | | class tagMCTurnFightObjReborn(Structure):
|
| | | _pack_ = 1
|
| | | _fields_ = [
|
| | | ("Cmd", c_ubyte),
|
| | | ("SubCmd", c_ubyte),
|
| | | ("ObjID", c_int), |
| | | ("ObjType", c_ubyte), |
| | | ("HP", c_int), # 复活后血量,求余亿部分
|
| | | ("HPEx", c_int), # 复活后血量,整除亿部分
|
| | | ("RebornType", c_ubyte), # 复活方式:1-灵宠技能复活;2-待扩展
|
| | | ("RebornValue1", c_int), # 复活方式对应值1,由复活方式决定其值意义
|
| | | ("RebornValue2", c_int), # 复活方式对应值2
|
| | | ]
|
| | |
|
| | | def __init__(self):
|
| | | self.Clear()
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x23
|
| | | return
|
| | |
|
| | | def ReadData(self, stringData, _pos=0, _len=0):
|
| | | self.Clear()
|
| | | memmove(addressof(self), stringData[_pos:], self.GetLength())
|
| | | return _pos + self.GetLength()
|
| | |
|
| | | def Clear(self):
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x23
|
| | | self.ObjID = 0
|
| | | self.ObjType = 0
|
| | | self.HP = 0
|
| | | self.HPEx = 0
|
| | | self.RebornType = 0
|
| | | self.RebornValue1 = 0
|
| | | self.RebornValue2 = 0
|
| | | return
|
| | |
|
| | | def GetLength(self):
|
| | | return sizeof(tagMCTurnFightObjReborn)
|
| | |
|
| | | def GetBuffer(self):
|
| | | return string_at(addressof(self), self.GetLength())
|
| | |
|
| | | def OutputString(self):
|
| | | DumpString = '''// B4 23 回合战斗角色复活 //tagMCTurnFightObjReborn:
|
| | | Cmd:%s,
|
| | | SubCmd:%s,
|
| | | ObjID:%d,
|
| | | ObjType:%d,
|
| | | HP:%d,
|
| | | HPEx:%d,
|
| | | RebornType:%d,
|
| | | RebornValue1:%d,
|
| | | RebornValue2:%d
|
| | | '''\
|
| | | %(
|
| | | self.Cmd,
|
| | | self.SubCmd,
|
| | | self.ObjID,
|
| | | self.ObjType,
|
| | | self.HP,
|
| | | self.HPEx,
|
| | | self.RebornType,
|
| | | self.RebornValue1,
|
| | | self.RebornValue2
|
| | | )
|
| | | return DumpString
|
| | |
|
| | |
|
| | | m_NAtagMCTurnFightObjReborn=tagMCTurnFightObjReborn()
|
| | | ChNetPackDict[eval("0x%02x%02x"%(m_NAtagMCTurnFightObjReborn.Cmd,m_NAtagMCTurnFightObjReborn.SubCmd))] = m_NAtagMCTurnFightObjReborn
|
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 20 回合制战斗状态 #tagMCTurnFightState
|
| | |
|
| | | class tagMCTurnFightState(Structure):
|
| | |
| | | import ChNPC
|
| | | import BossHurtMng
|
| | | import NPCHurtMgr
|
| | | import TurnAttack
|
| | |
|
| | | import datetime
|
| | | import math
|
| | |
| | | dFinalHurtReduce = PlayerControl.GetFinalHurtReduce(defObj) # 最终固定伤害减少
|
| | | dBeHurtPer = PlayerControl.GetBeHurtPer(defObj) # 加深受到伤害百分比
|
| | | dFightPower = PlayerControl.GetFightPower(defObj)
|
| | | dFinalHurtReducePer = PlayerControl.GetFinalHurtReducePer(defObj)
|
| | | dFinalHurtReducePer = GameObj.GetFinalHurtReducePer(defObj)
|
| | | dFinalHurtReducePer += PassiveBuffEffMng.GetPassiveSkillValueByTriggerType(defObj, atkObj, curSkill, ChConfig.TriggerType_dFinalHurtReducePer)
|
| | |
|
| | | else:
|
| | |
| | | dFinalHurtReduce = 0 # 最终固定伤害减少
|
| | | dBeHurtPer = 0
|
| | | dFightPower = NPCCommon.GetSuppressFightPower(defObj)
|
| | | dFinalHurtReducePer = 0 # 最终伤害减少百分比 默认0
|
| | | dFinalHurtReducePer = GameObj.GetFinalHurtReducePer(defObj)
|
| | |
|
| | | #攻击字典 { 攻击类型 : '公式' }
|
| | | mapID = FBCommon.GetRecordMapID(GameWorld.GetMap().GetMapID())
|
| | |
| | | if not hurtValue:
|
| | | return
|
| | |
|
| | | if atkObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum):
|
| | | if atkObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline):
|
| | | pass
|
| | | else:
|
| | | tick = GameWorld.GetGameWorld().GetTick()
|
| | |
| | | if GameObj.GetHP(curObjDetel) > 0:
|
| | | return
|
| | |
|
| | | if TurnAttack.SetKilled(curObjDetel):
|
| | | return
|
| | | |
| | | #---玩家处理---
|
| | | if curObjDetel.GetGameObjType() == IPY_GameWorld.gotPlayer:
|
| | | playerControl = PlayerControl.PlayerControl(curObjDetel)
|
| | |
| | | import ChNPC
|
| | | import GameObj
|
| | | import GameWorld
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | | Def_FB_NPCAI_SideList = []
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | #普通NPC
|
| | | if GameObj.GetHP(defender) <= 0:
|
| | | if TurnAttack.SetKilled(defender):
|
| | | return
|
| | | if not ChNPC.OnCheckCanDie(attacker, defender, skill, tick):
|
| | | return
|
| | | #副本
|
| | |
| | | import PetControl
|
| | | import NPCCommon
|
| | | import SkillShell
|
| | | import TurnAttack
|
| | | import GameObj
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | |
| | |
|
| | | #宠物死亡
|
| | | if GameObj.GetHP(curTagPet) <= 0:
|
| | | if TurnAttack.SetKilled(curTagPet):
|
| | | return
|
| | | curTagPetNPCControl = NPCCommon.NPCControl(curTagPet)
|
| | | curTagPetNPCControl.SetKilled()
|
| | |
|
| | |
| | | import NPCCommon
|
| | | import ChNPC
|
| | | import PlayerTJG
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | AttackCommon.SetPlayerBattleState(curTagPlayer, tick)
|
| | | #触发被动buff
|
| | | #AttackCommon.DefenderSpringBuff(curTagPlayer, tick, BaseAttack.GetIsSuperHit())
|
| | | elif TurnAttack.SetKilled(curTagPlayer):
|
| | | pass
|
| | | else:
|
| | | #通知玩家
|
| | | if curTagPlayer.GetMapID() != ChConfig.Def_FBMapID_XMZZ:
|
| | |
| | | import IPY_GameWorld
|
| | | import GameWorld
|
| | | import SkillShell
|
| | | import TurnAttack
|
| | | import GameObj
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | |
| | |
|
| | | #召唤兽死亡
|
| | | if GameObj.GetHP(curTagSummonNPC) <= 0:
|
| | | if TurnAttack.SetKilled(curTagSummonNPC):
|
| | | return
|
| | | curTagSummonNPCControl = NPCCommon.NPCControl(curTagSummonNPC)
|
| | | #召唤兽死亡
|
| | | curTagSummonNPCControl.SetKilled()
|
| | |
| | | import SkillShell
|
| | | import ChNPC
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | #执行击杀NPC逻辑
|
| | | curPlayer = PetControl.GetPetOwner(curPet) # 宠物主人
|
| | |
|
| | | if TurnAttack.SetKilled(curTagNPC):
|
| | | return
|
| | | |
| | | if not ChNPC.OnCheckCanDie(curPlayer, curTagNPC, skill, tick):
|
| | | return
|
| | |
|
| | |
| | | import PetControl
|
| | | import SkillShell
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | #宠物死亡
|
| | | if GameObj.GetHP(curTagPet) <= 0:
|
| | | if TurnAttack.SetKilled(curTagPet):
|
| | | return
|
| | | curTagPetNPCControl = NPCCommon.NPCControl(curTagPet)
|
| | | curTagPetNPCControl.SetKilled()
|
| | |
|
| | |
| | | import PetControl
|
| | | import SkillShell
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | return
|
| | |
|
| | | if TurnAttack.SetKilled(curTagPlayer):
|
| | | return
|
| | | |
| | | if curPlayer != None:
|
| | | #执行玩家击杀玩家逻辑
|
| | | AttackCommon.OnPlayerKillPlayer(curPlayer, curTagPlayer, tick)
|
| | |
| | | import PetControl
|
| | | import SkillShell
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | #防守方召唤兽死亡
|
| | | if GameObj.GetHP(curTagSummon) <= 0:
|
| | | if TurnAttack.SetKilled(curTagSummon):
|
| | | return
|
| | | curTagSummonNPCControl = NPCCommon.NPCControl(curTagSummon)
|
| | | #召唤兽死亡
|
| | | curTagSummonNPCControl.SetKilled()
|
| | |
| | | import SkillShell
|
| | | import ChNPC
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | return
|
| | |
|
| | | if GameObj.GetHP(curTagNormalNPC) <= 0:
|
| | | if TurnAttack.SetKilled(curTagNormalNPC):
|
| | | return
|
| | | if not ChNPC.OnCheckCanDie(curPlayer, curTagNormalNPC, skill, tick):
|
| | | return
|
| | | #执行击杀NPC逻辑
|
| | |
| | | import SkillCommon
|
| | | import PetControl
|
| | | import SkillShell
|
| | | import TurnAttack
|
| | | import GameObj
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | |
| | |
|
| | | #宠物死亡
|
| | | if GameObj.GetHP(curTagPet) <= 0:
|
| | | if TurnAttack.SetKilled(curTagPet):
|
| | | return
|
| | | curTagPetNPCControl = NPCCommon.NPCControl(curTagPet)
|
| | | curTagPetNPCControl.SetKilled()
|
| | |
|
| | |
| | | import FBLogic
|
| | | import GameObj
|
| | | import ChNPC
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | #召唤兽死亡
|
| | | if GameObj.GetHP(curTagSummon) <= 0:
|
| | | if TurnAttack.SetKilled(curTagSummon):
|
| | | return
|
| | | NPCCommon.OnPlayerAttackNPCDie(curTagSummon, curPlayer, skill)
|
| | | FBLogic.DoFB_Player_KillNPC(curPlayer , curTagSummon , tick)
|
| | | #获得控制器
|
| | |
| | | import SkillShell
|
| | | import ChNPC
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | #玩家击杀NPC副本触发器
|
| | | curPlayer = NPCCommon.GetSummonNPCOwner(IPY_GameWorld.gotPlayer, curSummonNPC)
|
| | |
|
| | | if TurnAttack.SetKilled(curTagNPC):
|
| | | return
|
| | | |
| | | if not ChNPC.OnCheckCanDie(curPlayer, curTagNPC, skill, tick):
|
| | | return
|
| | |
|
| | |
| | | import PlayerControl
|
| | | import PetControl
|
| | | import SkillShell
|
| | | import TurnAttack
|
| | | import GameObj
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | |
| | |
|
| | | #宠物死亡
|
| | | if GameObj.GetHP(curTagPet) <= 0:
|
| | | if TurnAttack.SetKilled(curTagPet):
|
| | | return
|
| | | curTagPetNPCControl = NPCCommon.NPCControl(curTagPet)
|
| | | curTagPetNPCControl.SetKilled()
|
| | |
|
| | |
| | | import SkillShell
|
| | | import ChNPC
|
| | | import GameObj
|
| | | import TurnAttack
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | | AttackCommon.OnPlayerHitPlayer(curPlayer, curTagPlayer, tick)
|
| | |
|
| | | return
|
| | | |
| | | |
| | | if TurnAttack.SetKilled(curTagPlayer):
|
| | | return
|
| | | |
| | | if curPlayer != None:
|
| | | #执行玩家击杀玩家逻辑
|
| | | AttackCommon.OnPlayerKillPlayer(curPlayer, curTagPlayer, tick)
|
| | |
| | | import GameWorld
|
| | | import PlayerControl
|
| | | import SkillShell
|
| | | import TurnAttack
|
| | | import GameObj
|
| | | #---------------------------------------------------------------------
|
| | |
|
| | |
| | |
|
| | | #防守方召唤兽死亡
|
| | | if GameObj.GetHP(curTagSummon) <= 0:
|
| | | if TurnAttack.SetKilled(curTagSummon):
|
| | | return
|
| | | curTagSummonNPCControl = NPCCommon.NPCControl(curTagSummon)
|
| | | #召唤兽死亡
|
| | | curTagSummonNPCControl.SetKilled()
|
| | |
| | | def Attack(attacker, defender, useSkill, tick, skillPercent=10000, skillEnhance=0, attackTime=1, isEnhanceSkill=False):
|
| | | global g_skillHurtList
|
| | |
|
| | | if attacker.GetGameObjType() == IPY_GameWorld.gotNPC:
|
| | | #Npc在防一次攻击限制, 防止眩晕时能进行普攻
|
| | | if not OperControlManager.IsObjCanDoAction(attacker,
|
| | | ChConfig.Def_Obj_ActState_ServerSkill,
|
| | | ChConfig.Def_Action_Attack_Bit):
|
| | | return False
|
| | | #if attacker.GetGameObjType() == IPY_GameWorld.gotNPC:
|
| | | # #Npc在防一次攻击限制, 防止眩晕时能进行普攻
|
| | | #玩家也需要判断普攻
|
| | | if not OperControlManager.IsObjCanDoAction(attacker,
|
| | | ChConfig.Def_Obj_ActState_ServerSkill,
|
| | | ChConfig.Def_Action_Attack_Bit):
|
| | | return False
|
| | |
|
| | | #判断攻击对象是否为敌人
|
| | | if not GetCanAttack(attacker, defender, useSkill, tick):
|
| | |
| | | GameWorld.DebugLog("击晕CD中! rate=%s,剩余tick=%s" % (rate, remainTick), attacker.GetID())
|
| | | return
|
| | | attacker.SetDict(ChConfig.Def_PlayerKey_AttrFaintCD, tick)
|
| | | GameWorld.DebugLog("触发击晕! rate=%s,tagID=%s" % (rate, defender.GetID()), attacker.GetID())
|
| | | |
| | | GameWorld.DebugLog("可触发击晕! rate=%s,tagID=%s" % (rate, defender.GetID()), attacker.GetID())
|
| | | SkillCommon.AddBuffBySkillType(defender, ChConfig.Def_SkillID_AtkerFaint, tick)
|
| | | return
|
| | |
|
| | |
| | | import GameWorld |
| | | import GameObj |
| | | import PetControl |
| | | import SkillShell |
| | | |
| | | ( |
| | | FightState_Start, |
| | |
| | | FightState_Fail, |
| | | FightState_Over, |
| | | ) = range(5) |
| | | |
| | | ( |
| | | RebornType_PetSkill, |
| | | ) = range(1, 1 + 1) |
| | | |
| | | def GetObjName(gameObj): |
| | | objName = gameObj.GetName() |
| | |
| | | factionListB = fightPetObjListB + [tagObj] |
| | | atkFactionList = [factionListA, factionListB] |
| | | |
| | | # 设置战斗主体 |
| | | curPlayer.SetDict(ChConfig.Def_Obj_Dict_TurnFightMainRole, 1) |
| | | tagObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightMainRole, 1) |
| | | |
| | | # 战斗前初始化,可能会改变攻速,所以先初始化 |
| | | for faction, factionObjList in enumerate(atkFactionList, 1): |
| | | for gameObj in factionObjList: |
| | | TurnFightObjStartInit(gameObj, faction, tick) |
| | | TurnFightObjStartInit(playerID, gameObj, faction, tick) |
| | | |
| | | #一个回合攻击顺序,为了后续逻辑统一,都是先确定好顺序 |
| | | sortType = 2 # 攻击顺序排序方式 |
| | |
| | | for gameObj in fightObjList: |
| | | TurnFightObjPerTurnStart(gameObj, turnNum, tick) |
| | | |
| | | isWin = CheckIswin(curPlayer, tagObj) |
| | | if isWin != None: |
| | | break |
| | | |
| | | # 回合战斗: 轮流依次攻击 |
| | | for gameObj in fightObjList: |
| | | if not gameObj or GameObj.GetHP(gameObj) <= 0: |
| | | for actionNum, gameObj in enumerate(fightObjList, 1): |
| | | if not gameObj: |
| | | # 没有对象可视为没有该节点 |
| | | continue |
| | | faction = GameObj.GetFaction(gameObj) |
| | | |
| | | for obj in fightObjList: |
| | | TurnFightObjPerTurnActionnum(turnNum, actionNum, obj, tick) |
| | | |
| | | objType = gameObj.GetGameObjType() |
| | | objID = gameObj.GetID() |
| | | SyncTurnFightObjAction(curPlayer, turnNum, objType, objID) |
| | | |
| | | if GameObj.GetHP(gameObj) <= 0: |
| | | # 复活时机在自己行动节点 |
| | | if not DoReborn(gameObj): |
| | | continue |
| | | |
| | | faction = GameObj.GetFaction(gameObj) |
| | | objName = GetObjName(gameObj) |
| | | curHP = GameObj.GetHP(gameObj) |
| | | |
| | |
| | | tagObjID = tagGameObj.GetID() |
| | | tagHP = GameObj.GetHP(tagGameObj) |
| | | |
| | | GameWorld.DebugLog(" ★回合%s %s 行动 : objType-ID-HP(%s-%s-%s), tagType-ID-HP(%s-%s-%s)" |
| | | % (turnNum, objName, objType, objID, curHP, tagObjType, tagObjID, tagHP)) |
| | | SyncTurnFightObjAction(curPlayer, turnNum, objType, objID) |
| | | GameWorld.DebugLog(" ★回合%s.%s %s 行动 : objType-ID-HP(%s-%s-%s),curAtk=%s, tagType-ID-HP(%s-%s-%s)" |
| | | % (turnNum, actionNum, objName, objType, objID, curHP, gameObj.GetMaxAtk(), tagObjType, tagObjID, tagHP)) |
| | | |
| | | DoAttack(gameObj, tagGameObj, tick) |
| | | |
| | | playerDead = GameObj.GetHP(curPlayer) <= 0 |
| | | tagObjDead = (not tagObj or GameObj.GetHP(tagObj) <= 0) |
| | | if not playerDead and not tagObjDead: |
| | | if not DoAttack(gameObj, tagGameObj, tick): |
| | | continue |
| | | |
| | | if playerDead and tagObjDead: |
| | | isWin = False # 平局算失败 |
| | | GameWorld.DebugLog(" 双方被击杀,平局算失败: isWin=%s" % isWin) |
| | | elif playerDead: |
| | | isWin = False |
| | | GameWorld.DebugLog(" 玩家被击杀,失败: isWin=%s" % isWin) |
| | | elif tagObjDead: |
| | | isWin = True # 胜利 |
| | | GameWorld.DebugLog(" 对手被击杀,胜利: isWin=%s" % isWin) |
| | | break |
| | | |
| | | isWin = CheckIswin(curPlayer, tagObj) |
| | | if isWin != None: |
| | | break |
| | | |
| | | if isWin != None: |
| | | break |
| | | |
| | |
| | | % (mapID, funcLineID, tagPlayerID, isWin, overState), playerID) |
| | | return |
| | | |
| | | def TurnFightObjStartInit(gameObj, faction, tick): |
| | | def CheckIswin(curPlayer, tagObj): |
| | | ## 检查是否结束 |
| | | # @return: None-未结束;True-获胜;False-失败 |
| | | playerDead = GameObj.GetHP(curPlayer) <= 0 and GetRebornTypeInfo(curPlayer) == None |
| | | tagObjDead = (not tagObj or GameObj.GetHP(tagObj) <= 0) and GetRebornTypeInfo(tagObj) == None |
| | | |
| | | if not playerDead and not tagObjDead: |
| | | return |
| | | |
| | | isWin = None |
| | | if playerDead and tagObjDead: |
| | | isWin = False # 平局算失败 |
| | | GameWorld.DebugLog(" 双方被击杀,平局算失败: isWin=%s" % isWin) |
| | | elif playerDead: |
| | | isWin = False |
| | | GameWorld.DebugLog(" 玩家被击杀,失败: isWin=%s" % isWin) |
| | | elif tagObjDead: |
| | | isWin = True # 胜利 |
| | | GameWorld.DebugLog(" 对手被击杀,胜利: isWin=%s" % isWin) |
| | | |
| | | return isWin |
| | | |
| | | def SetKilled(gameObj, killer=None): |
| | | if not gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightMainRole): |
| | | #GameWorld.DebugLog("非回合战斗主体被击杀: curID=%s" % gameObj.GetID()) |
| | | return |
| | | |
| | | GameWorld.DebugLog(" %s 回合战斗主体被击杀: curID=%s" % (GetObjName(gameObj), gameObj.GetID())) |
| | | GameObj.SetHP(gameObj, 0) |
| | | |
| | | playerID = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightID) |
| | | if not playerID: |
| | | return |
| | | curPlayer = GameWorld.GetMapCopyPlayerManager().FindPlayerByID(playerID) |
| | | if not curPlayer: |
| | | return |
| | | |
| | | # 通知前端 |
| | | clientPack = ChPyNetSendPack.tagMCTurnFightObjDead() |
| | | clientPack.ObjID = gameObj.GetID() |
| | | clientPack.ObjType = gameObj.GetGameObjType() |
| | | NetPackCommon.SendFakePack(curPlayer, clientPack) |
| | | return True |
| | | |
| | | def GetRebornTypeInfo(gameObj): |
| | | ''' 获取可复活的方式信息 |
| | | @return: None-代表不可复活 |
| | | ''' |
| | | if not gameObj: |
| | | return |
| | | |
| | | if not gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightMainRole): |
| | | # 仅主体可复活 |
| | | return |
| | | |
| | | rebornCountMax = 1 |
| | | curRebornCount = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnRebornCount) |
| | | if curRebornCount >= rebornCountMax: |
| | | GameWorld.DebugLog("%s 已经超过复活次数,不能再复活! curID=%s,curRebornCount=%s" % (GetObjName(gameObj), gameObj.GetID(), curRebornCount)) |
| | | return |
| | | |
| | | # 检查是否有灵宠复活技能 |
| | | for index in range(gameObj.GetSummonCount()): |
| | | curSummonNPC = gameObj.GetSummonNPCAt(index) |
| | | if not curSummonNPC: |
| | | continue |
| | | if not PetControl.IsPetNPC(curSummonNPC): |
| | | continue |
| | | skillManager = curSummonNPC.GetSkillManager() |
| | | for skillIndex in range(skillManager.GetSkillCount()): |
| | | skill = skillManager.GetSkillByIndex(skillIndex) |
| | | if skill.GetSkillType() != ChConfig.Def_SkillType_Revive: |
| | | continue |
| | | if not skill.GetRemainTime(): |
| | | return RebornType_PetSkill, curSummonNPC, skill |
| | | |
| | | # 检查其他功能复活,待扩展... |
| | | |
| | | #GameWorld.DebugLog(" 没有可以复活的方式!") |
| | | return |
| | | |
| | | def DoReborn(gameObj, hpPer=ChConfig.Def_MaxRateValue): |
| | | ## 执行复活 |
| | | rebornTypeInfo = GetRebornTypeInfo(gameObj) |
| | | if rebornTypeInfo == None: |
| | | return |
| | | |
| | | objName = GetObjName(gameObj) |
| | | objID = gameObj.GetID() |
| | | objType = gameObj.GetGameObjType() |
| | | |
| | | rebornType = rebornTypeInfo[0] |
| | | rebornValue1, rebornValue2 = 0, 0 |
| | | if rebornType == RebornType_PetSkill: |
| | | petNPC, skill = rebornTypeInfo[1:] |
| | | skill.SetRemainTime(skill.GetCoolDownTime()) |
| | | hpPer = skill.GetEffect(0).GetEffectValue(0) |
| | | rebornValue1 = petNPC.GetID() |
| | | rebornValue2 = skill.GetSkillID() |
| | | |
| | | rebornCount = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnRebornCount) + 1 |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnRebornCount, rebornCount) |
| | | setHP = int(GameObj.GetMaxHP(gameObj) * hpPer / float(ChConfig.Def_MaxRateValue)) |
| | | GameObj.SetHP(gameObj, setHP) |
| | | |
| | | if objType == IPY_GameWorld.gotPlayer: |
| | | gameObj.ChangeAction(IPY_GameWorld.paNull) |
| | | else: |
| | | gameObj.ChangeAction(IPY_GameWorld.laNPCNull) |
| | | |
| | | curHP = GameObj.GetHP(gameObj) |
| | | GameWorld.DebugLog("复活 %s: rebornType=%s,objID=%s,hpPer=%s,curHP=%s,rebornCount=%s" % (objName, rebornType, objID, hpPer, curHP, rebornCount)) |
| | | |
| | | playerID = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightID) |
| | | if not playerID: |
| | | return |
| | | curPlayer = GameWorld.GetMapCopyPlayerManager().FindPlayerByID(playerID) |
| | | if not curPlayer: |
| | | return |
| | | |
| | | # 通知前端 |
| | | clientPack = ChPyNetSendPack.tagMCTurnFightObjReborn() |
| | | clientPack.ObjID = gameObj.GetID() |
| | | clientPack.ObjType = gameObj.GetGameObjType() |
| | | clientPack.HP = curHP % ChConfig.Def_PerPointValue |
| | | clientPack.HPEx = curHP / ChConfig.Def_PerPointValue |
| | | clientPack.RebornType = rebornType |
| | | clientPack.RebornValue1 = rebornValue1 |
| | | clientPack.RebornValue2 = rebornValue2 |
| | | NetPackCommon.SendFakePack(curPlayer, clientPack) |
| | | return True |
| | | |
| | | def SetTimeline(gameObj, turnNum, actionNum): |
| | | '''设置回合制战斗所在时间节点 |
| | | @param turnNum: 第几回合,如果在回合制战斗中,则回合数一定大于0, |
| | | @param actionNum: 第几个行动节点,每回合的行动节点会重置,也就是说行动节点0可视为每回合的起始节点,1位第一个行动目标节点,以此类推 |
| | | ''' |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightTimeline, turnNum * 100 + actionNum) |
| | | return |
| | | |
| | | def TurnFightObjStartInit(playerID, gameObj, faction, tick): |
| | | ## 回合制战斗实例初始化 |
| | | if not gameObj: |
| | | return |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightNum, 1) |
| | | isMainRole = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightMainRole) |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightID, playerID) |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnRebornCount, 0) |
| | | SetTimeline(gameObj, 1, 0) |
| | | GameObj.SetFaction(gameObj, faction) |
| | | GameObj.SetHPFull(gameObj) |
| | | gameObj.RefreshView() |
| | |
| | | objName = GetObjName(gameObj) |
| | | fightPlaceNum = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_FightPetPlaceNum) |
| | | |
| | | GameWorld.DebugLog("【 %s 初始化 %s 】 objID=%s,npcID=%s,atkSpeed=%s,HP=%s,Atk=%s,Def=%s" |
| | | % (objName, BaseAttack.GetObjAttackName(gameObj), gameObj.GetID(), npcID, |
| | | GameObj.GetAtkSpeed(gameObj), GameObj.GetHP(gameObj), gameObj.GetMaxAtk(), gameObj.GetDef())) |
| | | GameWorld.DebugLog("【 %s 初始化 %s 】 objID=%s,npcID=%s,atkSpeed=%s,HP=%s,Atk=%s,Def=%s,isMainRole=%s" |
| | | % (objName, BaseAttack.GetObjAttackName(gameObj), gameObj.GetID(), npcID, |
| | | GameObj.GetAtkSpeed(gameObj), GameObj.GetHP(gameObj), gameObj.GetMaxAtk(), gameObj.GetDef(), isMainRole)) |
| | | GameWorld.DebugLog(" 闪避(%s,%s),暴击(%s,%s),击晕(%s,%s),连击(%s,%s),反击(%s,%s),吸血(%s,%s)" |
| | | % (GameObj.GetMissRate(gameObj), GameObj.GetMissDefRate(gameObj), |
| | | GameObj.GetSuperHitRate(gameObj), GameObj.GetSuperHitRateReduce(gameObj), |
| | |
| | | continue |
| | | skillIDList.append(curSkill.GetSkillID()) |
| | | if fightPlaceNum: |
| | | # 灵宠技能开始时直接进入CD |
| | | curSkill.SetLastUseTick(tick) |
| | | curSkill.SetRemainTime(curSkill.GetCoolDownTime()) |
| | | if curSkill.GetSkillType() != ChConfig.Def_SkillType_Revive: |
| | | # 灵宠技能开始时直接进入CD |
| | | curSkill.SetLastUseTick(tick) |
| | | curSkill.SetRemainTime(curSkill.GetCoolDownTime()) |
| | | GameWorld.DebugLog(" NPC技能: npcID=%s,skillIDList=%s" % (npcID, skillIDList)) |
| | | |
| | | return |
| | |
| | | if not gameObj: |
| | | return |
| | | |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightNum, turnNum) |
| | | SetTimeline(gameObj, turnNum, 0) |
| | | # 重置连击、反击数 |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnComboNum, 0) |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnAtkBackNum, 0) |
| | |
| | | skill.SetRemainTime(updRemainTime) |
| | | GameWorld.DebugLog(" skillID=%s,remainTime=%s,updRemainTime=%s" % (skillID, remainTime, updRemainTime)) |
| | | |
| | | # 刷新定时处理的buff效果 |
| | | SkillShell.ProcessPersistBuff(gameObj, tick) |
| | | return |
| | | |
| | | def TurnFightObjPerTurnActionnum(turnNum, actionNum, gameObj, tick): |
| | | ## 回合制战斗实例 - 每个行动节点处理 |
| | | if not gameObj: |
| | | return |
| | | |
| | | SetTimeline(gameObj, turnNum, actionNum) |
| | | |
| | | objType = gameObj.GetGameObjType() |
| | | if objType == IPY_GameWorld.gotPlayer: |
| | | #刷新玩家Buff时长 |
| | | gameObj.SetTickByType(ChConfig.TYPE_Player_Tick_Buff, 0) |
| | | gameObj.SetPersistBuffTick(0) |
| | | |
| | | #刷新玩家Buff |
| | | reFlashBuff = PlayerState.ProcessRefreshBuffState(gameObj, tick) |
| | | #刷新玩家场景buff效果 |
| | | PlayerState.ProcessPlayerBuffEffect(gameObj, tick) |
| | | #SkillShell.ProcessPersistBuff(gameObj, tick) # 定时处理的在每个时间节点有需要再开启,目前默认回合开始处理 |
| | | |
| | | attrBuffResult, actBuffResult = PlayerState.ProcessRefreshActionBuffState(gameObj, tick) |
| | | playerControl = PlayerControl.PlayerControl(gameObj) |
| | |
| | | ## 回合制战斗实例结束重置 |
| | | if not gameObj: |
| | | return |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnFightNum, 0) |
| | | SetTimeline(gameObj, 0, 0) |
| | | gameObj.SetDict(ChConfig.Def_Obj_Dict_TurnBattleType, 0) |
| | | GameObj.SetFaction(gameObj, 0) |
| | | |
| | |
| | | return |
| | | |
| | | def RecycleObj(gameObj): |
| | | ## 释放回合制战斗对象 |
| | | |
| | | #灵宠跟召唤兽由主人回收时触发回收,不然会导致报错 |
| | | npcObjType = gameObj.GetGameNPCObjType() |
| | | if npcObjType == IPY_GameWorld.gnotPet: |
| | | #GameWorld.DebugLog("RecycleObj 灵宠不回收 objID=%s,npcObjType=%s,%s" % (gameObj.GetID(), npcObjType, gameObj.GetNPCID())) |
| | |
| | | if curOwner and curOwner.GetGameObjType() == IPY_GameWorld.gotNPC: |
| | | #GameWorld.DebugLog("RecycleObj 召唤兽主人是NPC不回收 objID=%s,npcObjType=%s,%s,ownerID=%s" % (gameObj.GetID(), npcObjType, gameObj.GetNPCID(), curOwner.GetID())) |
| | | return |
| | | if GameObj.GetHP(gameObj) <= 0: |
| | | #GameWorld.DebugLog("RecycleObj 已死亡,不用重复回收 objID=%s,npcObjType=%s,%s" % (gameObj.GetID(), npcObjType, gameObj.GetNPCID())) |
| | | return |
| | | |
| | | #GameWorld.DebugLog("RecycleObj: objID=%s,npcObjType=%s,%s" % (gameObj.GetID(), npcObjType, gameObj.GetNPCID())) |
| | | NPCCommon.SetDeadEx(gameObj) |
| | | return |
| | |
| | | tagHP = GameObj.GetHP(tagObj) |
| | | GameWorld.DebugLog(" curID-HP=(%s-%s),tagID-HP=(%s-%s)" % (curID, curHP, tagID, tagHP)) |
| | | if tagHP <= 0 or curHP <= 0: |
| | | return |
| | | return True |
| | | |
| | | # 反击,反击可打断连击,所以优先判断 |
| | | if CanAtkBack(curObj, tagObj): |
| | | DoAttack(tagObj, curObj, tick) |
| | | return |
| | | return True |
| | | |
| | | # 连击 |
| | | if CanCombo(curObj, tagObj): |
| | | DoAttack(curObj, tagObj, tick) |
| | | |
| | | return |
| | | return True |
| | | |
| | | def CanAtkBack(atkObj, defObj): |
| | | ## 可否反击 |
| | |
| | |
|
| | | #---Obj字典-------
|
| | | Def_Obj_Dict_Faction = 'Faction' # 所属阵营
|
| | | Def_Obj_Dict_TurnFightNum = 'TurnFightNum' # 回合制战斗当前轮次
|
| | | Def_Obj_Dict_TurnFightID = 'TurnFightID' # 回合制战斗所属玩家ID
|
| | | Def_Obj_Dict_TurnFightTimeline = 'TurnFightTimeline' # 回合制战斗时间线: 回合数*100+行动编号节点
|
| | | Def_Obj_Dict_TurnFightMainRole = 'TurnFightMainRole' # 是否回合制战斗主体,最终胜负由主体存活状态决定
|
| | | Def_Obj_Dict_TurnRebornCount = 'TurnRebornCount' # 回合战斗已复活次数
|
| | | Def_Obj_Dict_TurnComboNum = 'TurnComboNum' # 本回合已累计连击次数
|
| | | Def_Obj_Dict_TurnAtkBackNum = 'TurnAtkBackNum' # 本回合已累计反击次数
|
| | | Def_Obj_Dict_TurnBattleType = 'TurnBattleType' # 本次攻击战斗类型:TurnBattleType_xxx
|
| | |
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 22 回合战斗角色死亡 #tagMCTurnFightObjDead
|
| | |
|
| | | class tagMCTurnFightObjDead(Structure):
|
| | | _pack_ = 1
|
| | | _fields_ = [
|
| | | ("Cmd", c_ubyte),
|
| | | ("SubCmd", c_ubyte),
|
| | | ("ObjID", c_int), |
| | | ("ObjType", c_ubyte), |
| | | ]
|
| | |
|
| | | def __init__(self):
|
| | | self.Clear()
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x22
|
| | | return
|
| | |
|
| | | def ReadData(self, stringData, _pos=0, _len=0):
|
| | | self.Clear()
|
| | | memmove(addressof(self), stringData[_pos:], self.GetLength())
|
| | | return _pos + self.GetLength()
|
| | |
|
| | | def Clear(self):
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x22
|
| | | self.ObjID = 0
|
| | | self.ObjType = 0
|
| | | return
|
| | |
|
| | | def GetLength(self):
|
| | | return sizeof(tagMCTurnFightObjDead)
|
| | |
|
| | | def GetBuffer(self):
|
| | | return string_at(addressof(self), self.GetLength())
|
| | |
|
| | | def OutputString(self):
|
| | | DumpString = '''// B4 22 回合战斗角色死亡 //tagMCTurnFightObjDead:
|
| | | Cmd:%s,
|
| | | SubCmd:%s,
|
| | | ObjID:%d,
|
| | | ObjType:%d
|
| | | '''\
|
| | | %(
|
| | | self.Cmd,
|
| | | self.SubCmd,
|
| | | self.ObjID,
|
| | | self.ObjType
|
| | | )
|
| | | return DumpString
|
| | |
|
| | |
|
| | | m_NAtagMCTurnFightObjDead=tagMCTurnFightObjDead()
|
| | | ChNetPackDict[eval("0x%02x%02x"%(m_NAtagMCTurnFightObjDead.Cmd,m_NAtagMCTurnFightObjDead.SubCmd))] = m_NAtagMCTurnFightObjDead
|
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 23 回合战斗角色复活 #tagMCTurnFightObjReborn
|
| | |
|
| | | class tagMCTurnFightObjReborn(Structure):
|
| | | _pack_ = 1
|
| | | _fields_ = [
|
| | | ("Cmd", c_ubyte),
|
| | | ("SubCmd", c_ubyte),
|
| | | ("ObjID", c_int), |
| | | ("ObjType", c_ubyte), |
| | | ("HP", c_int), # 复活后血量,求余亿部分
|
| | | ("HPEx", c_int), # 复活后血量,整除亿部分
|
| | | ("RebornType", c_ubyte), # 复活方式:1-灵宠技能复活;2-待扩展
|
| | | ("RebornValue1", c_int), # 复活方式对应值1,由复活方式决定其值意义
|
| | | ("RebornValue2", c_int), # 复活方式对应值2
|
| | | ]
|
| | |
|
| | | def __init__(self):
|
| | | self.Clear()
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x23
|
| | | return
|
| | |
|
| | | def ReadData(self, stringData, _pos=0, _len=0):
|
| | | self.Clear()
|
| | | memmove(addressof(self), stringData[_pos:], self.GetLength())
|
| | | return _pos + self.GetLength()
|
| | |
|
| | | def Clear(self):
|
| | | self.Cmd = 0xB4
|
| | | self.SubCmd = 0x23
|
| | | self.ObjID = 0
|
| | | self.ObjType = 0
|
| | | self.HP = 0
|
| | | self.HPEx = 0
|
| | | self.RebornType = 0
|
| | | self.RebornValue1 = 0
|
| | | self.RebornValue2 = 0
|
| | | return
|
| | |
|
| | | def GetLength(self):
|
| | | return sizeof(tagMCTurnFightObjReborn)
|
| | |
|
| | | def GetBuffer(self):
|
| | | return string_at(addressof(self), self.GetLength())
|
| | |
|
| | | def OutputString(self):
|
| | | DumpString = '''// B4 23 回合战斗角色复活 //tagMCTurnFightObjReborn:
|
| | | Cmd:%s,
|
| | | SubCmd:%s,
|
| | | ObjID:%d,
|
| | | ObjType:%d,
|
| | | HP:%d,
|
| | | HPEx:%d,
|
| | | RebornType:%d,
|
| | | RebornValue1:%d,
|
| | | RebornValue2:%d
|
| | | '''\
|
| | | %(
|
| | | self.Cmd,
|
| | | self.SubCmd,
|
| | | self.ObjID,
|
| | | self.ObjType,
|
| | | self.HP,
|
| | | self.HPEx,
|
| | | self.RebornType,
|
| | | self.RebornValue1,
|
| | | self.RebornValue2
|
| | | )
|
| | | return DumpString
|
| | |
|
| | |
|
| | | m_NAtagMCTurnFightObjReborn=tagMCTurnFightObjReborn()
|
| | | ChNetPackDict[eval("0x%02x%02x"%(m_NAtagMCTurnFightObjReborn.Cmd,m_NAtagMCTurnFightObjReborn.SubCmd))] = m_NAtagMCTurnFightObjReborn
|
| | |
|
| | |
|
| | | #------------------------------------------------------
|
| | | # B4 20 回合制战斗状态 #tagMCTurnFightState
|
| | |
|
| | | class tagMCTurnFightState(Structure):
|
| | |
| | | gameObj.SetDict(ChConfig.Def_PlayerKey_BloodShiledHurtEx, value / ShareDefine.Def_PerPointValue)
|
| | | return
|
| | |
|
| | | def GetFinalHurtReducePer(gameObj): return gameObj.GetDictByKey(ChConfig.Def_PlayerKey_FinalHurtReducePer)
|
| | | def SetFinalHurtReducePer(gameObj, value):
|
| | | ## 最终伤害减免百分比
|
| | | gameObj.SetDict(ChConfig.Def_PlayerKey_FinalHurtReducePer, value)
|
| | | if gameObj.GetGameObjType() == IPY_GameWorld.gotPlayer:
|
| | | PlayerControl.SendPropertyRefresh(gameObj, ShareDefine.CDBPlayerRefresh_FinalHurtReducePer, value)
|
| | | return
|
| | |
|
| | | def GetFaction(gameObj):
|
| | | faction = gameObj.GetDictByKey(ChConfig.Def_Obj_Dict_Faction)
|
| | | if faction:
|
| | |
| | | return False
|
| | |
|
| | | #CD时间
|
| | | if curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum):
|
| | | if curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline):
|
| | | if useSkill.GetRemainTime():
|
| | | #GameWorld.Log('技能回合CD中 = %s, %s'%(useSkill.GetSkillName(), useSkill.GetRemainTime()))
|
| | | return False
|
| | |
| | | def DoAutoUseSkill(curNPC, curTag, tagDist, tick):
|
| | | #攻击僵持中
|
| | | if tick - curNPC.GetAttackTick() < curNPC.GetAtkInterval():
|
| | | if not (PetControl.IsPet(curNPC) or curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum)):
|
| | | if not (PetControl.IsPet(curNPC) or curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline)):
|
| | | #GameWorld.Log('攻击僵持中')
|
| | | return False
|
| | |
|
| | |
| | | if not useSkill or useSkill.GetSkillTypeID() == 0:
|
| | | break
|
| | |
|
| | | if useSkill.GetSkillType() == ChConfig.Def_SkillType_Revive:
|
| | | #复活技能单独处理
|
| | | continue
|
| | | |
| | | if useSkillIDOnDie and useSkillIDOnDie == useSkill.GetSkillID():
|
| | | #GameWorld.DebugLog("死亡释放的技能仅在死亡时才能释放!useSkillIDOnDie=%s" % useSkillIDOnDie)
|
| | | continue
|
| | |
| | | def __GetIsInRefreshPoint(self, curPosX, curPosY, refreshPoint):
|
| | | if not refreshPoint:
|
| | | curNPC = self.curNPC
|
| | | if curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum):
|
| | | if curNPC.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline):
|
| | | return True
|
| | | if self.logDetail:
|
| | | GameWorld.Log(" not refreshPoint=%s" % refreshPoint, self.npcID, self.lineID)
|
| | |
| | | curPlayer.SetDict(ChConfig.Def_PlayerKey_FinalHurtPer, value)
|
| | | SendPropertyRefresh(curPlayer, ShareDefine.CDBPlayerRefresh_FinalHurtPer, value)
|
| | |
|
| | | ## 最终伤害减免百分比
|
| | | def GetFinalHurtReducePer(curPlayer): return curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_FinalHurtReducePer)
|
| | | def SetFinalHurtReducePer(curPlayer, value):
|
| | | curPlayer.SetDict(ChConfig.Def_PlayerKey_FinalHurtReducePer, value)
|
| | | SendPropertyRefresh(curPlayer, ShareDefine.CDBPlayerRefresh_FinalHurtReducePer, value)
|
| | | |
| | | ## 最终固定伤害增加
|
| | | def GetFinalHurt(curPlayer): return curPlayer.GetDictByKey(ChConfig.Def_PlayerKey_FinalHurt)
|
| | | def SetFinalHurt(curPlayer, value):
|
| | |
| | | curPlayerPropDict["FinalHurt"] = PlayerControl.GetFinalHurt(curPlayer) # 最终固定伤害增加
|
| | | curPlayerPropDict["FinalHurtReduce"] = PlayerControl.GetFinalHurtReduce(curPlayer) # 最终固定伤害减少
|
| | | curPlayerPropDict["FinalHurtPer"] = PlayerControl.GetFinalHurtPer(curPlayer) # 最终伤害百分比
|
| | | curPlayerPropDict["FinalHurtReducePer"] = PlayerControl.GetFinalHurtReducePer(curPlayer) # 最终伤害减少百分比
|
| | | curPlayerPropDict["FinalHurtReducePer"] = GameObj.GetFinalHurtReducePer(curPlayer) # 最终伤害减少百分比
|
| | | curPlayerPropDict["OnlyFinalHurt"] = PlayerControl.GetOnlyFinalHurt(curPlayer) # 额外输出伤害
|
| | | curPlayerPropDict["DamChanceDef"] = PlayerControl.GetDamChanceDef(curPlayer) # 20%的概率抵御伤害比率
|
| | | curPlayerPropDict["NPCHurtAddPer"] = PlayerControl.GetNPCHurtAddPer(curPlayer) # 对怪物伤害加成
|
| | |
| | | # 继承上一个buff的循环记录
|
| | | addBuff.SetProcessInterval(updProcessInterval)
|
| | |
|
| | | turnFightTimeline = curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline)
|
| | | if turnFightTimeline:
|
| | | addBuff.SetCalcStartTick(turnFightTimeline)
|
| | | #GameWorld.DebugLog(" SetCalcStartTick:%s, skillID=%s,objID=%s" % (turnFightTimeline, skillID, curObj.GetID()))
|
| | | |
| | | #设置buff属性
|
| | | __SetBuffValue(addBuff , plusValueList , buffOwner)
|
| | |
|
| | |
| | | PYSync_RefreshBuff(curObj, addBuff, SkillCommon.GetBuffType(curSkill), notifyAll=False, owner = buffOwner, errSkillID=skillID)
|
| | |
|
| | | #添加BUFF后的特殊处理
|
| | | DoAddBuffOver(curObj, curSkill, addBuff, buffOwner, tick)
|
| | | DoAddBuffOver(curObj, buffState, curSkill, addBuff, buffOwner, tick)
|
| | |
|
| | | #检查是否属于刷新BUFF
|
| | | #===========================================================================
|
| | |
| | | # @param addBuff 玩家身上的BUFF实例
|
| | | # @param tick 时间戳
|
| | | # @return None
|
| | | def DoAddBuffOver(curObj, curSkill, addBuff, buffOwner, tick):
|
| | | def DoAddBuffOver(curObj, buffState, curSkill, addBuff, buffOwner, tick):
|
| | | #触发被动技能
|
| | | if buffOwner:
|
| | | PassiveBuffEffMng.OnPassiveSkillTrigger(buffOwner, curObj, curSkill, ChConfig.TriggerType_AddBuffOver, tick)
|
| | |
| | |
|
| | | callFunc(curObj, addBuff, curEffect, tick, buffOwner)
|
| | |
|
| | | # 回合制下,持续型处理buff添加后立即处理一次
|
| | | if isLstSkill and curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline):
|
| | | SkillShell.ProcessSinglePersistBuff(curObj, buffState, addBuff, tick, True)
|
| | | |
| | | return
|
| | |
|
| | |
|
| | |
| | |
|
| | | buffState.Sync_RefreshBuff(buffIndex, curBuff.GetRemainTime())
|
| | |
|
| | | DoAddBuffOver(curObj, curBuff.GetSkill(), curBuff, buffOwner, GameWorld.GetGameWorld().GetTick()) |
| | | DoAddBuffOver(curObj, buffState, curBuff.GetSkill(), curBuff, buffOwner, GameWorld.GetGameWorld().GetTick()) |
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | |
| | |
|
| | | index = 0
|
| | | isPlayerTJG = (curObj.GetGameObjType() == IPY_GameWorld.gotPlayer and PlayerTJG.GetIsTJG(curObj))
|
| | | turnNum = curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum) # 回合编号,大于0同时也代表回合制中
|
| | | turnFightTimeline = curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline)
|
| | | turnNum, actionNum = turnFightTimeline / 100, turnFightTimeline % 100
|
| | |
|
| | | skillIDListInDelBuff = [] # buff消失中需要处理添加buff,外层处理避免错乱
|
| | |
|
| | |
| | | #GameWorld.DebugLog("脱机挂状态下不刷新buff时间: skillTypeID=%s" % curSkill.GetSkillTypeID())
|
| | | continue
|
| | |
|
| | | remainTime = curBuffRemainTime - ( tick - curBuff.GetCalcStartTick() )
|
| | | # buff回合时长计算
|
| | | if turnNum > 0:
|
| | | remainTime -= ChConfig.Def_PerTurnTick
|
| | | GameWorld.DebugLog(" 刷新buff时间: objID=%s,skillID=%s,remainTime=%s,turnNum=%s" % (curObj.GetID(), curSkill.GetSkillID(), remainTime, turnNum))
|
| | | #回合制下持续性类型buff由process时机处理 ProcessSinglePersistBuff
|
| | | if curSkill.GetSkillType() in ChConfig.Def_LstBuff_List:
|
| | | index += 1
|
| | | continue
|
| | | calcTick = curBuff.GetCalcStartTick()
|
| | | calcTurnNum, calcActionNum = calcTick / 100, calcTick % 100
|
| | | passTurnNum = turnNum - calcTurnNum # 经过的回合数
|
| | | if passTurnNum > 0:
|
| | | if actionNum < calcActionNum:
|
| | | passTurnNum -= 1 # 还未到该buff的计算节点,可视为本回合未到,需-1
|
| | | |
| | | remainTime = curBuffRemainTime
|
| | | if passTurnNum > 0: # 最小单位1回合,有满1回合才减时长
|
| | | remainTime = curBuffRemainTime - ChConfig.Def_PerTurnTick * passTurnNum
|
| | | GameWorld.DebugLog(" 刷新回合buff时间: objID=%s,skillID=%s,remainTime=%s,calcTick=%s,timeline=%s,passTurnNum=%s" |
| | | % (curObj.GetID(), curSkill.GetSkillID(), remainTime, calcTick, turnFightTimeline, passTurnNum))
|
| | | curBuff.SetCalcStartTick(turnFightTimeline)
|
| | | curBuff.SetRemainTime(remainTime)
|
| | | |
| | | #还有剩余时间
|
| | | if remainTime > 0:
|
| | | index += 1
|
| | | continue
|
| | |
|
| | | #还有剩余时间
|
| | | if remainTime > 0:
|
| | | curBuff.SetCalcStartTick( tick ) |
| | | curBuff.SetRemainTime( remainTime )
|
| | | index += 1
|
| | | continue
|
| | | # buff常规时长计算
|
| | | else:
|
| | | remainTime = curBuffRemainTime - ( tick - curBuff.GetCalcStartTick() )
|
| | | |
| | | #还有剩余时间
|
| | | if remainTime > 0:
|
| | | curBuff.SetCalcStartTick( tick ) |
| | | curBuff.SetRemainTime( remainTime )
|
| | | index += 1
|
| | | continue
|
| | | #-------------------无剩余时间了
|
| | | curBuff.SetRemainTime(0)
|
| | |
|
| | |
| | | [lambda curObj:PlayerControl.GetNormalHurtPer(curObj), lambda curObj, value:PlayerControl.SetNormalHurtPer(curObj, value), ShareDefine.CDBPlayerRefresh_NormalHurtPer, 1, 0], # 属性普通攻击加成
|
| | | [lambda curObj:PlayerControl.GetFabaoHurt(curObj), lambda curObj, value:PlayerControl.SetFabaoHurt(curObj, value), ShareDefine.CDBPlayerRefresh_FabaoHurt, 1, 0], # 属性法宝技能增伤
|
| | | [lambda curObj:PlayerControl.GetFabaoHurtPer(curObj), lambda curObj, value:PlayerControl.SetFabaoHurtPer(curObj, value), ShareDefine.CDBPlayerRefresh_FabaoHurtPer, 1, 0], # 属性法宝技能加成
|
| | | [lambda curObj:PlayerControl.GetFinalHurtReducePer(curObj), lambda curObj, value:PlayerControl.SetFinalHurtReducePer(curObj, value), ShareDefine.CDBPlayerRefresh_FinalHurtReducePer, 1, 0], # 最终伤害减少百分比
|
| | | [lambda curObj:GameObj.GetFinalHurtReducePer(curObj), lambda curObj, value:GameObj.SetFinalHurtReducePer(curObj, value), ShareDefine.CDBPlayerRefresh_FinalHurtReducePer, 1, 0], # 最终伤害减少百分比
|
| | | [lambda curObj:PlayerControl.GetLostYinjiTime(curObj), lambda curObj, value:PlayerControl.SetLostYinjiTime(curObj, value), ShareDefine.CDBPlayerRefresh_YinjiTime, 1, 0], # 每X秒自动消失一个印记 毫秒
|
| | | [lambda curObj:PlayerControl.GetTheFBSkillsCD(curObj), lambda curObj, value:PlayerControl.SetTheFBSkillsCD(curObj, value), 0, 0, 0], # 减少指定技能组CD XX%
|
| | | [lambda curObj:PlayerControl.GetBurnValue(curObj), lambda curObj, value:PlayerControl.SetBurnValue(curObj, value), 0, 0, 0], # 灼烧固定伤害
|
| | |
| | | if not buffStateCount:
|
| | | return
|
| | |
|
| | | turnNum = curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightNum) # 回合编号,大于0同时也代表回合制中
|
| | | |
| | | #buff持续效果
|
| | | for i in range(0, buffStateCount):
|
| | | #buff持续效果,回合下可能删除buff,倒序遍历
|
| | | for i in range(0, buffStateCount)[::-1]:
|
| | | curBuff = buffState.GetBuff(i)
|
| | | ProcessSinglePersistBuff(curObj, buffState, curBuff, tick)
|
| | |
|
| | | if not curBuff:
|
| | | #在以下处理过程中, 对方有可能死亡, 如果死亡, 会清空buff, 导致这里取得None
|
| | | #所以一定要continue |
| | | continue
|
| | | |
| | | curBuffSkill = curBuff.GetSkill()
|
| | | |
| | | if not __BuffCanProcess(curObj, curBuffSkill):
|
| | | continue
|
| | |
|
| | | processBuffTick = GetProcessBuffTick(curBuffSkill, curObj)
|
| | | |
| | | #---验证触发间隔TICK---
|
| | | if turnNum > 0:
|
| | | GameWorld.DebugLog(" buffProcess: objID=%s,skillID=%s,turnNum=%s" % (curObj.GetID(), curBuffSkill.GetSkillID(), turnNum))
|
| | | else:
|
| | | if tick - curBuff.GetProcessInterval() <= processBuffTick:
|
| | | continue
|
| | | curBuff.SetProcessInterval(tick)
|
| | | |
| | | |
| | | #得到当前buff
|
| | | for effIndex in range(0, curBuffSkill.GetEffectCount()):
|
| | | #得到当前效果
|
| | | curEffect = curBuffSkill.GetEffect(effIndex)
|
| | | curEffectID = curEffect.GetEffectID()
|
| | | |
| | | if not curEffectID:
|
| | | continue
|
| | | |
| | | processStr = "BuffProcess_%d.%s"%(curEffectID, "ProcessBuff")
|
| | | |
| | | callBuffProcessFunc = GameWorld.GetExecFunc(GameBuffs, processStr)
|
| | | |
| | | if not callBuffProcessFunc:
|
| | | continue
|
| | | |
| | | callBuffProcessFunc(curObj, curBuff, curEffect, processBuffTick, tick)
|
| | | |
| | | #执行ProcessBuff中设定的玩家字典
|
| | | __DoProcessBuff_PlayerKey(curObj, tick)
|
| | | return
|
| | |
|
| | | def ProcessSinglePersistBuff(curObj, buffState, curBuff, tick, turnForce=False):
|
| | | '''处理单个持续性buff,可能会删除buff,调用时如果是循环遍历,需注意遍历顺序,防止buff删除后索引错乱
|
| | | @param turnForce: 回合下强制立刻执行
|
| | | '''
|
| | | if not curBuff:
|
| | | return
|
| | | curBuffSkill = curBuff.GetSkill()
|
| | | |
| | | if not __BuffCanProcess(curObj, curBuffSkill):
|
| | | return
|
| | | |
| | | processBuffTick = GetProcessBuffTick(curBuffSkill, curObj)
|
| | | |
| | | isDel = False
|
| | | remainTime = None
|
| | | timeLine = curObj.GetDictByKey(ChConfig.Def_Obj_Dict_TurnFightTimeline)
|
| | | #---验证触发间隔TICK---
|
| | | if timeLine > 0:
|
| | | turnNum, actionNum = timeLine / 100, timeLine % 100
|
| | | if not turnForce and actionNum != 0:
|
| | | # 持续型buff暂仅支持回合开始时处理
|
| | | return
|
| | | remainTime = curBuff.GetRemainTime() - ChConfig.Def_PerTurnTick # 每处理一次固定算一回合
|
| | | if remainTime <= 0:
|
| | | isDel = True
|
| | | GameWorld.DebugLog(" 回合buffProcess: objID=%s,skillID=%s,remainTime=%s,turnNum=%s" % (curObj.GetID(), curBuffSkill.GetSkillID(), remainTime, turnNum))
|
| | | else:
|
| | | if tick - curBuff.GetProcessInterval() <= processBuffTick:
|
| | | return
|
| | | curBuff.SetProcessInterval(tick)
|
| | | |
| | | #得到当前buff
|
| | | for effIndex in range(0, curBuffSkill.GetEffectCount()):
|
| | | #得到当前效果
|
| | | curEffect = curBuffSkill.GetEffect(effIndex)
|
| | | curEffectID = curEffect.GetEffectID()
|
| | | |
| | | if not curEffectID:
|
| | | continue
|
| | | |
| | | processStr = "BuffProcess_%d.%s"%(curEffectID, "ProcessBuff")
|
| | | |
| | | callBuffProcessFunc = GameWorld.GetExecFunc(GameBuffs, processStr)
|
| | | |
| | | if not callBuffProcessFunc:
|
| | | continue
|
| | | |
| | | callBuffProcessFunc(curObj, curBuff, curEffect, processBuffTick, tick)
|
| | | |
| | | # 剩余时间需效果处理后再设置
|
| | | if remainTime != None:
|
| | | curBuff.SetRemainTime(remainTime)
|
| | | |
| | | if not isDel:
|
| | | return
|
| | | |
| | | GameWorld.DebugLog(" buffProcess后删除buff: objID=%s,skillID=%s,turnNum=%s" % (curObj.GetID(), curBuffSkill.GetSkillID(), turnNum))
|
| | | skillID = curBuffSkill.GetSkillID()
|
| | | skillTypeID = curBuffSkill.GetSkillTypeID()
|
| | | ownerID, ownerType = curBuff.GetOwnerID(), curBuff.GetOwnerType()
|
| | | BuffSkill.DoBuffDisApper(curObj, curBuff, tick)
|
| | | buffState.DeleteBuffByTypeID(skillTypeID)
|
| | | SkillShell.ClearBuffEffectBySkillID(curObj, skillID, ownerID, ownerType)
|
| | | return
|
| | |
|
| | | #---------------------------------------------------------------------
|
| | | ##执行ProcessBuff中设定的玩家字典
|
| | |
| | | def CheeckTrigSkillandTag(attacker, exSkill, defender, tick):
|
| | | #再次验证附加技能是否对目标可用
|
| | | if attacker.GetGameObjType() != IPY_GameWorld.gotPlayer:
|
| | | skillTag = GetSkillAffectTag(exSkill)
|
| | | #该技能是对自己使用的 防守者应该改为攻击者
|
| | | if GetSkillAffectTag(exSkill) in [ChConfig.Def_UseSkillTag_Self,
|
| | | if skillTag in [ChConfig.Def_UseSkillTag_Self,
|
| | | ChConfig.Def_UseSkillTag_SelfAndFriend]:
|
| | | return True, attacker
|
| | | |
| | | # 召唤兽对主人释放技能
|
| | | if skillTag == ChConfig.Def_UseSkillTag_SummonMaster:
|
| | | if not NPCCommon.IsSummonNPC(attacker):
|
| | | return False, None
|
| | | curSummonOwner = NPCCommon.GetSummonNPCOwner(IPY_GameWorld.gotPlayer, attacker) |
| | | if curSummonOwner == None:
|
| | | curSummonOwner = NPCCommon.GetSummonNPCOwner(IPY_GameWorld.gotNPC, attacker)
|
| | | if curSummonOwner == None:
|
| | | return False, None
|
| | | return True, curSummonOwner
|
| | | |
| | | return True, defender
|
| | |
|
| | | #该技能是对自己使用的 防守者应该改为攻击者
|