private void ZoneHit(int Castingid, short x, short y)
        {
            List <CharacterSkill> skills         = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();
            CharacterSkill        characterSkill = skills.FirstOrDefault(s => s.Skill.CastId == Castingid);

            if (!Session.Character.WeaponLoaded(characterSkill) || !Session.HasCurrentMap)
            {
                Session.SendPacket("cancel 2 0");
                return;
            }

            if (characterSkill != null && characterSkill.CanBeUsed())
            {
                if (Session.Character.Mp >= characterSkill.Skill.MpCost)
                {
                    Session.CurrentMap?.Broadcast($"ct_n 1 {Session.Character.CharacterId} 3 -1 {characterSkill.Skill.CastAnimation} {characterSkill.Skill.CastEffect} {characterSkill.Skill.SkillVNum}");
                    characterSkill.LastUse = DateTime.Now;
                    if (!Session.Character.HasGodMode)
                    {
                        Session.Character.Mp -= characterSkill.Skill.MpCost;
                    }
                    Session.SendPacket(Session.Character.GenerateStat());
                    characterSkill.LastUse = DateTime.Now;
                    Observable.Timer(TimeSpan.FromMilliseconds(characterSkill.Skill.CastTime * 100))
                    .Subscribe(
                        o =>
                    {
                        Session.Character.LastSkillUse = DateTime.Now;

                        Session.CurrentMap?.Broadcast($"bs 1 {Session.Character.CharacterId} {x} {y} {characterSkill.Skill.SkillVNum} {characterSkill.Skill.Cooldown} {characterSkill.Skill.AttackAnimation} {characterSkill.Skill.Effect} 0 0 1 1 0 0 0");

                        IEnumerable <MapMonster> monstersInRange = Session.CurrentMap?.GetListMonsterInRange(x, y, characterSkill.Skill.TargetRange).ToList();
                        if (monstersInRange != null)
                        {
                            foreach (MapMonster mon in monstersInRange.Where(s => s.CurrentHp > 0))
                            {
                                mon.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.ZoneHit, Session, characterSkill.Skill, x, y));
                            }
                        }
                    });

                    Observable.Timer(TimeSpan.FromMilliseconds(characterSkill.Skill.CastTime * 100))
                    .Subscribe(
                        o =>
                    {
                        Session.SendPacket($"sr {Castingid}");
                    });
                }
                else
                {
                    Session.SendPacket(Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("NOT_ENOUGH_MP"), 10));
                    Session.SendPacket("cancel 2 0");
                }
            }
            else
            {
                Session.SendPacket("cancel 2 0");
            }
        }
Beispiel #2
0
        /// <summary>
        /// mtlist
        /// </summary>
        /// <param name="packet"></param>
        public void MultiTargetListHit(MultiTargetListPacket mutliTargetListPacket)
        {
            PenaltyLogDTO penalty = Session.Account.PenaltyLogs.OrderByDescending(s => s.DateEnd).FirstOrDefault();

            if (Session.Character.IsMuted())
            {
                Session.SendPacket("cancel 0 0");
                Session.CurrentMap?.Broadcast(Session.Character.Gender == GenderType.Female ? Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("MUTED_FEMALE"), 1) :
                                              Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("MUTED_MALE"), 1));
                Session.SendPacket(Session.Character.GenerateSay(String.Format(Language.Instance.GetMessageFromKey("MUTE_TIME"), (penalty.DateEnd - DateTime.Now).ToString("hh\\:mm\\:ss")), 11));
                Session.SendPacket(Session.Character.GenerateSay(String.Format(Language.Instance.GetMessageFromKey("MUTE_TIME"), (penalty.DateEnd - DateTime.Now).ToString("hh\\:mm\\:ss")), 12));
                return;
            }
            if ((DateTime.Now - Session.Character.LastTransform).TotalSeconds < 3)
            {
                Session.SendPacket("cancel 0 0");
                Session.SendPacket(Session.Character.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACKNOW"), 0));
                return;
            }
            if (Session.Character.IsVehicled)
            {
                Session.SendPacket("cancel 0 0");
                return;
            }
            Logger.Debug(mutliTargetListPacket.ToString(), Session.SessionId);
            if (mutliTargetListPacket != null && mutliTargetListPacket.TargetsAmount > 0 && mutliTargetListPacket.TargetsAmount == mutliTargetListPacket.Targets.Count())
            {
                foreach (MultiTargetListSubPacket subpacket in mutliTargetListPacket.Targets)
                {
                    List <CharacterSkill> skills = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();
                    if (skills != null)
                    {
                        CharacterSkill ski = skills.FirstOrDefault(s => s.Skill.CastId == subpacket.SkillCastId - 1);
                        if (ski.CanBeUsed())
                        {
                            MapMonster mon = Session.CurrentMap.GetMonster(subpacket.TargetId);
                            if (mon != null && mon.IsInRange(Session.Character.MapX, Session.Character.MapY, ski.Skill.Range) && ski != null && mon.CurrentHp > 0)
                            {
                                Session.Character.LastSkillUse = DateTime.Now;
                                mon.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.SpecialZoneHit, Session, ski.Skill));
                            }

                            Observable.Timer(TimeSpan.FromMilliseconds(ski.Skill.CastTime * 100))
                            .Subscribe(
                                o =>
                            {
                                Session.SendPacket($"sr {subpacket.SkillCastId - 1}");
                            }
                                );
                        }
                    }
                }
            }
        }
