Пример #1
0
        public void analyze(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            WarAnimParam warParam = msg as WarAnimParam;

            if (warParam != null && warParam.described != null)
            {
                SelfDescribed des = warParam.described;

                int castor   = des.srcEnd.param1;
                int sufferer = des.srcEnd.param2;

                ServerNPC bCast = npcMgr.GetNPCByUniqueID(castor);
                ServerNPC bSuf  = npcMgr.GetNPCByUniqueID(sufferer);

                if (bCast != null && bSuf != null)
                {
                    Pair pair = new Pair()
                    {
                        CastorNum = bCast.data.num,
                        KilledNum = bCast.data.num,
                    };
                    killingInfo.Add(pair);
                }
            }
        }
Пример #2
0
        void HookNpcOnAttack(WarAnimParam warParam, WarServerNpcMgr npcMgr)
        {
            ServerNPC caster = npcMgr.GetNPCByUniqueID(warParam.Sender);
            ServerNPC suffer = npcMgr.GetNPCByUniqueID(warParam.Receiver);

            SufferHookEffect hookSuf = warMgr.sufMgr.getImplement <SufferHookEffect>(EffectOp.HookNpc);

            hookSuf.Suffer(caster, suffer, warParam.described, npcMgr);
        }
Пример #3
0
        public void OnHappen(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            if (msg != null)
            {
                ServerNPC castor = npcMgr.GetNPCByUniqueID(msg.Sender);
                ServerNPC target = npcMgr.GetNPCByUniqueID(msg.Receiver);

                List <ServerNPC> itor = new List <ServerNPC>();
                itor.Add(target);

                warMgr.triMgr.trigCastor.cast(castor, itor, cfg);
            }
        }
Пример #4
0
        //收到伤害
        protected void BeInjured(WarTarAnimParam param)
        {
            if (param == null)
            {
                ConsoleEx.DebugWarning("BeInjured :: BeInjured :: param is null");
                return;
            }


            if (param.described != null)
            {
                SufferInjureEffect sufInjury = warServerMgr.sufMgr.getImplement <SufferInjureEffect>(EffectOp.Injury);
                SelfDescribed      des       = param.described;

                //记录攻击自己的人的ID
                data.btData.atkerID = des.src;

                if (des.target == UniqueId && IsAlive)
                {
                    ServerNPC caster = npcMgr.GetNPCByUniqueID(des.src);
                    sufInjury.Suffer(caster, this, des, npcMgr);
                    Dmg oneDmg = sufInjury.getHandled;

                    hpMsg.uniqueId = UniqueID;
                    hpMsg.deltaHp  = (int)oneDmg.dmgValue;
                    hpMsg.curHp    = data.rtData.curHp;
                    hpMsg.totalHp  = data.rtData.totalHp;
                    hpMsg.isDamage = true;
                    hpMsg.srcID    = des.src;
                    warServerMgr.realServer.proxyCli.NPChp(hpMsg);

//                    if (caster.UniqueID == npcMgr.ActiveHero.UniqueId)
//                    {
//                        if (OnHitByActiveHero != null)
//                        {
//                            Vector3 posIn2D = Vector3.zero;
//                            Vector3 posIn3D = transform.position;
//                            posIn3D.y += 3.5f;
//                            wmMgr.GetUIPos_Ref3DPos (posIn3D, ref posIn2D);
//                            OnHitByActiveHero ((int)oneDmg.dmgValue, true, oneDmg.isCritical, posIn2D);
//                        }
//                    }

                    //检查自己是否被杀
                    if (data.rtData.curHp <= 0)
                    {
                        BeKillded();
                    }
                }
            }
        }
Пример #5
0
        /// <summary>
        /// 触发条件满足,或者说感兴趣的事情发生了。
        /// 但是是不是要真的处理什么逻辑,还不一定
        /// </summary>
        /// <param name="msg">Message</param>
        /// <param name="npcMgr">Npc mgr.</param>
        public void OnHappen(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            checkList.Clear();
            WarAnimParam warParam = msg as WarAnimParam;

            if (warParam != null && warParam.described != null)
            {
                SelfDescribed des  = warParam.described;
                Pair          pair = new Pair();
                pair.castor = npcMgr.GetNPCByUniqueID(des.src);
                pair.target = npcMgr.GetNPCByUniqueID(des.target);

                checkList.Add(pair);
            }
        }
