6459 【后端】【2.0】缥缈仙域开发单(增加按时间掉血的NPC支持)
| | |
| | | DWORD FightPowerCoefficient;//压制战斗力系数
|
| | | };
|
| | |
|
| | | //NPC时间掉血表
|
| | |
|
| | | struct tagNPCTimeLostHP
|
| | | {
|
| | | DWORD _NPCID; //NPCID
|
| | | DWORD LostHPPerSecond; //单人每秒掉血量
|
| | | BYTE MaxPlayerCount; //最大人数
|
| | | DWORD ReduceRate; //衰减万分率
|
| | | };
|
| | |
|
| | | //装备套装属性表
|
| | |
|
| | | struct tagEquipSuitAttr
|
| | |
| | | elif defObj.GetType() == ChConfig.ntHelpBattleRobot:
|
| | | remainHP = min(dHP, max(GameObj.GetMaxHP(defObj)/2, remainHP)) # 助战机器人剩余血量不能少于一半
|
| | | GameObj.SetHP(defObj, remainHP)
|
| | | |
| | | elif defObj.GetType() == ChConfig.ntMonsterTime:
|
| | | UpdateTimeMonsterHP(defObj, tick)
|
| | |
|
| | | else:
|
| | | #防守方是怪物NPC,只扣其血
|
| | |
| | |
|
| | | return resultHurtType
|
| | |
|
| | | def UpdateTimeMonsterHP(curNPC, tick):
|
| | | '''
|
| | | NPC总血量 = 单人每秒掉血量*理论击杀所需时间
|
| | | 掉血值 = 单人每秒掉血量*min(攻击人数, 最大人数)*衰减万分率/10000
|
| | | '''
|
| | | |
| | | npcID = curNPC.GetNPCID()
|
| | | ipyData = IpyGameDataPY.GetIpyGameData("NPCTimeLostHP", npcID)
|
| | | if not ipyData:
|
| | | return
|
| | | |
| | | lastLostHPTick = curNPC.GetDictByKey(ChConfig.Def_NPC_Dict_TimeLostHPTick)
|
| | | curNPC.SetDict(ChConfig.Def_NPC_Dict_TimeLostHPTick, tick)
|
| | | if not lastLostHPTick or tick - lastLostHPTick >= 2000:
|
| | | passTick = 1000
|
| | | else:
|
| | | passTick = tick - lastLostHPTick
|
| | | |
| | | if passTick <= 0:
|
| | | return
|
| | | |
| | | effPlayerCount = curNPC.GetDictByKey(ChConfig.Def_NPC_Dict_TimeLostHPPlayerCount)
|
| | | refreshPlayerCountTick = curNPC.GetDictByKey(ChConfig.Def_NPC_Dict_TimeLostHPPlayerCountTick)
|
| | | if not refreshPlayerCountTick or tick - refreshPlayerCountTick >= 3000:
|
| | | curNPC.SetDict(ChConfig.Def_NPC_Dict_TimeLostHPPlayerCountTick, tick)
|
| | | effPlayerCount = 0
|
| | | for i in xrange(curNPC.GetInSightObjCount()):
|
| | | seeObj = curNPC.GetInSightObjByIndex(i)
|
| | | if seeObj == None :
|
| | | continue
|
| | | if not seeObj.GetVisible():
|
| | | continue
|
| | | seeObjType = seeObj.GetGameObjType()
|
| | | if seeObjType == IPY_GameWorld.gotPlayer:
|
| | | effPlayerCount += 1
|
| | | curNPC.SetDict(ChConfig.Def_NPC_Dict_TimeLostHPPlayerCount, effPlayerCount)
|
| | | #GameWorld.DebugLog("刷新影响人数: effPlayerCount=%s" % effPlayerCount)
|
| | | |
| | | lostHPPerSecond = ipyData.GetLostHPPerSecond()
|
| | | maxPlayerCount = ipyData.GetMaxPlayerCount()
|
| | | reduceRate = ipyData.GetReduceRate()
|
| | | if effPlayerCount > 1:
|
| | | hurtValuePerSecond = lostHPPerSecond * min(maxPlayerCount, effPlayerCount) * reduceRate / 10000.0
|
| | | else:
|
| | | hurtValuePerSecond = lostHPPerSecond
|
| | | lostHPTotal = int(hurtValuePerSecond * passTick / 1000.0)
|
| | | |
| | | remainHP = min(GameObj.GetMaxHP(curNPC), max(0, GameObj.GetHP(curNPC) - lostHPTotal))
|
| | | GameObj.SetHP(curNPC, remainHP, isByTime=True)
|
| | | #GameWorld.DebugLog("怪物按时间掉血: npcID=%s,effPlayerCount=%s,hurtValuePerSecond=%s,passTick=%s,lostHPTotal=%s" |
| | | # % (npcID, effPlayerCount, hurtValuePerSecond, passTick, lostHPTotal))
|
| | | return
|
| | |
|
| | | # 计算伤害后,因各种buff和状态的影响处理
|
| | | def CalcHurtHPWithBuff(atkObj, defObj, hurtValue, curSkill, tick):
|
| | | # 优先处理神兵护盾
|
| | |
| | | Def_NPC_Dict_AtkDelayTick = "AtkDelayTick" # 延迟攻击时长
|
| | | Def_NPC_Dict_AtkStartTick = "AtkStartTick" # 开始攻击tick
|
| | |
|
| | | # 按时间掉血的NPC
|
| | | Def_NPC_Dict_TimeLostHPTick = 'TimeLostHPTick' # 上次按时间掉血tick
|
| | | Def_NPC_Dict_TimeLostHPPlayerCountTick = 'TimeLostHPPlayerCountTick ' # 上次刷新按时间掉血人数tick
|
| | | Def_NPC_Dict_TimeLostHPPlayerCount = 'TimeLostHPPlayerCount' # 按时间掉血有效人数
|
| | |
|
| | | #玩家状态定义,不能超过31个,如超过,需扩展多个key支持
|
| | | Def_PlayerStateList = (
|
| | | Def_PlayerState_Normal, # 无 0
|
| | |
| | | ntDestructible, #场景内可破坏的 19
|
| | | ntHelpBattleRobot, #助战机器人 20
|
| | | ntRobot, #机器人21
|
| | | ntMonsterTime, #按时间掉血的怪物 22
|
| | | ntMax
|
| | | ) = range(23)
|
| | | ) = range(24)
|
| | |
|
| | |
|
| | | (Def_SkillFuncType_Common, #0为通用技能
|
| | |
| | | return
|
| | | if curNPC.GetCurAction() == IPY_GameWorld.laNPCDie:
|
| | | return
|
| | | if curNPC.GetType() not in [IPY_GameWorld.ntMonster]:
|
| | | if curNPC.GetType() not in [IPY_GameWorld.ntMonster, ChConfig.ntMonsterTime]:
|
| | | return
|
| | | if not curNPC.GetVisible():
|
| | | return
|
| | |
| | | return gameObj.GetHPEx()*ShareDefine.Def_PerPointValue + gameObj.GetHP()
|
| | |
|
| | |
|
| | | def SetHP(gameObj, value, isNotify=True):
|
| | | def SetHP(gameObj, value, isNotify=True, isByTime=False):
|
| | | if gameObj.GetGameObjType() == IPY_GameWorld.gotPlayer:
|
| | | gameObj.SetHP(value, isNotify)
|
| | | else:
|
| | | if gameObj.GetType() == ChConfig.ntMonsterTime and not isByTime and value not in [GetMaxHP(gameObj), 0]:
|
| | | #GameWorld.DebugLog("不能设置按时间掉血的怪物血量! id=%s,npciD=%s,value=%s,isByTime=%s" % (gameObj.GetID(), gameObj.GetNPCID(), value, isByTime))
|
| | | return
|
| | | gameObj.SetHPEx(value/ShareDefine.Def_PerPointValue)
|
| | | gameObj.SetHP(value%ShareDefine.Def_PerPointValue)
|
| | |
|
| | |
| | | def GetCurFBLineBOSSID(lineID= -1):
|
| | | #该分线刷的BOSSID
|
| | | if lineID == -1:
|
| | | lineID = GameWorld.GetGameWorld().GetPropertyID() - 1
|
| | | lineID = GetCurFBFuncLineID()
|
| | | if lineID == -1:
|
| | | return 0
|
| | | ipyData = IpyGameDataPY.GetIpyGameDataByCondition("FairyDomain", {"MapID":ChConfig.Def_FBMapID_CrossDemonKing, "LineID":lineID})
|
| | |
| | | ("DWORD", "FightPowerCoefficient", 0),
|
| | | ),
|
| | |
|
| | | "NPCTimeLostHP":(
|
| | | ("DWORD", "NPCID", 1),
|
| | | ("DWORD", "LostHPPerSecond", 0),
|
| | | ("BYTE", "MaxPlayerCount", 0),
|
| | | ("DWORD", "ReduceRate", 0),
|
| | | ),
|
| | |
|
| | | "EquipSuitAttr":(
|
| | | ("WORD", "SuiteID", 1),
|
| | | ("BYTE", "SuiteCnt", 0),
|
| | |
| | | def GetIceDefCoefficient(self): return self.IceDefCoefficient # 元素抗性比例
|
| | | def GetMaxEnduranceTime(self): return self.MaxEnduranceTime # 玩家最大承受伤害时间
|
| | | def GetFightPowerCoefficient(self): return self.FightPowerCoefficient # 压制战斗力系数 |
| | | |
| | | # NPC时间掉血表 |
| | | class IPY_NPCTimeLostHP(): |
| | | |
| | | def __init__(self): |
| | | self.NPCID = 0
|
| | | self.LostHPPerSecond = 0
|
| | | self.MaxPlayerCount = 0
|
| | | self.ReduceRate = 0 |
| | | return |
| | | |
| | | def GetNPCID(self): return self.NPCID # NPCID
|
| | | def GetLostHPPerSecond(self): return self.LostHPPerSecond # 单人每秒掉血量
|
| | | def GetMaxPlayerCount(self): return self.MaxPlayerCount # 最大人数
|
| | | def GetReduceRate(self): return self.ReduceRate # 衰减万分率 |
| | | |
| | | # 装备套装属性表 |
| | | class IPY_EquipSuitAttr(): |
| | |
| | | self.ipyGMAttrLen = len(self.ipyGMAttrCache)
|
| | | self.ipyNPCStrengthenCache = self.__LoadFileData("NPCStrengthen", IPY_NPCStrengthen)
|
| | | self.ipyNPCStrengthenLen = len(self.ipyNPCStrengthenCache)
|
| | | self.ipyNPCTimeLostHPCache = self.__LoadFileData("NPCTimeLostHP", IPY_NPCTimeLostHP)
|
| | | self.ipyNPCTimeLostHPLen = len(self.ipyNPCTimeLostHPCache)
|
| | | self.ipyEquipSuitAttrCache = self.__LoadFileData("EquipSuitAttr", IPY_EquipSuitAttr)
|
| | | self.ipyEquipSuitAttrLen = len(self.ipyEquipSuitAttrCache)
|
| | | self.ipyWingRefineAttrCache = self.__LoadFileData("WingRefineAttr", IPY_WingRefineAttr)
|
| | |
| | | def GetGMAttrByIndex(self, index): return self.ipyGMAttrCache[index]
|
| | | def GetNPCStrengthenCount(self): return self.ipyNPCStrengthenLen
|
| | | def GetNPCStrengthenByIndex(self, index): return self.ipyNPCStrengthenCache[index]
|
| | | def GetNPCTimeLostHPCount(self): return self.ipyNPCTimeLostHPLen
|
| | | def GetNPCTimeLostHPByIndex(self, index): return self.ipyNPCTimeLostHPCache[index]
|
| | | def GetEquipSuitAttrCount(self): return self.ipyEquipSuitAttrLen
|
| | | def GetEquipSuitAttrByIndex(self, index): return self.ipyEquipSuitAttrCache[index]
|
| | | def GetWingRefineAttrCount(self): return self.ipyWingRefineAttrLen
|
| | |
| | | return False
|
| | |
|
| | | useSkillList.sort() # 按使用次数优先升序排,使用次数低的优先判断使用
|
| | | GameWorld.DebugLog('技能使用顺序 = useSkillList%s' % str(useSkillList), curNPC.GetID())
|
| | | #GameWorld.DebugLog('技能使用顺序 = useSkillList%s' % str(useSkillList), curNPC.GetID())
|
| | |
|
| | | for useCnt, index, useSkill in useSkillList:
|
| | | if DoNPCUseSkill(curNPC, curTag, useSkill, tagDist, tick):
|
| | |
| | | GameWorld.DebugLog("竞争归属玩家不在boss范围里,移除归属!playerID=%s" % ownerID)
|
| | | return
|
| | |
|
| | | GameWorld.DebugLog("竞争归属玩家归属正常!playerID=%s" % ownerID)
|
| | | #GameWorld.DebugLog("竞争归属玩家归属正常!playerID=%s" % ownerID)
|
| | | return owner
|
| | |
|
| | | def __GetMaxHurtTeamPlayer(self, teamID, isDead):
|
| | |
| | | copyMapID = GameWorld.GetGameWorld().GetCopyMapID()
|
| | |
|
| | | if mapID == ChConfig.Def_FBMapID_CrossDemonKing:
|
| | | bossID = GameLogic_CrossDemonKing.GetCurFBLineBOSSID(lineID)
|
| | | bossID = GameLogic_CrossDemonKing.GetCurFBLineBOSSID()
|
| | | stoneNPCID = 0
|
| | | zoneID = GameLogic_CrossDemonKing.GetCurFBLineZoneID()
|
| | |
|