From 223d88c4b42d4541ed743b83cce2bbd4e1bdac59 Mon Sep 17 00:00:00 2001
From: hxp <ale99527@vip.qq.com>
Date: 星期五, 04 一月 2019 21:06:29 +0800
Subject: [PATCH] 5424 【后端】【1.4】跨服竞技场开发(屏蔽部分日志)

---
 ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/NPC/NPCCommon.py |  264 ++++++++++++++++++++++++++++++++++++++++------------
 1 files changed, 202 insertions(+), 62 deletions(-)

diff --git a/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/NPC/NPCCommon.py b/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/NPC/NPCCommon.py
index c6753db..74b8512 100644
--- a/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/NPC/NPCCommon.py
+++ b/ServerPython/ZoneServerGroup/map1_8G/MapServer/MapServerData/Script/NPC/NPCCommon.py
@@ -24,7 +24,7 @@
 import SkillShell
 import BuffSkill
 import BaseAttack
-import PlayerTruck
+import ChNetSendPack
 import SkillCommon
 import AttackCommon
 import ItemControler
@@ -47,7 +47,7 @@
 import BossHurtMng
 import PlayerSuperMarket
 import GameLogic_FamilyInvade
-#import GameLogic_MunekadoTrial
+import GameLogic_GatherSoul
 import FormulaControl
 import PlayerMagicWeapon
 import PlayerBossReborn
@@ -159,6 +159,11 @@
     # 根据平均等级
     elif lvStrengthenType == 1:
         strengthenLV = gameFB.GetGameFBDictByKey(ChConfig.Def_FB_NPCStrengthenAverageLV)
+    # 根据按成长等级的上下限随机
+    elif lvStrengthenType == 4:
+        randMinLV = gameFB.GetGameFBDictByKey(ChConfig.Def_FB_NPCStrengthenMinLV)
+        randMaxLV = gameFB.GetGameFBDictByKey(ChConfig.Def_FB_NPCStrengthenMaxLV)
+        strengthenLV = random.randint(randMinLV, randMaxLV)
         
     if strengthenIpyData.GetCmpNPCBaseLV():
         strengthenLV = max(strengthenLV, curNPC.GetLV())
@@ -209,6 +214,62 @@
             curNPC.Notify_HPEx()
             curNPC.Notify_MaxHPEx()
             #GameWorld.DebugLog("    aftHP=%s,aftMaxHP=%s" % (aftHP, aftMaxHP))
+    
+    # 机器人复活初始化给技能
+    if isReborn and curNPC.GetType() == ChConfig.ntRobot:
+        __OnFBRobotReborn(curNPC, strengthenLV)
+        
+    return
+
+def __OnFBRobotReborn(curNPC, npcLV):
+    tick = GameWorld.GetGameWorld().GetTick()
+    lineID = GameWorld.GetGameWorld().GetLineID()
+    objID = curNPC.GetID()
+    jobSkillDict = IpyGameDataPY.GetFuncEvalCfg("FBRobotCfg", 1)
+    robotJob = random.choice(jobSkillDict.keys())
+    lineRobotJobDict = PyGameData.g_fbRobotJobDict.get(lineID, {})
+    lineRobotJobDict[objID] = robotJob
+    PyGameData.g_fbRobotJobDict[lineID] = lineRobotJobDict
+    skillInfoDict = jobSkillDict[robotJob]
+    skillIDList = []
+    for skillInfo, needLV in skillInfoDict.items():
+        if npcLV < needLV:
+            continue
+        if isinstance(skillInfo, int):
+            skillIDList.append(skillInfo)
+        else:
+            skillIDList += list(skillInfo)
+    GameWorld.DebugLog("给机器人NPC技能: objID=%s,robotJob=%s,npcLV=%s, %s" % (objID, robotJob, npcLV, skillIDList))
+    skillManager = curNPC.GetSkillManager()
+    for skillID in skillIDList:
+        skillManager.LearnSkillByID(skillID)
+    playerManager = GameWorld.GetMapCopyPlayerManager()
+    for index in xrange(playerManager.GetPlayerCount()):
+        curPlayer = playerManager.GetPlayerByIndex(index)
+        if not curPlayer:
+            continue
+        FBLogic.DoFBHelp(curPlayer, tick)
+    return
+
+
+def __DoGiveVSPlayerNPCSkill(curNPC, job, npcLV):
+    skillManager = curNPC.GetSkillManager()
+    jobSkillDict = IpyGameDataPY.GetFuncEvalCfg("XMZZRobotSkill", 1)
+    if job not in jobSkillDict:
+        return
+    skillInfoDict = jobSkillDict[job]
+    #{1:{(100, 101, 102, 103):1, 50000:100, 50100:200, 50400:300}, 2:{(200, 201, 202, 203):1, 55000:100, 55100:200, 55200:300}}
+    skillIDList = []
+    for skillInfo, needLV in skillInfoDict.items():
+        if npcLV < needLV:
+            continue
+        if isinstance(skillInfo, int):
+            skillIDList.append(skillInfo)
+        else:
+            skillIDList += list(skillInfo)
+    GameWorld.DebugLog("给NPC技能: job=%s,npcLV=%s, %s" % (job, npcLV, skillIDList))
+    for skillID in skillIDList:
+        skillManager.LearnSkillByID(skillID)
     return
 
 def GetNPCStrengthenAttrDict(npcID, strengthenLV=0, strengthenPlayerCnt=0, strengthenIpyData=None):