Пример #6
0
        void BulletNPCCreator(WarAnimParam warParam, WarServerNpcMgr npcMgr)
        {
            ServerNPC caster = npcMgr.GetNPCByUniqueID(warParam.Sender);
            ServerNPC suffer = npcMgr.GetNPCByUniqueID(warParam.Receiver);

            SelfDescribed des = new SelfDescribed()
            {
                src    = warParam.arg1,
                target = warParam.arg2,
            };

            SufferBulletEffect bulletSuf = warMgr.sufMgr.getImplement <SufferBulletEffect>(EffectOp.Bullet_NPC);

            bulletSuf.Suffer(caster, suffer, des, npcMgr);
        }
Пример #7
0
        public void OnHappen(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            WarAnimParam warParam = msg as WarAnimParam;

            if (warParam != null && warParam.described != null)
            {
                SelfDescribed described = warParam.described;
                if (described.srcEnd != null)
                {
                    ///
                    /// 每次被攻击几率对周围造成伤害
                    ///
                    int casterId = described.srcEnd.param1;
                    int sufferId = described.srcEnd.param2;

                    //不能自己打自己也反弹
                    if (sufferId == casterId)
                    {
                        return;
                    }

                    if (sufferId == HangUpNpcId)
                    {
                        //选择自己和目标
                        //目标也是自己
                        ServerNPC        castor  = npcMgr.GetNPCByUniqueID(sufferId);
                        List <ServerNPC> targets = new List <ServerNPC>();
                        targets.Add(castor);

                        warMgr.triMgr.trigCastor.cast(castor, targets, cfg);
                    }
                }
            }
        }
Пример #8
0
        //清理逻辑
        void clearDeadNpcStatus(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            WarAnimParam warMsg = msg as WarAnimParam;

            if (warMsg != null && warMsg.described != null)
            {
                int           deadNpcId = warMsg.described.srcEnd.param2;
                ServerNPC     npc       = npcMgr.GetNPCByUniqueID(deadNpcId);
                ServerLifeNpc life      = npc as ServerLifeNpc;
                if (life != null)
                {
                    life.curStatus = NpcStatus.None;

                    ///
                    /// ---- 解除挂载的Trigger ----
                    ///
                    WarServerManager.Instance.triMgr.RemoveAllTrigger(deadNpcId);

                    ///
                    /// ---- 解除挂载的Buff ----
                    ///
                    WarServerManager.Instance.bufMgr.rmAllBuff(deadNpcId);

                    //--- 解除仇恨信息 ----
                    life.clearHatred();
                }
            }
        }
Пример #9
0
        ExistFlag NPCToFlag(ServerNPC npc, WarServerNpcMgr npcMgr, LifeNPCType type)
        {
            ExistFlag tar1 = ExistFlag.None;
            ExistFlag tar2 = ExistFlag.None;

            switch (type)
            {
            case LifeNPCType.Hero:
                tar1 = ExistFlag.Hostile_Hero;
                tar2 = ExistFlag.Hostile_Hero_ATK_Self_Hero;
                break;

            case LifeNPCType.Summon:
                tar1 = ExistFlag.Hostile_Summoner;
                tar2 = ExistFlag.Hostile_Summoner_ATK_Self_Hero;
                break;

            case LifeNPCType.Soldier:
                tar1 = ExistFlag.Hostile_Minion;
                tar2 = ExistFlag.Hostile_Minion_ATK_Self_Hero;
                break;
            }


            ExistFlag toTest = ExistFlag.None;

            //没有攻击过的目标
            if (npc.TargetID == -1)
            {
                toTest = tar1;
            }
            else
            {
                ServerNPC targetNpc = npcMgr.GetNPCByUniqueID(npc.TargetID);
                if (targetNpc != null)
                {
                    ///
                    /// 发现目标是Hero,则会判定为攻击了英雄
                    ///
                    NPCConfigData tarCfg = targetNpc.data.configData;
                    if (tarCfg.type.check(LifeNPCType.Hero))
                    {
                        toTest = tar2;
                    }
                    else
                    {
                        toTest = tar1;
                    }
                }
                else
                {
                    toTest = tar1;
                }
            }

            return(toTest);
        }