Beispiel #3
0
        private void ZoneHit(int Castingid, short x, short y)
        {
            List <CharacterSkill> skills = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();
            ushort         damage        = 0;
            int            hitmode       = 0;
            CharacterSkill ski           = skills.FirstOrDefault(s => s.Skill.CastId == Castingid);

            if (!Session.Character.WeaponLoaded(ski))
            {
                Session.SendPacket("cancel 2 0");
                return;
            }
            if (ski != null && ski.CanBeUsed())
            {
                if (Session.Character.Mp >= ski.Skill.MpCost)
                {
                    Task t = Task.Factory.StartNew((Func <Task>)(async() =>
                    {
                        Session.CurrentMap?.Broadcast($"ct_n 1 {Session.Character.CharacterId} 3 -1 {ski.Skill.CastAnimation} {ski.Skill.CastEffect} {ski.Skill.SkillVNum}");
                        ski.LastUse = DateTime.Now;
                        if (!Session.Character.HasGodMode)
                        {
                            Session.Character.Mp -= ski.Skill.MpCost;
                        }
                        Session.SendPacket(Session.Character.GenerateStat());
                        ski.LastUse = DateTime.Now;
                        await Task.Delay(ski.Skill.CastTime * 100);
                        Session.Character.LastSkillUse = DateTime.Now;

                        Session.CurrentMap?.Broadcast($"bs 1 {Session.Character.CharacterId} {x} {y} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {ski.Skill.Effect} 0 0 1 1 0 0 0");

                        IEnumerable <MapMonster> monstersInRange = Session.CurrentMap.GetListMonsterInRange(x, y, ski.Skill.TargetRange).ToList();
                        foreach (MapMonster mon in monstersInRange.Where(s => s.CurrentHp > 0))
                        {
                            damage = GenerateDamage(mon.MapMonsterId, ski.Skill, ref hitmode);
                            Session.CurrentMap?.Broadcast($"su 1 {Session.Character.CharacterId} 3 {mon.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {ski.Skill.Effect} {x} {y} {(mon.IsAlive ? 1 : 0)} {(int)(((float)mon.CurrentHp / (float)ServerManager.GetNpc(mon.MonsterVNum).MaxHP) * 100)} {damage} 5 {ski.Skill.SkillType - 1}");
                            Task.Factory.StartNew(() => { GenerateKillBonus(mon.MapMonsterId); });
                        }

                        await Task.Delay((ski.Skill.Cooldown) * 100);
                        Session.SendPacket($"sr {Castingid}");
                    }));
                }
                else
                {
                    Session.SendPacket(Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("NOT_ENOUGH_MP"), 10));
                    Session.SendPacket("cancel 2 0");
                }
            }
            else
            {
                Session.SendPacket("cancel 2 0");
            }
        }