@@ -224,7 +285,7 @@
     
     attrDict = {}
     paramDict = attrStrengthenInfo[NPCAttr_ParamDict] # 过程参数公式字典
-    attrStrengthenList = attrStrengthenInfo[NPCAttr_AttrStrengthenList] # 属性成长公式字典
+    attrStrengthenDict = attrStrengthenInfo[NPCAttr_AttrStrengthenList] # 属性成长公式字典
     playerCntCoefficient = attrStrengthenInfo[NPCAttr_PlayerCntCoefficient] # 人数系数
     npcIDPlayerCntCoefficient = attrStrengthenInfo[NPCAttr_NPCPlayerCntCoefficient] # 特殊NPC人数系数
     baseMaxHP = npcData.GetHPEx() * ShareDefine.Def_PerPointValue + npcData.GetHP()
@@ -287,9 +348,10 @@
                                                                     paramDict["AtkReplyCoefficient"])) # 怪物攻击回复调整值
         MonterHurt = eval(FormulaControl.GetCompileFormula("NPCParam_MonterHurt", paramDict["MonterHurt"])) # 怪物固定伤害
         LostHPPerSecond = eval(FormulaControl.GetCompileFormula("NPCParam_LostHPPerSecond", paramDict["LostHPPerSecond"])) # 玩家每秒掉血量
-        
+        LVStrengthenMark = strengthenIpyData.GetLVStrengthenMark()
+        attrStrengthenList = attrStrengthenDict.get(LVStrengthenMark, [])
         for attrKey, strengthenFormat in attrStrengthenList:
-            strengthenValue = int(eval(FormulaControl.GetCompileFormula("NPCStrengthen_%s" % attrKey, strengthenFormat)))
+            strengthenValue = int(eval(FormulaControl.GetCompileFormula("NPCStrengthen_%s_%s" % (attrKey,LVStrengthenMark), strengthenFormat)))
             #GameWorld.DebugLog("    %s=%s" % (attrKey, strengthenValue))
             locals()[attrKey] = strengthenValue # 创建该属性局部变量作为参数提供给后面属性计算时用
             attrDict[attrKey] = strengthenValue
@@ -335,7 +397,7 @@
     return attrDict
 
 def GiveKillNPCDropPrize(curPlayer, mapID, npcCountDict, exp_rate=None, mailTypeKey=None, isMail=False, 
-                         extraItemList=[], prizeMultiple=1, dropItemMapInfo=[]):
+                         extraItemList=[], prizeMultiple=1, dropItemMapInfo=[], curGrade=0):
     '''给玩家击杀NPC掉落奖励
     @param mapID: 击杀的NPC所在地图ID,注意次地图并不一定是玩家当前地图
     @param npcCountDict: 执行单次时所击杀的npc数量字典 {npcID:count, ...}
@@ -375,7 +437,7 @@
         # 掉落有概率因素,需多次执行
         for dCount in xrange(1, totalCount + 1):
             isKillCountDropEquipEx = dCount == 1 # 同一只NPC一次处理中多次击杀的情况,只算一次附加装备处理
-            dropInfo = GetNPCDropInfo(curPlayer, mapID, npcID, isKillCountDropEquipEx=isKillCountDropEquipEx)
+            dropInfo = GetNPCDropInfo(curPlayer, mapID, npcID, isKillCountDropEquipEx=isKillCountDropEquipEx, curGrade=curGrade)
             if not dropInfo:
                 continue
             dropIDList, dropIDBindDict, dropMoneyCnt, moneyValue = dropInfo
@@ -690,7 +752,7 @@
                            % (npcID, killCount, dropIDCountDict, dropIDBindDict, dropMoney), playerID)
     return dropIDCountDict, dropIDBindDict, dropMoney
 
-def GetNPCDropInfo(dropPlayer, mapID, npcID, ownerPlayerList=[], ipyDrop=None, isSingle=True, isKillCountDropEquipEx=True):
+def GetNPCDropInfo(dropPlayer, mapID, npcID, ownerPlayerList=[], ipyDrop=None, isSingle=True, isKillCountDropEquipEx=True, curGrade=0):
     '''获取NPC掉落信息, 击杀及扫荡通用,调用该函数获得掉落信息,然后再看掉落地板上还是直接放入背包
         @param dropPlayer: 用于判断调用相关用的玩家示例,该玩家并不一定是击杀者,只是按一定规则设定的掉落判断依据的玩家
                             如队伍,取等级最大的玩家,该玩家并不一定是击杀者