Пример #10
0
        /// <summary>
        /// 获取挂载BUff的NPC
        /// </summary>
        /// <returns>The hang up.</returns>
        public ServerNPC getHangUp(RtBufData rtBf)
        {
                        #if DEBUG
            Utils.Assert(rtBf == null, "RtBufData is null when get Hang Up.");
                        #endif

            ServerNPC hangUp = npcMgr.GetNPCByUniqueID(rtBf.HangUpNpcID);
            return(hangUp);
        }
Пример #11
0
        ExistFlag toExistType(ServerNPC npc, WarServerNpcMgr npcMgr)
        {
            NPCConfigData cfg  = npc.data.configData;
            ExistFlag     flag = LifeNpcType2ExistFlag(cfg.type, cfg.bldType);

            if (flag == ExistFlag.Hero)
            {
                if (npc.TargetID != -1)
                {
                    ServerNPC npcTar = npcMgr.GetNPCByUniqueID(npc.TargetID);
                    if (npcTar != null)
                    {
                        flag = ExistFlag.HeroTar;
                    }
                }
            }

            return(flag);
        }
Пример #12
0
        public void Update(float delTime)
        {
            foreach (RtBufData buf in OnWork.Values)
            {
                if (buf != null)
                {
                    working.Add(buf);
                }
            }

            int workCnt = working.Count;

            if (workCnt > 0)
            {
                for (int i = 0; i < workCnt; ++i)
                {
                    RtBufData buf   = working[i];
                    bool      alive = buf.Update(delTime);
                    if (!alive)
                    {
                        rmBuff(buf.ID, buf.HangUpNpcID, true);
                    }

                    ///
                    /// 判定当前的是否是引导技能
                    ///
                    if (buf.canInterrupt)
                    {
                        //检测是否已被打断
                        ServerNPC     npc       = NpcMgr.GetNPCByUniqueID(buf.HangUpNpcID);
                        ServerLifeNpc life      = npc as ServerLifeNpc;
                        bool          interrupt = life.curStatus.AnySame(NpcStatus.Interrupt);
                        if (interrupt)
                        {
                            rmBuff(buf.ID, buf.HangUpNpcID);
                        }
                    }
                }
                working.Clear();
            }
        }