Beispiel #4
0
        private void ExecuteHandler(ClientSession session)
        {
            CharacterSkill ski = (session.Character.UseSp
                    ? session.Character.SkillsSp?.GetAllItems()
                    : session.Character.Skills?.GetAllItems())?.Find(s =>
                                                                     s.Skill?.CastId == CastId && (s.Skill?.UpgradeSkill == 0 || s.Skill?.UpgradeSkill == 3));

            if (session.Character.NoAttack > 0 || ski?.CanBeUsed() != true)
            {
                session.SendPacket(StaticPacketHelper.Cancel(2));
                return;
            }

            if (session.Character.CanFight)
            {
                bool isMuted = session.Character.MuteMessage();
                if (isMuted || session.Character.IsVehicled || session.Character.InvisibleGm)
                {
                    session.SendPacket(StaticPacketHelper.Cancel());
                    return;
                }

                bool sendCoordinates = false;
                if (MapX.HasValue && MapY.HasValue)
                {
                    session.Character.PositionX = MapX.Value;
                    session.Character.PositionY = MapY.Value;
                    sendCoordinates             = true;
                }

                if (session.Character.IsSitting)
                {
                    session.Character.Rest();
                }

                switch (UserType)
                {
                case UserType.Monster:
                    if (session.Character.Hp > 0)
                    {
                        session.TargetHit(CastId, MapMonsterId, sendCoordinates: sendCoordinates);
                        int[] fairyWings = session.Character.GetBuff(BCardType.CardType.EffectSummon, 11);
                        int   random     = ServerManager.RandomNumber();
                        if (fairyWings[0] > random)
                        {
                            Observable.Timer(TimeSpan.FromSeconds(1)).Subscribe(o =>
                            {
                                ski.LastUse = DateTime.UtcNow.AddMilliseconds(ski.Skill.Cooldown * 100 * -1);
                                session.SendPacket(StaticPacketHelper.SkillReset(CastId));
                            });
                        }
                    }
                    break;

                case UserType.Player:
                    if (session.Character.Hp > 0)
                    {
                        if (MapMonsterId != session.Character.CharacterId)
                        {
                            session.TargetHit(CastId, MapMonsterId, true, sendCoordinates);
                        }
                        else
                        {
                            session.TargetHit(CastId, MapMonsterId, sendCoordinates: sendCoordinates);
                        }

                        int[] fairyWings = session.Character.GetBuff(BCardType.CardType.EffectSummon, 11);
                        int   random     = ServerManager.RandomNumber();
                        if (fairyWings[0] > random)
                        {
                            Observable.Timer(TimeSpan.FromSeconds(1)).Subscribe(o =>
                            {
                                ski.LastUse = DateTime.UtcNow.AddMilliseconds(ski.Skill.Cooldown * 100 * -1);
                                session.SendPacket(StaticPacketHelper.SkillReset(CastId));
                            });
                        }
                    }
                    else
                    {
                        session.SendPacket(StaticPacketHelper.Cancel(2));
                    }
                    break;

                default:
                    session.SendPacket(StaticPacketHelper.Cancel(2));
                    return;
                }

                Observable.Timer(TimeSpan.FromMilliseconds(200)).Subscribe(observer =>
                {
                    session.Character.RemoveBuff(614);
                    session.Character.RemoveBuff(615);
                    session.Character.RemoveBuff(616);
                });
            }
            else
            {
                session.SendPacket(StaticPacketHelper.Cancel(2));
            }
        }