@@ -782,7 +844,7 @@
     indepRateDoCnt = ipyDrop.GetIndepRateDoCnt()
     if indepRateDoCnt:
         indepRateDoCnt = __GetNPCDropDoCountChange(indepRateDoCnt, doCountRate + equipDropDoCountPlus, doCountAdd)
-        dropEquipInfoList += __GetNPCIndepRateEquipDrop(ipyDrop, indepRateDoCnt, equipDropRatePlus)
+        dropEquipInfoList += __GetNPCIndepRateEquipDrop(ipyDrop, indepRateDoCnt, equipDropRatePlus, curGrade)
         
     #GameWorld.DebugLog("阶,颜色,部位集合key,dropEquipInfoList=%s" % (dropEquipInfoList))
     placeDict = IpyGameDataPY.GetFuncCfg("EquipDropPartSets", 1)
@@ -878,7 +940,7 @@
     fbGradeColorStarRateDict = IpyGameDataPY.GetFuncEvalCfg("FBGradeEquipDropRate", 2) # 评级影响品质星级概率 {npcID:{(颜色,星级):[D级影响概率, ..., S级影响概率], ...}, ...}
     if npcID in fbGradeColorStarRateDict:
         gradeColorStarRateDict = fbGradeColorStarRateDict[npcID]
-        curGrade = GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
+        curGrade = curGrade if curGrade else GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
         
     colorDropCntDict = {} # 装备颜色已经掉落数 {颜色:数量, ...}
     colorMaxDropCntDict = ipyDrop.GetIndepRateMaxDropCount() # {颜色:上限数量,...}
@@ -953,7 +1015,7 @@
         fbGradePriItemIDDropDict = IpyGameDataPY.GetFuncEvalCfg("FBGradeEquipDropRate", 3)
         if npcID in fbGradePriItemIDDropDict:
             gradePriItemIDDropDict = fbGradePriItemIDDropDict[npcID]
-            curGrade = GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
+            curGrade = curGrade if curGrade else GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
             priDropInfoList = gradePriItemIDDropDict.get(curGrade, [])
             priDropIDList = []
             for priItemID, priItemCount in priDropInfoList:
@@ -1107,6 +1169,8 @@
     # 1. 职业物品ID集合
     job = curPlayer.GetJob()
     JobItemDropSets = IpyGameDataPY.GetFuncCfg("JobItemDropSets", 1) # {物品ID集合key:[职业顺序物品ID列表], ...}
+    itemDropSets = IpyGameDataPY.GetFuncCfg("JobItemDropSets", 2) # {物品ID集合key:[随机物品ID列表], ...}
+    itemDropRateSets = IpyGameDataPY.GetFuncCfg("JobItemDropSets", 3) # {物品ID集合key:[随机物品ID饼图列表], ...}
     ItemKeyMaxDropCountDict = ipyDrop.GetItemKeyMaxDropCount() # {物品ID集合key:随机次数,...}
     
     #     1.1 只掉本职业的
@@ -1137,20 +1201,14 @@
     #     1.2 随机掉落一个
     ItemKeyDropRateDict = ipyDrop.GetItemKeyDropRate() # {物品ID集合key:概率, ...}, 随机掉一个,优先级低
     if ItemKeyDropRateDict:
-        for jobItemKey, dropRate in ItemKeyDropRateDict.items():
-            if jobItemKey not in JobItemDropSets:
-                continue
-            jobItemList = JobItemDropSets[jobItemKey]
-            if len(jobItemList) < job:
-                GameWorld.ErrLog("职业物品集合key没有配置对应职业ID: npcID=%s,jobItemKey=%s,job=%s" % (npcID, jobItemKey, job))
-                continue
+        for itemKey, dropRate in ItemKeyDropRateDict.items():
             # 在只掉本职业里的不处理
-            if jobItemKey in ItemKeyDropRateJobDict:
+            if itemKey in ItemKeyDropRateJobDict:
                 continue
             mustDropCount = dropRate / Def_NPCMaxDropRate
             dropRate = dropRate % Def_NPCMaxDropRate # 基础概率
             canDropCount = mustDropCount
-            doCnt = ItemKeyMaxDropCountDict.get(jobItemKey, 1) # 默认1个
+            doCnt = ItemKeyMaxDropCountDict.get(itemKey, 1) # 默认1个
             doCnt = __GetNPCDropDoCountChange(doCnt, doCountRate, doCountAdd)
             for _ in xrange(doCnt):
                 if not GameWorld.CanHappen(dropRate, maxRate=Def_NPCMaxDropRate):
@@ -1158,9 +1216,20 @@
                 canDropCount += 1
                 
             for _ in xrange(canDropCount):
-                randJobItemID = random.choice(jobItemList)
-                dropItemIDList.append(randJobItemID)
-                #GameWorld.DebugLog("掉落随机职业指定物品ID: jobItemKey=%s,randJobItemID=%s" % (jobItemKey, randJobItemID))
+                if itemKey in itemDropRateSets:
+                    randItemRateList = itemDropRateSets[itemKey]
+                    randItemID = GameWorld.GetResultByRandomList(randItemRateList)
+                    #GameWorld.DebugLog("掉落饼图物品ID: itemKey=%s,randItemRateList=%s,randItemID=%s" % (itemKey, randItemRateList, randItemID))
+                elif itemKey in itemDropSets:
+                    randItemList = itemDropSets[itemKey]
+                    randItemID = random.choice(randItemList)
+                    #GameWorld.DebugLog("掉落随机物品ID: itemKey=%s,randItemList=%s,randItemID=%s" % (itemKey, randItemList, randItemID))
+                else:
+                    continue
+                if not randItemID:
+                    continue
+                dropItemIDList.append(randItemID)
+                #GameWorld.DebugLog("掉落随机指定物品ID: itemKey=%s,randItemID=%s" % (itemKey, randItemID))
                 
     # 2. 指定掉落ID处理, 受全局设定影响
     itemIDDropRateDict = ipyDrop.GetItemIDDropRate() # {物品ID:概率, ...}
@@ -1227,17 +1296,17 @@
         GameWorld.GetPlayerManager().GameServer_QueryPlayerResult(0, 0, 0, "GlobalDropRate", msgInfo, len(msgInfo))
          
     # 4. 指定全服击杀次数必掉,算额外掉落
-    globalKillDropDict = IpyGameDataPY.GetFuncEvalCfg("GlobalDropCD", 2) # {NPCID:{击杀次数:[是否本职业, [物品ID, ...], [随机物品ID, ...]]}, ...}
+    globalKillDropDict = IpyGameDataPY.GetFuncEvalCfg("GlobalDropCD", 2) # {NPCID:{击杀次数:[是否本职业, {物品ID:个数, ...}, [[随机物品ID,个数], ...]]}, ...}
     if npcID in globalKillDropDict:
         killCountDropDict = globalKillDropDict[npcID]
         updNPCKilledCount = min(gw.GetGameWorldDictByKey(ShareDefine.Def_Notify_WorldKey_NPCKilledCount % npcID) + 1, ShareDefine.Def_UpperLimit_DWord)
-        GameWorld.DebugLog("更新全服击杀次数: %s" % updNPCKilledCount)
+        GameWorld.Log("更新全服击杀次数:npcID=%s, %s" % (npcID, updNPCKilledCount))
         # 通知GameServer记录
         msgInfo = str([npcID, updNPCKilledCount])
         GameWorld.GetPlayerManager().GameServer_QueryPlayerResult(0, 0, 0, "GlobalKillCount", msgInfo, len(msgInfo))
         if updNPCKilledCount in killCountDropDict:
-            isJobLimit, itemIDList, randItemIDList = killCountDropDict[updNPCKilledCount]
-            for itemID in itemIDList:
+            isJobLimit, itemIDCountDict, randItemIDCountList = killCountDropDict[updNPCKilledCount]
+            for itemID, itemCount in itemIDCountDict.items():
                 if isJobLimit:
                     itemData = GameWorld.GetGameData().GetItemByTypeID(itemID)
                     if not itemData:
@@ -1247,12 +1316,12 @@
                         # 非本职业可用,不掉落
                         GameWorld.DebugLog("全服击杀次数必掉,非本职业可用,不掉落! itemID=%s" % itemID)
                         continue
-                dropItemIDList.append(itemID)
-                GameWorld.DebugLog("全服击杀次数必掉物品: itemID=%s" % itemID)
-            if randItemIDList:
+                dropItemIDList += [itemID] * itemCount
+                GameWorld.Log("全服击杀次数必掉物品: itemID=%s,itemCount=%s" % (itemID, itemCount))
+            if randItemIDCountList:
                 if isJobLimit:
                     randJobItemList = []
-                    for rItemID in randItemIDList:
+                    for rItemID, rItemCount in randItemIDCountList:
                         itemData = GameWorld.GetGameData().GetItemByTypeID(rItemID)
                         if not itemData:
                             continue
@@ -1261,12 +1330,12 @@
                             # 非本职业可用,不掉落
                             GameWorld.DebugLog("全服击杀次数必掉随机,非本职业可用,不掉落! rItemID=%s" % rItemID)
                             continue
-                        randJobItemList.append(rItemID)
-                    randItemID = random.choice(randJobItemList)
+                        randJobItemList.append([rItemID, rItemCount])
+                    randItemID, randItemCount = random.choice(randJobItemList)
                 else:
-                    randItemID = random.choice(randItemIDList)
-                dropItemIDList.append(randItemID)
-                GameWorld.DebugLog("全服击杀次数必掉随机物品: randItemID=%s" % randItemID)
+                    randItemID, randItemCount = random.choice(randItemIDCountList)
+                dropItemIDList += [randItemID] * randItemCount
+                GameWorld.Log("全服击杀次数必掉随机物品: randItemID=%s,randItemCount=%s" % (randItemID, randItemCount))
                 
     return dropItemIDList
 
@@ -1335,7 +1404,7 @@
     #GameWorld.DebugLog("饼图装备掉落结果: doCnt=%s, %s" % (doCnt, dropEquipInfoList))
     return dropEquipInfoList
 
-def __GetNPCIndepRateEquipDrop(ipyDrop, doCnt, equipDropPlus):
+def __GetNPCIndepRateEquipDrop(ipyDrop, doCnt, equipDropPlus, curGrade=0):
     ## 获取NPC独立掉率装备掉落信息
     npcID = ipyDrop.GetNPCID()
     indepRateDict = ipyDrop.GetIndepRateDrop() # {(阶,颜色,部位集合key):概率,...}
@@ -1346,7 +1415,7 @@
     fbGradeColorRateDict = IpyGameDataPY.GetFuncEvalCfg("FBGradeEquipDropRate", 1) #{npcID:{颜色:[D级影响概率, ..., S级影响概率], ...}, ...}
     if npcID in fbGradeColorRateDict:
         gradeColorRateDict = fbGradeColorRateDict[npcID]
-        curGrade = GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
+        curGrade = curGrade if curGrade else GameWorld.GetGameFB().GetGameFBDictByKey(ChConfig.Def_FB_Grade)
         
     #colorDropCntDict = {} # 装备颜色已经掉落数 {颜色:数量, ...}
     dropEquipInfoList = []
@@ -1986,9 +2055,8 @@
         # 设置npc死亡及自身处理
         SetDeadEx(summonNPC)
         
-    if curNPC.GetGameObjType() == IPY_GameWorld.gotNPC and \
-        curNPC.GetGameNPCObjType() == IPY_GameWorld.gnotSummon:
-        FBLogic.DoFB_SummonNPCDead(curNPC)
+    if curNPC.GetGameObjType() == IPY_GameWorld.gotNPC:
+        FBLogic.DoFB_NPCDead(curNPC)
     
     summonPlayerID = curNPC.GetDictByKey(ChConfig.Def_NPC_Dict_SummonMapNPCPlayerID)
     if summonPlayerID > 0:
@@ -2019,7 +2087,12 @@
     AttackCommon.ClearTeamPlayerHurtValue(curNPC)
     # 清除自定义伤血列表
     #BossHurtMng.ClearHurtValueList(curNPC)
-
+    if curNPC.GetType() == ChConfig.ntRobot:
+        lineID = GameWorld.GetGameWorld().GetLineID()
+        lineRobotJobDict = PyGameData.g_fbRobotJobDict.get(lineID, {})
+        lineRobotJobDict.pop(curNPC.GetID(), 0)
+        PyGameData.g_fbRobotJobDict[lineID] = lineRobotJobDict
+        
     # C++设置npc死亡
     curNPC.SetDead(curNPC.GetDictByKey(ChConfig.Def_NPCDead_Reason),
                    curNPC.GetDictByKey(ChConfig.Def_NPCDead_KillerType),
@@ -2382,7 +2455,7 @@
     def GetIsBossView(self):
         # 主动视野情况,GetIsBoss 0 1 4 为普通NPC视野(有视野范围配置,但去除视野刷新),其他为BOSS类视野有刷新
         curNPC = self.__Instance
-        if not ChConfig.IsGameBoss(curNPC) and not GetFaction(curNPC):
+        if not ChConfig.IsGameBoss(curNPC) and not GetFaction(curNPC) and curNPC.GetType() != ChConfig.ntRobot:
             return False
         
         return True
@@ -3305,7 +3378,12 @@
         #范围校验
         posMapX = posMap.GetPosX()
         posMapY = posMap.GetPosY()
-        posMapArea = posMap.GetArea()
+        
+        if curNPC.GetType() == IPY_GameWorld.ntFunctionNPC: #功能NPC
+            posMapArea = 0
+        else:
+            posMapArea = posMap.GetArea()
+        
         #获取范围内一点可以移动的点
         posX, poxY = GameMap.GetNearbyPosByDis(posMapX, posMapY, posMapArea)
         
@@ -3654,7 +3732,7 @@
     #  @remarks 刷新NPC属性
     def RefreshNPCAttrState(self, canSyncClient=True, isReborn=False):
         curNPC = self.__Instance
-        curNPCMaxHP_Before = GameObj.GetMaxHP(curNPC)
+        #curNPCMaxHP_Before = GameObj.GetMaxHP(curNPC)
         #清空NPC战斗属性
         curNPC.ClearBattleEffect()
         #--------------------------------------------
@@ -3691,6 +3769,28 @@
             
         return
     
+    def SetHelpBattleRobotRebornAttr(self, fightPower):
+        '''助战机器人只设置血量属性
+                        血量算法,(助战玩家=助战机器人):每个副本配置伤害*(助战玩家战力/副本规定战力)*系数值  系数值暂定为50
+        '''
+        curNPC = self.__Instance
+        mapID = FBCommon.GetRecordMapID(GameWorld.GetMap().GetMapID())
+        funcLineID = FBCommon.GetFBPropertyMark()
+        ipyData = IpyGameDataPY.GetIpyGameData("FBHelpBattle", mapID, funcLineID)
+        if not ipyData:
+            return
+        
+        SetSuppressFightPower(curNPC, fightPower)
+        fbFightPower = ipyData.GetFightPowerMin()
+        baseHurt = ipyData.GetRobotBaseHurt()
+        hpCoefficient = ipyData.GetRobotHPCoefficient()
+        maxHP = int(eval(IpyGameDataPY.GetFuncCompileCfg("HelpBattleRobot", 2)))
+        GameWorld.DebugLog("设置助战机器人属性: objID=%s,fightPower=%s,maxHP=%s" % (curNPC.GetID(), fightPower, maxHP))
+        GameObj.SetMaxHP(curNPC, maxHP)
+        GameObj.SetHP(curNPC, maxHP)
+        curNPC.Notify_HPEx()
+        curNPC.Notify_MaxHPEx()
+        return
     
     # NPC移动速度特殊处理,只处理百分比不能处理固定值 
     # 因为 ChConfig.TYPE_Calc_AttrSpeed 非服务端移动速度,偷懒处理法
@@ -3701,11 +3801,13 @@
         if not speedPer:
             if curNPC.GetDictByKey(ChConfig.Def_NPC_Dict_SpeedPer):
                 curNPC.SetDict(ChConfig.Def_NPC_Dict_SpeedPer, 0)
-            return
-        speed = int(curNPC.GetSpeed() * (ShareDefine.Def_MaxRateValue) / max(100.0, float(ShareDefine.Def_MaxRateValue + speedPer)))
-        
-        curNPC.SetSpeed(speed)
-        curNPC.SetDict(ChConfig.Def_NPC_Dict_SpeedPer, speedPer)
+        else:
+            speed = int(curNPC.GetSpeed() * (ShareDefine.Def_MaxRateValue) / max(100.0, float(ShareDefine.Def_MaxRateValue + speedPer)))
+            curNPC.SetSpeed(speed)
+            curNPC.SetDict(ChConfig.Def_NPC_Dict_SpeedPer, speedPer)
+        if GameWorld.GetMap().GetMapID() == ChConfig.Def_FBMapID_GatherSoul:
+            #目前只在聚魂副本里通知
+            NPCSpeedChangeNotify(curNPC, curNPC.GetSpeed())
         return
     
     
@@ -3715,7 +3817,6 @@
     #  @remarks 刷新NPC行为属性
     def RefreshNPCActionState(self):
         curNPC = self.__Instance
-        
         OperControlManager.ClearObjActionState(curNPC)
         
         #根据BUFF 加上状态
@@ -3919,7 +4020,7 @@
                 return moneyID
         return moneyItemList[-1][1]
     
-    def __NPCSpecialDropItem(self, ownerPlayerList, ipyDrop):
+    def __NPCSpecialDropItem(self, dropPlayer, ownerPlayerList, ipyDrop):
         '''特殊掉落 (私有特殊掉落 + 击杀次数特殊掉落), 支持摸怪
         @return: None
         @return: [[ownerPlayer, itemID, isBind, isDropInItemPack], ...]
@@ -3927,6 +4028,12 @@
         curNPC = self.__Instance
         npcID = curNPC.GetNPCID()
         specDropItemList = []
+        
+        playerLV = dropPlayer.GetLV()
+        maxDropLV = ipyDrop.GetMaxDropLV()
+        if maxDropLV and playerLV > maxDropLV:
+            GameWorld.DebugLog("超过最大可掉落等级,不掉落物品,特殊掉落!npcID=%s,playerLV(%s) > maxDropLV(%s)" % (npcID, playerLV, maxDropLV))
+            return specDropItemList
         
         # 私有掉落
         fbGradePriItemIDDropDict = IpyGameDataPY.GetFuncEvalCfg("FBGradeEquipDropRate", 3)
@@ -4027,7 +4134,7 @@
         mapID = FBCommon.GetRecordMapID(mapID)
         isGameBoss = ChConfig.IsGameBoss(curNPC)
         if isGameBoss:
-            GameWorld.Log("NPC开始掉落: npcID=%s,dropPlayerID=%s" % (npcID, dropPlayer.GetPlayerID()))
+            GameWorld.Log("NPC开始掉落: npcID=%s,dropPlayerID=%s" % (npcID, dropPlayer.GetPlayerID()), dropPlayer.GetPlayerID())
         if mapID == ChConfig.Def_FBMapID_MunekadoTrial:
             return
         ipyDrop = GetNPCDropIpyData(npcID)
@@ -4051,13 +4158,17 @@
             dropIDList += [moneyID] * dropMoneyCnt
             
         specItemSign = "SpecItem"
-        playerSpecDropList = self.__NPCSpecialDropItem(ownerPlayerList, ipyDrop) # 特殊掉落 [[ownerPlayer, itemID, isBind, isDropInItemPack], ...]  私有特殊掉落 + 击杀次数特殊掉落
+        playerSpecDropList = self.__NPCSpecialDropItem(dropPlayer, ownerPlayerList, ipyDrop) # 特殊掉落 [[ownerPlayer, itemID, isBind, isDropInItemPack], ...]  私有特殊掉落 + 击杀次数特殊掉落
         dropIDList += [specItemSign] * len(playerSpecDropList)
         
         if len(dropIDList) > 5:
             #打乱物品顺序
             random.shuffle(playerSpecDropList)
             random.shuffle(dropIDList)
+            
+        if not dropIDList and isGameBoss:
+            GameWorld.ErrLog("Boss没有掉落: dropPlayerLV=%s,ipyWorldLV=%s,maxDropLV=%s" 
+                             % (dropPlayer.GetLV(), ipyDrop.GetMaxWorldLV(), ipyDrop.GetMaxDropLV()), dropPlayer.GetPlayerID())
             
         gameMap = GameWorld.GetMap()
         dropPosX, dropPosY = curNPC.GetPosX(), curNPC.GetPosY() # 以NPC为中心点开始掉落
@@ -4088,9 +4199,16 @@
                 ownerType, ownerID = hurtType, hurtID
                 itemCnt = moneyValue if itemID == moneyID else 1
                 isBind = dropIDBindDict.get(itemID, 1)
-                
+            
             curItem = self.__CreateDropItem(curNPC, itemID, itemCnt, isBind)
             if not curItem:
+                continue
+            
+            if mapID == ChConfig.Def_FBMapID_GatherSoul:#聚魂副本特殊处理
+                GameLogic_GatherSoul.KillGatherSoulNPCDropAward(itemID, itemCnt, isBind)
+                dropItemDataStr = ChItem.GetMapDropItemDataStr(curItem)
+                self.SendVirtualItemDrop(ownerPlayer, itemID, resultX, resultY, dropItemDataStr)
+                curItem.Clear()
                 continue
             
             if isDropInItemPack:
@@ -4100,17 +4218,22 @@
                 if ItemControler.DoLogic_PutItemInPack(ownerPlayer, curItem, True, True,
                                                        event=["NPCDrop", False, {"npcID":npcID}]):
                     #通知客户端
-                    vItemDrop = ChPyNetSendPack.tagMCVirtualItemDrop()
-                    vItemDrop.ItemTypeID = itemID
-                    vItemDrop.PosX = resultX
-                    vItemDrop.PosY = resultY
-                    vItemDrop.UserData = dropItemDataStr
-                    vItemDrop.UserDataLen = len(vItemDrop.UserData)
-                    NetPackCommon.SendFakePack(ownerPlayer, vItemDrop)
+                    self.SendVirtualItemDrop(ownerPlayer, itemID, resultX, resultY, dropItemDataStr)
+                    
             else:
                 self.__MapCreateItem(curItem, resultX, resultY, ownerType, ownerID)
         return
     
+    def SendVirtualItemDrop(self, player, itemID, posX, posY, userDataStr):
+        #通知客户端
+        vItemDrop = ChPyNetSendPack.tagMCVirtualItemDrop()
+        vItemDrop.ItemTypeID = itemID
+        vItemDrop.PosX = posX
+        vItemDrop.PosY = posY
+        vItemDrop.UserData = userDataStr
+        vItemDrop.UserDataLen = len(vItemDrop.UserData)
+        NetPackCommon.SendFakePack(player, vItemDrop)
+        return
     #---------------------------------------------------------------------
     ## NPC被杀死逻辑处理
     #  @param self 类实例
@@ -4511,6 +4634,13 @@
                 hurtID = killerDict.keys()[0]
                 if isGameBoss:
                     GameWorld.Log("    归属默认玩家, npcID=%s,playerID=%s" % (npcID, hurtID))
+            elif GameWorld.GetMap().GetMapID() == ChConfig.Def_FBMapID_GatherSoul:
+                player = FBCommon.GetCurSingleFBPlayer()
+                if player:
+                    hurtID = player.GetPlayerID()
+                    killerDict[hurtID] = player
+                    hurtType = ChConfig.Def_NPCHurtTypePlayer
+                    #GameWorld.Log("    聚魂副本归属默认玩家, npcID=%s,playerID=%s" % (npcID, hurtID))
                 
         return killerDict, killTeam, hurtType, hurtID
     
@@ -5971,3 +6101,13 @@
     GameWorld.DebugLog("通知GameServer地图Boss分流信息: mapID=%s,lineID=%s,shuntPlayerDict=%s" % (mapID, lineID, shuntPlayerDict), lineID)
     return
 
+def NPCSpeedChangeNotify(curNPC, speed):
+    ##通知NPC速度
+    sendPack = ChNetSendPack.tagObjInfoRefresh()
+    sendPack.Clear()
+    sendPack.ObjID = curNPC.GetID()
+    sendPack.ObjType = curNPC.GetGameObjType()
+    sendPack.RefreshType = IPY_GameWorld.CDBPlayerRefresh_Speed
+    sendPack.Value = speed
+    curNPC.NotifyAll(sendPack.GetBuffer(), sendPack.GetLength())
+    return

--
Gitblit v1.8.0