Пример #13
0
        /// <summary>
        /// 选择的规则是:
        ///  多目标判定规则
        /// 1. 判定施法者的状态
        /// 2. 判定施法者的上次目标,如果目标在攻击范围内,则选择为最优先目标
        /// 3. 判定施法的范围类型
        /// 4. 目标的状态
        /// 5. 根据施法的距离选择出目标
        /// 6. 根据血量选择出目标
        /// 7. 目标的优先级
        /// 8. 单体攻击敌方,并且有最高优先级的目标
        ///
        ///
        /// 单目标判定规则
        ///
        ///
        ///
        /// </summary>
        /// <returns><c>true</c>, if cast was caned, <c>false</c> otherwise.</returns>
        public IEnumerable <ServerNPC> Select(ServerNPC caster, RtSkData rtOne, Sight sight)
        {
            //枚举器
            IEnumerable <ServerNPC> itor = null, itor1 = null;

                        #if DEBUG
            Utils.Assert(caster == null, "Can't find target unless caster isn't null");
            Utils.Assert(rtOne == null, "Can't find target unless runtime skill isn't null");
                        #endif


            SkillConfigData skillCfg = rtOne.skillCfg;

            /// 视野范围 -- 决定索敌范围
            float CheckDistance = 0F;
            if (sight == Sight.NearSight)
            {
                CheckDistance = skillCfg.Distance;
            }
            else
            {
                CheckDistance = caster.data.rtData.seekRange;
            }

            bool castcan = true;
            //只有LifeNPC才检查施法者的状态
            //1. 判定施法者的状态
            ServerLifeNpc castlife = caster as ServerLifeNpc;
            if (castlife != null)
            {
                if (castlife.curStatus.AnySame(skillCfg.CasterStatusReject))
                {
                    //不可施法
                    castcan = false;
                }
            }

            if (castcan == false)
            {
                return(new List <ServerNPC>().AsEnumerable <ServerNPC>());
            }
            //能进入CD
            rtOne.EnterCD();

            ///
            /// 3. 判定施法的范围类型 .
            /// 单体和AOE都需要在技能配置里选择出目标 , 再次到Effect里面选择目标。 -- 叫做前置判定
            /// 方向性则不需要选择目标,该类型的技能可对空地释放,再次到EffectTarget的目标是skill的目标 -- 叫做后置判定
            ///

            TargetClass rtTargetCls = skillCfg.SkillTarget;

            if (skillCfg.RangeType == RangeClass.Direction)
            {
                //后置判定
                return(new List <ServerNPC>().AsEnumerable <ServerNPC>());
            }

            bool isMultiTarget = skillCfg.RangeType != RangeClass.SingleTarget;
            bool isNoPriority  = skillCfg.TargetPriority == SkTargetPriority.NonePriority;
            bool isTargetSelf  = rtTargetCls.AnySame(TargetClass.Self);
            //单目标
            ServerNPC singlePriority = null;

            LifeNPCType type = skillCfg.TargetType.toPositive();
            ///
            /// 是否为多目标的战斗, 或者是没有优先级的单目标
            ///
            if (isMultiTarget || isNoPriority || isTargetSelf)
            {
                ///
                /// 4. 目标的状态
                ///
                if (rtTargetCls.AnySame(TargetClass.Friendly))
                {
                    //友方
                    itor1 = SelectorTools.GetNPCValideStatus(caster, npcMgr, KindOfNPC.Life, rtTargetCls, NpcStatus.None, type);
                }
                else if (rtTargetCls.AnySame(TargetClass.Hostile))
                {
                    //敌方
                    itor1 = SelectorTools.GetNPCValideStatus(caster, npcMgr, KindOfNPC.Life, rtTargetCls, skillCfg.TargetStatusReject, type);
                }
                else if (rtTargetCls.AnySame(TargetClass.Self))
                {
                    //自己
                    List <ServerNPC> targets = new List <ServerNPC>();
                    targets.Add(caster);
                    itor = targets.AsEnumerable <ServerNPC>();
                    return(targets);
                }
                else
                {
                    itor1 = SelectorTools.GetNPCValideStatus(caster, npcMgr, KindOfNPC.Life, rtTargetCls, skillCfg.TargetStatusReject, type);
                    ConsoleEx.DebugLog("Warning : We should have a Camp. But sometimes, it's Ok.", ConsoleEx.RED);
                }

                ///
                /// 5. 根据施法的距离选择出目标
                ///

                itor1 = SelectorTools.GetNPCInRadius(caster, CheckDistance, rtTargetCls, itor1);

                ///
                /// 6. 根据血量选择出目标
                ///
                itor1 = SelectorTools.GetNPCByHp(caster, rtTargetCls, itor1);

                if (isNoPriority)
                {
                    singlePriority = itor1.FirstOrDefault();
                }
            }
            else
            {
                ///
                /// 获取单目标
                ///

                singlePriority = SelectorTools.GetPrioritiedNpc(caster, rtTargetCls, npcMgr, CheckDistance, skillCfg.TargetStatusReject, skillCfg.TargetPriority, priorityMgr, type);

                //单目标的友方,有可能选择到自己(但并不属于 TargetClass 64.就针对自己)
                if (!rtTargetCls.AnySame(TargetClass.Hostile))
                {
                    List <ServerNPC> broker = new List <ServerNPC>();
                    if (singlePriority != null)
                    {
                        broker.Add(singlePriority);
                    }
                    itor1 = broker.AsEnumerable <ServerNPC>();
                }
            }

            if (isMultiTarget == false)
            {
                ///
                /// 9. 单体攻击敌方,只有打敌方单体的时候,TargetID才会被重新设定
                ///
                if (rtTargetCls.AnySame(TargetClass.Hostile))
                {
                    ServerLifeNpc HighestPriority = null;
                    ///
                    /// 检测嘲讽
                    ///
                    int tarId = caster.getHighestHatred;
                    if (tarId != -1)
                    {
                        //有被嘲讽的目标
                        HighestPriority = npcMgr.GetNPCByUniqueID(tarId) as ServerLifeNpc;
                    }
                    else
                    {
                        //没有被嘲讽的目标

                        ///
                        ///  判定施法者的上次目标,则选择为最优先目标
                        ///  此逻辑,能保证追击残血逃跑的
                        ///

                        if (caster.TargetID != -1)
                        {
                            HighestPriority = npcMgr.GetNPCByUniqueID(caster.TargetID) as ServerLifeNpc;
                            if (HighestPriority != null)
                            {
                                ///
                                /// 如果单一目标的是英雄,
                                ///
                                if (singlePriority != null && singlePriority.data.configData.type == LifeNPCType.Hero &&
                                    HighestPriority.data.configData.type != LifeNPCType.Hero)
                                {
                                    HighestPriority = null;
                                    caster.TargetID = -1;
                                }
                                else
                                {
                                    bool validate1 = true, validate2 = true, validate3 = true;
                                    /// 生命判定
                                    if (HighestPriority.data.rtData.curHp <= 0)
                                    {
                                        validate1 = false;
                                    }

                                    /// 距离判定
                                    float distance = SelectorTools.GetDistance(HighestPriority.transform.position, caster.transform.position);
                                    distance = distance - HighestPriority.data.configData.radius - caster.data.configData.radius;

                                    /// 视野范围
                                    if (distance > CheckDistance)
                                    {
                                        validate2 = false;
                                    }

                                    ///如果有相同的状态,则不让释放技能
                                    validate3 = !HighestPriority.curStatus.AnySame(skillCfg.TargetStatusReject);

                                    /// 失败的判定
                                    bool validate = validate1 & validate2 & validate3;
                                    if (!validate)
                                    {
                                        HighestPriority = null;
                                        caster.TargetID = -1;
                                    }
                                    else
                                    {
                                        caster.RstTimeout();
                                    }
                                }
                            }
                            else
                            {
                                caster.TargetID = -1;
                            }
                        }
                    }

                    //找到普通选择出的目标
                    if (HighestPriority == null)
                    {
                        ServerNPC target = singlePriority;
                        caster.TargetID = target != null ? target.UniqueID : -1;
                        HighestPriority = target as ServerLifeNpc;
                    }

                    List <ServerNPC> high = new List <ServerNPC>();
                    if (HighestPriority != null)
                    {
                        high.Add(HighestPriority);
                    }
                    itor1 = high.AsEnumerable <ServerNPC>();
                }
                else
                {
                    ///
                    /// 10.单体友方
                    ///
                    if (itor1.Any())
                    {
                        itor1 = itor1.Take(1);
                    }
                }
            }


            itor = itor1;
            return(itor);
        }