Beispiel #5
0
        public void TargetHit(int castingId, int targetId)
        {
            if ((DateTime.Now - Session.Character.LastTransform).TotalSeconds < 3)
            {
                Session.SendPacket("cancel 0 0");
                Session.SendPacket(Session.Character.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACK"), 0));
                return;
            }

            bool doNotCancel             = false;
            List <CharacterSkill> skills = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();

            if (skills != null)
            {
                CharacterSkill ski = skills.FirstOrDefault(s => s.Skill?.CastId == castingId && s.Skill?.UpgradeSkill == 0);
                Session.SendPacket("ms_c 0");
                if (!Session.Character.WeaponLoaded(ski) || !ski.CanBeUsed())
                {
                    Session.SendPacket("cancel 2 0");
                    return;
                }

                if (ski != null && Session.Character.Mp >= ski.Skill.MpCost)
                {
                    // AOE Target hit
                    if (ski.Skill.TargetType == 1 && ski.Skill.HitType == 1)
                    {
                        Session.Character.LastSkillUse = DateTime.Now;
                        if (!Session.Character.HasGodMode)
                        {
                            Session.Character.Mp -= ski.Skill.MpCost;
                        }

                        if (Session.Character.UseSp && ski.Skill.CastEffect != -1)
                        {
                            Session.SendPackets(Session.Character.GenerateQuicklist());
                        }

                        Session.SendPacket(Session.Character.GenerateStat());
                        CharacterSkill skillinfo = Session.Character.Skills.GetAllItems().OrderBy(o => o.SkillVNum).FirstOrDefault(s => s.Skill.UpgradeSkill == ski.Skill.SkillVNum && s.Skill.Effect > 0 && s.Skill.SkillType == 2);
                        Session.CurrentMap?.Broadcast($"ct 1 {Session.Character.CharacterId} 1 {Session.Character.CharacterId} {ski.Skill.CastAnimation} {(skillinfo != null ? skillinfo.Skill.CastEffect : ski.Skill.CastEffect)} {ski.Skill.SkillVNum}");

                        // Generate scp
                        ski.LastUse = DateTime.Now;
                        if (ski.Skill.CastEffect != 0)
                        {
                            Thread.Sleep(ski.Skill.CastTime * 100);
                        }

                        doNotCancel = true;
                        Session.CurrentMap.Broadcast($"su 1 {Session.Character.CharacterId} 1 {Session.Character.CharacterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(skillinfo != null ? skillinfo.Skill.Effect : ski.Skill.Effect)} {Session.Character.MapX} {Session.Character.MapY} 1 {((int)((double)Session.Character.Hp / Session.Character.HPLoad()) * 100)} 0 -2 {ski.Skill.SkillType - 1}");
                        if (ski.Skill.TargetRange != 0)
                        {
                            foreach (MapMonster mon in Session.CurrentMap.GetListMonsterInRange(Session.Character.MapX, Session.Character.MapY, ski.Skill.TargetRange).Where(s => s.CurrentHp > 0))
                            {
                                mon.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.AOETargetHit, Session, ski.Skill, skillEffect: (skillinfo != null ? skillinfo.Skill.Effect : ski.Skill.Effect)));
                            }
                        }
                    }
                    else if (ski.Skill.TargetType == 0)
                    // monster target
                    {
                        MapMonster monsterToAttack = Session.CurrentMap.GetMonster(targetId);
                        if (monsterToAttack != null && monsterToAttack.IsAlive)
                        {
                            if (monsterToAttack != null && ski != null && ski.CanBeUsed())
                            {
                                if (Session.Character.Mp >= ski.Skill.MpCost)
                                {
                                    short distanceX = (short)(Session.Character.MapX - monsterToAttack.MapX);
                                    short distanceY = (short)(Session.Character.MapY - monsterToAttack.MapY);
                                    if (Map.GetDistance(new MapCell()
                                    {
                                        X = Session.Character.MapX, Y = Session.Character.MapY
                                    },
                                                        new MapCell()
                                    {
                                        X = monsterToAttack.MapX, Y = monsterToAttack.MapY
                                    }) <= (ski.Skill.Range) + monsterToAttack.Monster.BasicArea)
                                    {
                                        Session.Character.LastSkillUse = DateTime.Now;
                                        ski.LastUse = DateTime.Now;
                                        doNotCancel = true;
                                        if (!Session.Character.HasGodMode)
                                        {
                                            Session.Character.Mp -= ski.Skill.MpCost;
                                        }
                                        if (Session.Character.UseSp && ski.Skill.CastEffect != -1)
                                        {
                                            Session.SendPackets(Session.Character.GenerateQuicklist());
                                        }
                                        Session.SendPacket(Session.Character.GenerateStat());
                                        CharacterSkill characterSkillInfo = Session.Character.Skills.GetAllItems().OrderBy(o => o.SkillVNum)
                                                                            .FirstOrDefault(s => s.Skill.UpgradeSkill == ski.Skill.SkillVNum && s.Skill.Effect > 0 && s.Skill.SkillType == 2);

                                        Session.CurrentMap?.Broadcast($"ct 1 {Session.Character.CharacterId} 3 {monsterToAttack.MapMonsterId} {ski.Skill.CastAnimation} {(characterSkillInfo != null ? characterSkillInfo.Skill.CastEffect : ski.Skill.CastEffect)} {ski.Skill.SkillVNum}");
                                        Session.Character.Skills.GetAllItems().Where(s => s.Id != ski.Id).ToList().ForEach(i => i.Hit = 0);

                                        // Generate scp
                                        ski.LastUse = DateTime.Now;
                                        if ((DateTime.Now - ski.LastUse).TotalSeconds > 3)
                                        {
                                            ski.Hit = 0;
                                        }
                                        else
                                        {
                                            ski.Hit++;
                                        }

                                        if (ski.Skill.CastEffect != 0)
                                        {
                                            Thread.Sleep(ski.Skill.CastTime * 100);
                                        }
                                        // check if we will hit mutltiple targets
                                        if (ski.Skill.TargetRange != 0)
                                        {
                                            ComboDTO skillCombo = ski.Skill.Combos.FirstOrDefault(s => ski.Hit == s.Hit);
                                            if (skillCombo != null)
                                            {
                                                if (ski.Skill.Combos.OrderByDescending(s => s.Hit).First().Hit == ski.Hit)
                                                {
                                                    ski.Hit = 0;
                                                }
                                                IEnumerable <MapMonster> monstersInAOERange = Session.CurrentMap?.GetListMonsterInRange(monsterToAttack.MapX, monsterToAttack.MapY, ski.Skill.TargetRange).ToList();
                                                foreach (MapMonster mon in monstersInAOERange.Where(s => s.CurrentHp > 0))
                                                {
                                                    mon.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.SingleTargetHitCombo, Session, ski.Skill
                                                                                                              , skillCombo: skillCombo));
                                                }
                                            }
                                            else
                                            {
                                                IEnumerable <MapMonster> monstersInAOERange = Session.CurrentMap?.GetListMonsterInRange(monsterToAttack.MapX, monsterToAttack.MapY, ski.Skill.TargetRange).ToList();
                                                Session.CurrentMap.Broadcast($"su 1 {Session.Character.CharacterId} 3 {targetId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(characterSkillInfo != null ? characterSkillInfo.Skill.Effect : ski.Skill.Effect)} 0 0 {(monsterToAttack.IsAlive ? 1 : 0)} {((int)((double)Session.Character.Hp / Session.Character.HPLoad()) * 100)} 0 0 {ski.Skill.SkillType - 1}");
                                                foreach (MapMonster mon in monstersInAOERange.Where(s => s.CurrentHp > 0))
                                                {
                                                    mon.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.SingleAOETargetHit, Session, ski.Skill
                                                                                                              , skillEffect: (characterSkillInfo != null ? characterSkillInfo.Skill.Effect : ski.Skill.Effect)));
                                                }
                                            }
                                        }
                                        else
                                        {
                                            ComboDTO skillCombo = ski.Skill.Combos.FirstOrDefault(s => ski.Hit == s.Hit);
                                            if (skillCombo != null)
                                            {
                                                if (ski.Skill.Combos.OrderByDescending(s => s.Hit).First().Hit == ski.Hit)
                                                {
                                                    ski.Hit = 0;
                                                }
                                                monsterToAttack.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.SingleTargetHitCombo, Session, ski.Skill, skillCombo: skillCombo));
                                            }
                                            else
                                            {
                                                monsterToAttack.HitQueue.Enqueue(new GameObject.Networking.HitRequest(TargetHitType.SingleTargetHit, Session, ski.Skill));
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }

                    Session.SendPacketAfterWait($"sr {castingId}", ski.Skill.Cooldown * 100);
                }
                else
                {
                    doNotCancel = false;
                    Session.SendPacket(Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("NOT_ENOUGH_MP"), 10));
                }
            }

            if (!doNotCancel)
            {
                Session.SendPacket($"cancel 2 {targetId}");
            }
        }