Пример #14
0
        /// <summary>
        /// 处理主动打击其他NPC的时候,触发的事情
        /// </summary>
        /// <param name="CasterId">施法者ID</param>
        /// <param name="SufferId">撞击者ID</param>
        /// <param name="idx">几个被撞击者</param>
        /// <param name="finalTar">是否最终目标</param>
        /// <param name="maxDis">是否最大距离</param>
        /// <param name="returnback">返回原处</param>
        /// <param name="EffectId">效果ID</param>
        /// <param name="npcMgr">Npc mgr.</param>
        void HandleOnAttack(int CasterId, int SufferId, int idx, bool finalTar, bool maxDis, bool returnback, int EffectId, WarServerNpcMgr npcMgr)
        {
            ServerNPC caster = npcMgr.GetNPCByUniqueID(CasterId);
            ServerNPC suffer = npcMgr.GetNPCByUniqueID(SufferId);

            ///
            /// -------- 获取Effect的配置 -------
            ///
            EffectModel      efModel = Core.Data.getIModelConfig <EffectModel>();
            EffectConfigData efCfg   = efModel.get(EffectId);

            Utils.Assert(efCfg == null, "Can't find Effect Configure. effect ID = " + EffectId);

            if (efSelector == null)
            {
                efSelector = EffectSufferShared.get(npcMgr);
            }

            ///
            /// 先做技能
            ///
            IEnumerable <ServerNPC> filter = efSelector.Select(caster, new List <ServerNPC> {
                suffer
            }, efCfg);

            if (filter.Any())
            {
                //消失的时候,触发可能的位移
                HookNpcDisappearType disappearType = (HookNpcDisappearType)Enum.ToObject(typeof(HookNpcDisappearType), efCfg.Param2);
                //HookNpcDmgType hookDmgType = (HookNpcDmgType) Enum.ToObject(typeof(HookNpcDmgType), efCfg.Param8);
                HookNpcMoveType moveType = (HookNpcMoveType)Enum.ToObject(typeof(HookNpcMoveType), efCfg.Param5);

                ///
                /// 一定会有伤害,之后,先判定是否消失,如果消失,则再次判定是否移动
                ///

                ///
                /// ------- 开始运算BulletOp --------
                ///
                OperatorMgr OpMgr = OperatorMgr.instance;
                BulletNpcOp op    = OpMgr.getImplement <BulletNpcOp>(EffectOp.Bullet_NPC);

                Dmg  dmg           = op.toTargetDmg(caster.data, suffer.data, efCfg);
                int  moveDirection = 0;
                bool dis           = Disappear(disappearType, idx, finalTar, maxDis, returnback);
                if (dis)
                {
                    moveDirection = (int)moveType;
                }

                SelfDescribed   des   = record(CasterId, SufferId, dmg, dis, moveDirection);
                WarTarAnimParam param = new WarTarAnimParam()
                {
                    OP        = EffectOp.Injury,
                    OringinOP = EffectOp.HookNpc,
                    described = des,
                };
                ///发送消息
                npcMgr.SendMessageAsync(CasterId, SufferId, param);
            }
        }