Beispiel #6
0
        public void SpecialZoneHit(string packet)
        {
            PenaltyLogDTO penalty = Session.Account.PenaltyLogs.OrderByDescending(s => s.DateEnd).FirstOrDefault();

            if (Session.Character.IsMuted())
            {
                Session.SendPacket("cancel 0 0");
                Session.CurrentMap?.Broadcast(Session.Character.Gender == GenderType.Female ? Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("MUTED_FEMALE"), 1) :
                                              Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("MUTED_MALE"), 1));
                Session.SendPacket(Session.Character.GenerateSay(String.Format(Language.Instance.GetMessageFromKey("MUTE_TIME"), (penalty.DateEnd - DateTime.Now).ToString("hh\\:mm\\:ss")), 11));
                Session.SendPacket(Session.Character.GenerateSay(String.Format(Language.Instance.GetMessageFromKey("MUTE_TIME"), (penalty.DateEnd - DateTime.Now).ToString("hh\\:mm\\:ss")), 12));
                return;
            }
            if ((DateTime.Now - Session.Character.LastTransform).TotalSeconds < 3)
            {
                Session.SendPacket("cancel 0 0");
                Session.SendPacket(Session.Character.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACKNOW"), 0));
                return;
            }
            if (Session.Character.IsVehicled)
            {
                Session.SendPacket("cancel 0 0");
                return;
            }
            Logger.Debug(packet, Session.SessionId);
            string[] packetsplit = packet.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
            ushort   damage      = 0;
            int      hitmode     = 0;

            if (packetsplit.Length > 3)
            {
                // get amount of mobs which are targeted
                short mobAmount = 0;
                short.TryParse(packetsplit[2], out mobAmount);
                if ((packetsplit.Length - 3) / 2 != mobAmount)
                {
                    return;
                }

                for (int i = 3; i < packetsplit.Length - 2; i += 2)
                {
                    List <CharacterSkill> skills = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();
                    if (skills != null)
                    {
                        short mapMonsterTargetId = -1;
                        short skillCastId        = -1;

                        if (short.TryParse(packetsplit[i], out skillCastId) && short.TryParse(packetsplit[i + 1], out mapMonsterTargetId))
                        {
                            Task t = Task.Factory.StartNew((Func <Task>)(async() =>
                            {
                                CharacterSkill ski = skills.FirstOrDefault(s => s.Skill.CastId == skillCastId - 1);
                                if (ski.CanBeUsed())
                                {
                                    MapMonster mon = Session.CurrentMap.GetMonster(mapMonsterTargetId);
                                    if (mon != null && mon.IsInRange(Session.Character.MapX, Session.Character.MapY, ski.Skill.Range) && ski != null && mon.CurrentHp > 0)
                                    {
                                        Session.Character.LastSkillUse = DateTime.Now;
                                        damage = GenerateDamage(mon.MapMonsterId, ski.Skill, ref hitmode);
                                        Session.CurrentMap?.Broadcast($"su 1 {Session.Character.CharacterId} 3 {mon.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {ski.Skill.Effect} {Session.Character.MapX} {Session.Character.MapY} {(mon.IsAlive ? 1 : 0)} {(int)(((float)mon.CurrentHp / (float)ServerManager.GetNpc(mon.MonsterVNum).MaxHP) * 100)} {damage} 0 {ski.Skill.SkillType - 1}");
                                        Task.Factory.StartNew(() => { GenerateKillBonus(mon.MapMonsterId); });
                                    }

                                    await Task.Delay((ski.Skill.Cooldown) * 100);
                                    Session.SendPacket($"sr {skillCastId - 1}");
                                }
                            }));
                        }
                    }
                }
            }
        }