Пример #15
0
        /// <summary>
        /// 处理主动打击其他NPC的时候,触发的事情
        /// </summary>
        void HandleOnAttack(MsgParam msg, WarServerNpcMgr npcMgr)
        {
            WarMsgParam warMsg = msg as WarMsgParam;

            if (warMsg != null)
            {
                if (efSelector == null)
                {
                    efSelector = EffectSufferShared.get(npcMgr);
                }

                int CasterId = warMsg.Sender;
                int SufferId = warMsg.Receiver;
                int EffectId = warMsg.arg1;
                int FinalId  = warMsg.arg2;
                //是否是最终目标
                bool IsfinalTarget = SufferId == FinalId;
                ///
                /// -------- 获取Effect的配置 -------
                ///
                EffectModel      efModel = Core.Data.getIModelConfig <EffectModel>();
                EffectConfigData efCfg   = efModel.get(EffectId);
                Utils.Assert(efCfg == null, "Can't find Effect Configure. effect ID = " + EffectId);
                //半径
                float radius = efCfg.Param9 * Consts.oneHundred;

                ServerNPC caster = npcMgr.GetNPCByUniqueID(CasterId);
                ServerNPC suffer = npcMgr.GetNPCByUniqueID(SufferId);

                ///
                /// ----------- 先坐第一步的选择和解析 ------------
                ///
                IEnumerable <ServerNPC> filter = efSelector.Select(caster, new List <ServerNPC> {
                    suffer
                }, efCfg);
                if (filter.Count() > 0)
                {
                    BulletHurtType   HurtType = (BulletHurtType)Enum.ToObject(typeof(BulletHurtType), efCfg.Param8);
                    List <ServerNPC> targets  = selectTarget(HurtType, suffer, IsfinalTarget, npcMgr, radius);

                    int tarCnt = targets.Count;
                    if (tarCnt > 0)
                    {
                        ///
                        /// ------- 开始运算BulletOp --------
                        ///
                        OperatorMgr OpMgr = OperatorMgr.instance;
                        BulletNpcOp op    = OpMgr.getImplement <BulletNpcOp>(EffectOp.Bullet_NPC);

                        for (int i = 0; i < tarCnt; ++i)
                        {
                            ServerNPC target = targets[i];
                            //alive ?
                            if (target.data.rtData.curHp > 0)
                            {
                                Dmg           damage = op.toTargetDmg(caster.data, target.data, efCfg);
                                SelfDescribed des    = record(CasterId, SufferId, damage, i);

                                WarTarAnimParam param = new WarTarAnimParam()
                                {
                                    OP        = EffectOp.Injury,
                                    OringinOP = EffectOp.Bullet_NPC,
                                    described = des,
                                };
                                ///发送消息
                                npcMgr.SendMessageAsync(CasterId, SufferId, param);
                            }
                        }
                    }
                }
            }
        }