Beispiel #7
0
        public void TargetHit(int castingId, int targetId)
        {
            IList <string> broadcastPackets = new List <string>();

            List <CharacterSkill> skills = Session.Character.UseSp ? Session.Character.SkillsSp.GetAllItems() : Session.Character.Skills.GetAllItems();
            bool notcancel = false;

            if ((DateTime.Now - Session.Character.LastTransform).TotalSeconds < 3)
            {
                Session.SendPacket("cancel 0 0");
                Session.SendPacket(Session.Character.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACK"), 0));
                return;
            }
            if (skills != null)
            {
                ushort         damage  = 0;
                int            hitmode = 0;
                CharacterSkill ski     = skills.FirstOrDefault(s => s.Skill?.CastId == castingId && s.Skill?.UpgradeSkill == 0);
                Session.SendPacket("ms_c 0");
                if (!Session.Character.WeaponLoaded(ski))
                {
                    Session.SendPacket("cancel 2 0");
                    return;
                }
                for (int i = 0; i < 10 && !ski.CanBeUsed(); i++)
                {
                    Thread.Sleep(100);
                    if (i == 10)
                    {
                        Session.SendPacket("cancel 2 0");
                        return;
                    }
                }

                if (ski != null && Session.Character.Mp >= ski.Skill.MpCost)
                {
                    if (ski.Skill.TargetType == 1 && ski.Skill.HitType == 1)
                    {
                        Session.Character.LastSkillUse = DateTime.Now;
                        if (!Session.Character.HasGodMode)
                        {
                            Session.Character.Mp -= ski.Skill.MpCost;
                        }
                        if (Session.Character.UseSp && ski.Skill.CastEffect != -1)
                        {
                            Session.SendPackets(Session.Character.GenerateQuicklist());
                        }

                        Session.SendPacket(Session.Character.GenerateStat());
                        CharacterSkill skillinfo = Session.Character.Skills.GetAllItems().OrderBy(o => o.SkillVNum).FirstOrDefault(s => s.Skill.UpgradeSkill == ski.Skill.SkillVNum && s.Skill.Effect > 0 && s.Skill.SkillType == 2);
                        Session.CurrentMap?.Broadcast($"ct 1 {Session.Character.CharacterId} 1 {Session.Character.CharacterId} {ski.Skill.CastAnimation} {(skillinfo != null ? skillinfo.Skill.CastEffect : ski.Skill.CastEffect)} {ski.Skill.SkillVNum}");

                        // Generate scp
                        ski.LastUse = DateTime.Now;
                        if (ski.Skill.CastEffect != 0)
                        {
                            Thread.Sleep(ski.Skill.CastTime * 100);
                        }
                        notcancel = true;
                        MapMonster mmon;
                        broadcastPackets.Add($"su 1 {Session.Character.CharacterId} 1 {Session.Character.CharacterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(skillinfo != null ? skillinfo.Skill.Effect : ski.Skill.Effect)} {Session.Character.MapX} {Session.Character.MapY} 1 {((int)((double)Session.Character.Hp / Session.Character.HPLoad()) * 100)} 0 -2 {ski.Skill.SkillType - 1}");
                        if (ski.Skill.TargetRange != 0)
                        {
                            foreach (MapMonster mon in Session.CurrentMap.GetListMonsterInRange(Session.Character.MapX, Session.Character.MapY, ski.Skill.TargetRange).Where(s => s.CurrentHp > 0))
                            {
                                mmon = Session.CurrentMap.GetMonster(mon.MapMonsterId);
                                if (mmon != null)
                                {
                                    damage = GenerateDamage(mon.MapMonsterId, ski.Skill, ref hitmode);
                                    broadcastPackets.Add($"su 1 {Session.Character.CharacterId} 3 {mmon.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(skillinfo != null ? skillinfo.Skill.Effect : ski.Skill.Effect)} {Session.Character.MapX} {Session.Character.MapY} {(mmon.IsAlive ? 1 : 0)} {(int)(((float)mmon.CurrentHp / (float)mon.Monster.MaxHP) * 100)} {damage} 5 {ski.Skill.SkillType - 1}");
                                    Task.Factory.StartNew(() => { GenerateKillBonus(mon.MapMonsterId); });
                                }
                            }
                        }
                    }
                    else if (ski.Skill.TargetType == 0)
                    {
                        // if monster target
                        MapMonster monsterToAttack = Session.CurrentMap.GetMonster(targetId);
                        if (monsterToAttack != null && monsterToAttack.IsAlive)
                        {
                            NpcMonster monsterToAttackInfo = ServerManager.GetNpc(monsterToAttack.MonsterVNum);
                            if (monsterToAttack != null && ski != null && ski.CanBeUsed())
                            {
                                if (Session.Character.Mp >= ski.Skill.MpCost)
                                {
                                    short distanceX = (short)(Session.Character.MapX - monsterToAttack.MapX);
                                    short distanceY = (short)(Session.Character.MapY - monsterToAttack.MapY);

                                    if (Map.GetDistance(new MapCell()
                                    {
                                        X = Session.Character.MapX, Y = Session.Character.MapY
                                    },
                                                        new MapCell()
                                    {
                                        X = monsterToAttack.MapX, Y = monsterToAttack.MapY
                                    }) <= ski.Skill.Range + (DateTime.Now - monsterToAttack.LastMove).TotalSeconds * 2 * (monsterToAttackInfo.Speed == 0 ? 1 : monsterToAttackInfo.Speed) || ski.Skill.TargetRange != 0)
                                    {
                                        Session.Character.LastSkillUse = DateTime.Now;
                                        damage = GenerateDamage(monsterToAttack.MapMonsterId, ski.Skill, ref hitmode);

                                        ski.LastUse = DateTime.Now;
                                        Task.Factory.StartNew(() => { GenerateKillBonus(monsterToAttack.MapMonsterId); });
                                        notcancel = true;
                                        if (!Session.Character.HasGodMode)
                                        {
                                            Session.Character.Mp -= ski.Skill.MpCost;
                                        }
                                        if (Session.Character.UseSp && ski.Skill.CastEffect != -1)
                                        {
                                            Session.SendPackets(Session.Character.GenerateQuicklist());
                                        }
                                        Session.SendPacket(Session.Character.GenerateStat());
                                        CharacterSkill characterSkillInfo = Session.Character.Skills.GetAllItems().OrderBy(o => o.SkillVNum).FirstOrDefault(s => s.Skill.UpgradeSkill == ski.Skill.SkillVNum && s.Skill.Effect > 0 && s.Skill.SkillType == 2);
                                        Session.CurrentMap?.Broadcast($"ct 1 {Session.Character.CharacterId} 3 {monsterToAttack.MapMonsterId} {ski.Skill.CastAnimation} {(characterSkillInfo != null ? characterSkillInfo.Skill.CastEffect : ski.Skill.CastEffect)} {ski.Skill.SkillVNum}");
                                        Session.Character.Skills.GetAllItems().Where(s => s.Id != ski.Id).ToList().ForEach(i => i.Hit = 0);

                                        // Generate scp
                                        ski.LastUse = DateTime.Now;
                                        if (damage == 0 || (DateTime.Now - ski.LastUse).TotalSeconds > 3)
                                        {
                                            ski.Hit = 0;
                                        }
                                        else
                                        {
                                            ski.Hit++;
                                        }
                                        if (ski.Skill.CastEffect != 0)
                                        {
                                            Thread.Sleep(ski.Skill.CastTime * 100);
                                        }

                                        ComboDTO skillCombo = ski.Skill.Combos.FirstOrDefault(s => ski.Hit == s.Hit);
                                        if (skillCombo != null)
                                        {
                                            if (ski.Skill.Combos.OrderByDescending(s => s.Hit).ElementAt(0).Hit == ski.Hit)
                                            {
                                                ski.Hit = 0;
                                            }
                                            broadcastPackets.Add($"su 1 {Session.Character.CharacterId} 3 {monsterToAttack.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {skillCombo.Animation} {skillCombo.Effect} {Session.Character.MapX} {Session.Character.MapY} {(monsterToAttack.IsAlive ? 1 : 0)} {(int)(((float)monsterToAttack.CurrentHp / (float)monsterToAttackInfo.MaxHP) * 100)} {damage} {hitmode} {ski.Skill.SkillType - 1}");
                                        }
                                        else
                                        {
                                            broadcastPackets.Add($"su 1 {Session.Character.CharacterId} 3 {monsterToAttack.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(characterSkillInfo != null ? characterSkillInfo.Skill.Effect : ski.Skill.Effect)} {Session.Character.MapX} {Session.Character.MapY} {(monsterToAttack.IsAlive ? 1 : 0)} {(int)(((float)monsterToAttack.CurrentHp / (float)monsterToAttackInfo.MaxHP) * 100)} {damage} {hitmode} {ski.Skill.SkillType - 1}");
                                        }
                                        if (ski.Skill.TargetRange != 0)
                                        {
                                            IEnumerable <MapMonster> monstersInAOERange = Session.CurrentMap?.GetListMonsterInRange(monsterToAttack.MapX, monsterToAttack.MapY, ski.Skill.TargetRange).ToList();
                                            foreach (MapMonster mon in monstersInAOERange.Where(s => s.CurrentHp > 0))
                                            {
                                                damage = GenerateDamage(mon.MapMonsterId, ski.Skill, ref hitmode);
                                                broadcastPackets.Add($"su 1 {Session.Character.CharacterId} 3 {mon.MapMonsterId} {ski.Skill.SkillVNum} {ski.Skill.Cooldown} {ski.Skill.AttackAnimation} {(characterSkillInfo != null ? characterSkillInfo.Skill.Effect : ski.Skill.Effect)} {Session.Character.MapX} {Session.Character.MapY} {(mon.IsAlive ? 1 : 0)} {(int)(((float)mon.CurrentHp / (float)ServerManager.GetNpc(mon.MonsterVNum).MaxHP) * 100)} {damage} 5 {ski.Skill.SkillType - 1}");
                                                Task.Factory.StartNew(() => { GenerateKillBonus(mon.MapMonsterId); });
                                            }
                                        }
                                    }
                                }
                            }
                        }
                    }

                    // send su packets
                    Session.CurrentMap.Broadcast(broadcastPackets.ToArray());

                    Task t = Task.Factory.StartNew((Func <Task>)(async() =>
                    {
                        await Task.Delay((ski.Skill.Cooldown) * 100);
                        Session.SendPacket($"sr {castingId}");
                    }));
                }
                else
                {
                    notcancel = false;
                    Session.SendPacket(Session.Character.GenerateSay(Language.Instance.GetMessageFromKey("NOT_ENOUGH_MP"), 10));
                }
            }
            if (!notcancel)
            {
                Session.SendPacket($"cancel 2 {targetId}");
            }
        }