private void ExecuteHandler(ClientSession session)
        {
            if (!session.HasCurrentMapInstance)
            {
                return;
            }

            bool isMuted = session.Character.MuteMessage();

            if (isMuted || session.Character.IsVehicled)
            {
                session.SendPacket(StaticPacketHelper.Cancel());
                return;
            }

            if ((DateTime.UtcNow - session.Character.LastTransform).TotalSeconds < 3)
            {
                session.SendPacket(StaticPacketHelper.Cancel());
                session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACK"), 0));
                return;
            }

            if (TargetsAmount > 0 &&
                TargetsAmount == TargetList.Count &&
                TargetList != null)
            {
                session.Character.MtListTargetQueue.Clear();
                foreach (Tuple <int, UserType> target in TargetList)
                {
                    session.Character.MtListTargetQueue.Push(new MtListHitTarget(target.Item2, target.Item1));
                }
            }
        }
 private void ExecuteHandler(ClientSession session)
 {
     if (session.Character.Miniland == session.Character.MapInstance)
     {
         ServerManager.Instance.JoinMiniland(session, session);
     }
     else
     {
         ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                  session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                  true);
         session.SendPacket(StaticPacketHelper.Cancel(2));
     }
 }
Beispiel #3
0
        private void ExecuteHandler(ClientSession session)
        {
            bool isMuted = session.Character.MuteMessage();

            if (isMuted || session.Character.IsVehicled)
            {
                session.SendPacket(StaticPacketHelper.Cancel());
            }
            else
            {
                if (session.Character.LastTransform.AddSeconds(3) > DateTime.UtcNow)
                {
                    session.SendPacket(StaticPacketHelper.Cancel());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_ATTACK"), 0));
                    return;
                }

                if (session.Character.CanFight && session.Character.Hp > 0)
                {
                    session.ZoneHit(CastId, MapX, MapY);
                }
            }
        }
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 ApplyBCards(object session, object sender = null)
        {
            Type type = session.GetType();

            // int counterBuff = 0;
            if (type == null)
            {
                return;
            }
            switch ((BCardType.CardType)Type)
            {
            case BCardType.CardType.Buff:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    Buff buff = null;
                    if (sender != null)
                    {
                        Type sType = sender.GetType();
                        if (sType != null)
                        {
                            if (sType == typeof(Character) && sender is Character sendingCharacter)
                            {
                                buff = new Buff((short)SecondData, sendingCharacter.Level);

                                //Todo: Get anti stats from BCard
                            }
                        }
                    }
                    else
                    {
                        buff = new Buff((short)SecondData, character.Level);
                    }
                    if (ServerManager.RandomNumber() < FirstData)
                    {
                        character.AddBuff(buff);
                    }
                }
                else if (type == typeof(MapMonster))
                {
                    if (ServerManager.RandomNumber() < FirstData && session is MapMonster mapMonster)
                    {
                        mapMonster.AddBuff(new Buff((short)SecondData, mapMonster.Monster.Level));
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
                break;
            }

            case BCardType.CardType.Move:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    character.LastSpeedChange = DateTime.Now;
                    character.Session.SendPacket(character.GenerateCond());
                }
            }
            break;

            case BCardType.CardType.Summons:
                if (type == typeof(Character))
                {
                }
                else if (type == typeof(MapMonster))
                {
                    if (session is MapMonster mapMonster)
                    {
                        List <MonsterToSummon> summonParameters = new List <MonsterToSummon>();
                        for (int i = 0; i < FirstData; i++)
                        {
                            short x = (short)(ServerManager.RandomNumber(-3, 3) + mapMonster.MapX);
                            short y = (short)(ServerManager.RandomNumber(-3, 3) + mapMonster.MapY);
                            summonParameters.Add(new MonsterToSummon((short)SecondData, new MapCell {
                                X = x, Y = y
                            }, -1, true));
                        }
                        if (ServerManager.RandomNumber() <= Math.Abs(ThirdData) || ThirdData == 0)
                        {
                            switch (SubType)
                            {
                            case 2:
                                EventHelper.Instance.RunEvent(new EventContainer(mapMonster.MapInstance, EventActionType.SPAWNMONSTERS, summonParameters));
                                break;

                            default:
                                if (!mapMonster.OnDeathEvents.Any(s => s.EventActionType == EventActionType.SPAWNMONSTERS))
                                {
                                    mapMonster.OnDeathEvents.Add(new EventContainer(mapMonster.MapInstance, EventActionType.SPAWNMONSTERS, summonParameters));
                                }
                                break;
                            }
                        }
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
                break;

            case BCardType.CardType.SpecialAttack:
                break;

            case BCardType.CardType.SpecialDefence:
                break;

            case BCardType.CardType.AttackPower:
                break;

            case BCardType.CardType.Target:
                break;

            case BCardType.CardType.Critical:
                break;

            case BCardType.CardType.SpecialCritical:
                break;

            case BCardType.CardType.Element:
                break;

            case BCardType.CardType.IncreaseDamage:
                break;

            case BCardType.CardType.Defence:
                break;

            case BCardType.CardType.DodgeAndDefencePercent:
                break;

            case BCardType.CardType.Block:
                break;

            case BCardType.CardType.Absorption:
                break;

            case BCardType.CardType.ElementResistance:
                break;

            case BCardType.CardType.EnemyElementResistance:
                break;

            case BCardType.CardType.Damage:
                break;

            case BCardType.CardType.GuarantedDodgeRangedAttack:
                break;

            case BCardType.CardType.Morale:
                break;

            case BCardType.CardType.Casting:
                break;

            case BCardType.CardType.Reflection:
                break;

            case BCardType.CardType.DrainAndSteal:
                break;

            case BCardType.CardType.HealingBurningAndCasting:
                if (type == typeof(Character))
                {
                    if (session is Character character && character.Hp > 0)
                    {
                        int bonus = 0;
                        if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreHP / 10)
                        {
                            if (IsLevelScaled)
                            {
                                bonus = character.Level * FirstData;
                            }
                            else
                            {
                                bonus = FirstData;
                            }
                            if (character.Hp + bonus <= character.HPLoad())
                            {
                                character.Hp += bonus;
                            }
                            else
                            {
                                bonus        = (int)character.HPLoad() - character.Hp;
                                character.Hp = (int)character.HPLoad();
                            }
                            character.Session.CurrentMapInstance?.Broadcast(character.Session, character.GenerateRc(bonus));
                        }
                        if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreMP / 10)
                        {
                            if (IsLevelScaled)
                            {
                                bonus = character.Level * FirstData;
                            }
                            else
                            {
                                bonus = FirstData;
                            }
                            if (character.Mp + bonus <= character.MPLoad())
                            {
                                character.Mp += bonus;
                            }
                            else
                            {
                                bonus        = (int)character.MPLoad() - character.Mp;
                                character.Mp = (int)character.MPLoad();
                            }
                        }
                        character.Session.SendPacket(character.GenerateStat());
                    }
                }
                else if (type == typeof(MapMonster))
                {
                    if (ServerManager.RandomNumber() < FirstData && session is MapMonster mapMonster)
                    {
                        mapMonster.AddBuff(new Buff((short)SecondData, mapMonster.Monster.Level));
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
                break;

            case BCardType.CardType.HPMP:
                break;

            case BCardType.CardType.SpecialisationBuffResistance:
                break;

            case BCardType.CardType.SpecialEffects:
                break;

            case BCardType.CardType.Capture:
                if (type == typeof(MapMonster))
                {
                    if (session is MapMonster mapMonster && sender is ClientSession senderSession)
                    {
                        NpcMonster mateNpc = ServerManager.GetNpc(mapMonster.MonsterVNum);
                        if (mateNpc != null)
                        {
                            if (mapMonster.Monster.Catch)
                            {
                                if (mapMonster.IsAlive && mapMonster.CurrentHp <= (int)((double)mapMonster.MaxHp / 2))
                                {
                                    if (mapMonster.Monster.Level < senderSession.Character.Level)
                                    {
#warning find a new algorithm
                                        int[] chance = { 100, 80, 60, 40, 20, 0 };
                                        if (ServerManager.RandomNumber() < chance[ServerManager.RandomNumber(0, 5)])
                                        {
                                            Mate mate = new Mate(senderSession.Character, mateNpc, (byte)(mapMonster.Monster.Level - 15 > 0 ? mapMonster.Monster.Level - 15 : 1), MateType.Pet);
                                            if (senderSession.Character.CanAddMate(mate))
                                            {
                                                senderSession.Character.AddPetWithSkill(mate);
                                                senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CATCH_SUCCESS"), 0));
                                                senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, senderSession.Character.CharacterId, 197));
                                                senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, senderSession.Character.CharacterId, 3, mapMonster.MapMonsterId, -1, 0, 15, -1, -1, -1, true, (int)((float)mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100), 0, -1, 0));
                                                mapMonster.SetDeathStatement();
                                                senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.Out(UserType.Monster, mapMonster.MapMonsterId));
                                            }
                                            else
                                            {
                                                senderSession.SendPacket(senderSession.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_SLOT_FULL"), 10));
                                                senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                            }
                                        }
                                        else
                                        {
                                            senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CATCH_FAIL"), 0));
                                            senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, senderSession.Character.CharacterId, 3, mapMonster.MapMonsterId, -1, 0, 15, -1, -1, -1, true, (int)((float)mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100), 0, -1, 0));
                                        }
                                    }
                                    else
                                    {
                                        senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("LEVEL_LOWER_THAN_MONSTER"), 0));
                                        senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                    }
                                }
                                else
                                {
                                    senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CURRENT_HP_TOO_HIGH"), 0));
                                    senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                }
                            }
                            else
                            {
                                senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("MONSTER_CANT_BE_CAPTURED"), 0));
                                senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                            }
                        }
                    }
                }
                break;

            case BCardType.CardType.SpecialDamageAndExplosions:
                break;

            case BCardType.CardType.SpecialEffects2:
                break;

            case BCardType.CardType.CalculatingLevel:
                break;

            case BCardType.CardType.Recovery:
                break;

            case BCardType.CardType.MaxHPMP:
                break;

            case BCardType.CardType.MultAttack:
                break;

            case BCardType.CardType.MultDefence:
                break;

            case BCardType.CardType.TimeCircleSkills:
                break;

            case BCardType.CardType.RecoveryAndDamagePercent:
                break;

            case BCardType.CardType.Count:
                break;

            case BCardType.CardType.NoDefeatAndNoDamage:
                break;

            case BCardType.CardType.SpecialActions:
                break;

            case BCardType.CardType.Mode:
                break;

            case BCardType.CardType.NoCharacteristicValue:
                break;

            case BCardType.CardType.LightAndShadow:
                break;

            case BCardType.CardType.Item:
                break;

            case BCardType.CardType.DebuffResistance:
                break;

            case BCardType.CardType.SpecialBehaviour:
                break;

            case BCardType.CardType.Quest:
                break;

            case BCardType.CardType.SecondSPCard:
                break;

            case BCardType.CardType.SPCardUpgrade:
                break;

            case BCardType.CardType.HugeSnowman:
                break;

            case BCardType.CardType.Drain:
                break;

            case BCardType.CardType.BossMonstersSkill:
                break;

            case BCardType.CardType.LordHatus:
                break;

            case BCardType.CardType.LordCalvinas:
                break;

            case BCardType.CardType.SESpecialist:
                break;

            case BCardType.CardType.FourthGlacernonFamilyRaid:
                break;

            case BCardType.CardType.SummonedMonsterAttack:
                break;

            case BCardType.CardType.BearSpirit:
                break;

            case BCardType.CardType.SummonSkill:
                break;

            case BCardType.CardType.InflictSkill:
                break;

            case BCardType.CardType.HideBarrelSkill:
                break;

            case BCardType.CardType.FocusEnemyAttentionSkill:
                break;

            case BCardType.CardType.TauntSkill:
                break;

            case BCardType.CardType.FireCannoneerRangeBuff:
                break;

            case BCardType.CardType.VulcanoElementBuff:
                break;

            case BCardType.CardType.DamageConvertingSkill:
                break;

            case BCardType.CardType.MeditationSkill:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    if (SkillVNum.HasValue && SubType.Equals((byte)AdditionalTypes.MeditationSkill.CausingChance / 10) && ServerManager.RandomNumber() < FirstData)
                    {
                        Skill skill    = ServerManager.GetSkill(SkillVNum.Value);
                        Skill newSkill = ServerManager.GetSkill((short)SecondData);
                        Observable.Timer(TimeSpan.FromMilliseconds(100)).Subscribe(observer =>
                            {
                                foreach (QuicklistEntryDTO quicklistEntry in character.QuicklistEntries.Where(s => s.Pos.Equals(skill.CastId)))
                                {
                                    character.Session.SendPacket($"qset {quicklistEntry.Q1} {quicklistEntry.Q2} {quicklistEntry.Type}.{quicklistEntry.Slot}.{newSkill.CastId}.0");
                                }
                                character.Session.SendPacket($"mslot {newSkill.CastId} -1");
                            });
                        character.SkillComboCount++;
                        character.LastSkillComboUse = DateTime.Now;
                        if (skill.CastId > 10)
                        {
                            // HACK this way
                            Observable.Timer(TimeSpan.FromMilliseconds((skill.Cooldown * 100) + 500)).Subscribe(observer => character.Session.SendPacket(StaticPacketHelper.SkillReset(skill.CastId)));
                        }
                    }
                    switch (SubType)
                    {
                    case 2:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(4);
                        break;

                    case 3:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(8);
                        break;

                    case 4:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(12);
                        break;
                    }
                }
            }
            break;

            case BCardType.CardType.FalconSkill:
                break;

            case BCardType.CardType.AbsorptionAndPowerSkill:
                break;

            case BCardType.CardType.LeonaPassiveSkill:
                break;

            case BCardType.CardType.FearSkill:
                break;

            case BCardType.CardType.SniperAttack:
                break;

            case BCardType.CardType.FrozenDebuff:
                break;

            case BCardType.CardType.JumpBackPush:
                break;

            case BCardType.CardType.FairyXPIncrease:
                break;

            case BCardType.CardType.SummonAndRecoverHP:
                break;

            case BCardType.CardType.TeamArenaBuff:
                break;

            case BCardType.CardType.ArenaCamera:
                break;

            case BCardType.CardType.DarkCloneSummon:
                break;

            case BCardType.CardType.AbsorbedSpirit:
                break;

            case BCardType.CardType.AngerSkill:
                break;

            case BCardType.CardType.MeteoriteTeleport:
                break;

            case BCardType.CardType.StealBuff:
                break;

            case BCardType.CardType.Unknown:
                break;

            case BCardType.CardType.EffectSummon:
                break;

            default:
                Logger.Warn($"Card Type {Type} not defined!");
                break;
            }
        }
Beispiel #6
0
        public override void Use(ClientSession session, ref ItemInstance inv, byte Option = 0, string[] packetsplit = null)
        {
            if (session.Character.IsVehicled)
            {
                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("CANT_DO_VEHICLED"), 10));
                return;
            }

            if (session.CurrentMapInstance.MapInstanceType == MapInstanceType.TalentArenaMapInstance)
            {
                return;
            }

            if (packetsplit == null)
            {
                return;
            }

            void releasePet(MateType mateType, Guid itemToRemoveId)
            {
                if (int.TryParse(packetsplit[3], out int mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId && s.MateType == mateType);
                    if (mate != null)
                    {
                        if (!mate.IsTeamMember)
                        {
                            List <ItemInstance> mateInventory = mate.GetInventory();
                            if (mateInventory.Count > 0)
                            {
                                session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("EQ_NOT_EMPTY"), 0));
                            }
                            else
                            {
                                session.Character.Mates.Remove(mate);
                                byte i = 0;
                                session.Character.Mates.Where(s => s.MateType == MateType.Partner).ToList().ForEach(s =>
                                {
                                    s.GetInventory().ForEach(item => item.Type = (InventoryType)(13 + i));
                                    s.PetId = i;
                                    i++;
                                });
                                session.SendPacket(UserInterfaceHelper.GenerateInfo(Language.Instance.GetMessageFromKey("PET_RELEASED")));
                                session.SendPacket(UserInterfaceHelper.GeneratePClear());
                                session.SendPackets(session.Character.GenerateScP());
                                session.SendPackets(session.Character.GenerateScN());
                                session.CurrentMapInstance?.Broadcast(mate.GenerateOut());
                                session.Character.Inventory.RemoveItemFromInventory(itemToRemoveId);
                            }
                        }
                        else
                        {
                            session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("PET_IN_TEAM_UNRELEASABLE"), 0));
                        }
                    }
                }
            }

            if (BCards.Count > 0 && session.Character.MapInstance == session.Character.Miniland)
            {
                BCards.ForEach(c => c.ApplyBCards(session.Character.BattleEntity, session.Character.BattleEntity));
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                return;
            }

            switch (Effect)
            {
            case 10:
                if (int.TryParse(packetsplit[3], out int mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate == null || mate.MateType != MateType.Pet || mate.Loyalty >= 1000)
                    {
                        return;
                    }
                    mate.Loyalty += 100;
                    if (mate.Loyalty > 1000)
                    {
                        mate.Loyalty = 1000;
                    }
                    mate.GenerateXp(EffectValue);
                    session.SendPacket(mate.GenerateCond());
                    session.SendPacket(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            case 11:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate == null || mate.MateType != MateType.Pet || mate.Level >= session.Character.Level - 5 || mate.Level + 1 > ServerManager.Instance.Configuration.MaxLevel)
                    {
                        return;
                    }
                    mate.Level++;
                    mate.Hp = mate.MaxHp;
                    mate.Mp = mate.MaxMp;
                    session.SendPacket($"say 2 {mate.MateTransportId} 0 " + Language.Instance.GetMessageFromKey("MATE_POWER_INCREASED"));
                    session.SendPackets(session.Character.GenerateScP());
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 8), mate.PositionX, mate.PositionY);
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 198), mate.PositionX, mate.PositionY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            case 12:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate == null || mate.MateType != MateType.Partner || mate.Level >= session.Character.Level - 5 || mate.Level + 1 > ServerManager.Instance.Configuration.MaxLevel)
                    {
                        return;
                    }
                    mate.Level++;
                    mate.Hp = mate.MaxHp;
                    mate.Mp = mate.MaxMp;
                    session.SendPacket($"say 2 {mate.MateTransportId} 0 " + Language.Instance.GetMessageFromKey("MATE_POWER_INCREASED"));
                    session.SendPackets(session.Character.GenerateScN());
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 8), mate.PositionX, mate.PositionY);
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 198), mate.PositionX, mate.PositionY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            case 13:
                if (int.TryParse(packetsplit[3], out mateTransportId) && session.Character.Mates.FirstOrDefault(s => s.MateTransportId == mateTransportId) is Mate pet)
                {
                    if (pet.MateType == MateType.Pet)
                    {
                        session.SendPacket(UserInterfaceHelper.GenerateGuri(10, 1, mateTransportId, 2));
                    }
                    else
                    {
                        session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CANT_CHANGE_PARTNER_NAME"), 0));
                    }
                }
                break;

            case 14:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    if (session.Character.MapInstance == session.Character.Miniland)
                    {
                        Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId && s.MateType == MateType.Pet);
                        if (mate?.CanPickUp == false)
                        {
                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                            session.SendPacket($"say 2 {mate.MateTransportId} 0 " + Language.Instance.GetMessageFromKey("PET_SMART"));
                            mate.CanPickUp = true;
                            session.SendPackets(session.Character.GenerateScP());
                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_CAN_PICK_UP"), 10));
                            session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                        }
                    }
                    else
                    {
                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("NOT_IN_MINILAND"), 12));
                    }
                }
                break;

            case 16:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate == null || mate.MateType != MateType.Pet || mate.Level == 1)
                    {
                        return;
                    }
                    mate.Level--;
                    mate.Hp = mate.MaxHp;
                    mate.Mp = mate.MaxMp;
                    session.SendPacket($"say 2 {mate.MateTransportId} 0 " + Language.Instance.GetMessageFromKey("MATE_POWER_DECREASED"));
                    session.SendPackets(session.Character.GenerateScP());
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 198), mate.PositionX, mate.PositionY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            case 17:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate?.IsSummonable == false)
                    {
                        mate.IsSummonable = true;
                        session.SendPackets(session.Character.GenerateScP());
                        session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("PET_SUMMONABLE"), mate.Name), 10));
                        session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("PET_SUMMONABLE"), mate.Name), 0));
                        session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    }
                }
                break;

            case 18:
                if (int.TryParse(packetsplit[3], out mateTransportId))
                {
                    Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                    if (mate == null || mate.MateType != MateType.Partner || mate.Level == 1)
                    {
                        return;
                    }
                    mate.Level--;
                    mate.Hp = mate.MaxHp;
                    mate.Mp = mate.MaxMp;
                    session.SendPacket($"say 2 {mate.MateTransportId} 0 " + Language.Instance.GetMessageFromKey("MATE_POWER_DECREASED"));
                    session.SendPackets(session.Character.GenerateScN());
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 198), mate.PositionX, mate.PositionY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            case 1000:
                releasePet(MateType.Pet, inv.Id);
                break;

            case 1001:
                releasePet(MateType.Partner, inv.Id);
                break;

            case 1339:
                int rndevolve = ServerManager.RandomNumber(0, 1000);
                if (rndevolve > 900)
                {
                    if (int.TryParse(packetsplit[3], out mateTransportId))
                    {
                        Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                        if (mate == null)
                        {
                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PICK_PET"), 10));
                            return;
                        }
                        if (mate.Level >= 30 && mate.NpcMonsterVNum == 649 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                        {
                            mate.Level          = 1;
                            mate.NpcMonsterVNum = 650;
                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                            session.SendPackets(session.Character.GenerateScP());
                            session.SendPackets(session.Character.GenerateScN());
                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                            if (session?.Character != null)
                            {
                                if (session.Character.Miniland == session.Character.MapInstance)
                                {
                                    ServerManager.Instance.JoinMiniland(session, session);
                                }
                                else
                                {
                                    ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                             session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                             true);
                                    session.SendPacket(StaticPacketHelper.Cancel(2));
                                }
                            }
                        }
                        else
                        {
                            if (mate.Level >= 30 && mate.NpcMonsterVNum == 648 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                            {
                                mate.Level          = 1;
                                mate.NpcMonsterVNum = 649;
                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                session.SendPackets(session.Character.GenerateScP());
                                session.SendPackets(session.Character.GenerateScN());
                                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                if (session?.Character != null)
                                {
                                    if (session.Character.Miniland == session.Character.MapInstance)
                                    {
                                        ServerManager.Instance.JoinMiniland(session, session);
                                    }
                                    else
                                    {
                                        ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                 session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                 true);
                                        session.SendPacket(StaticPacketHelper.Cancel(2));
                                    }
                                }
                            }
                            else
                            {
                                if (mate.Level >= 30 && mate.NpcMonsterVNum == 651 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                {
                                    mate.Level          = 1;
                                    mate.NpcMonsterVNum = 652;
                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                    session.SendPackets(session.Character.GenerateScP());
                                    session.SendPackets(session.Character.GenerateScN());
                                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                    if (session?.Character != null)
                                    {
                                        if (session.Character.Miniland == session.Character.MapInstance)
                                        {
                                            ServerManager.Instance.JoinMiniland(session, session);
                                        }
                                        else
                                        {
                                            ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                     session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                     true);
                                            session.SendPacket(StaticPacketHelper.Cancel(2));
                                        }
                                    }
                                }
                                else
                                {
                                    if (mate.Level >= 30 && mate.NpcMonsterVNum == 652 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                    {
                                        mate.Level          = 1;
                                        mate.NpcMonsterVNum = 653;
                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                        session.SendPackets(session.Character.GenerateScP());
                                        session.SendPackets(session.Character.GenerateScN());
                                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                        if (session?.Character != null)
                                        {
                                            if (session.Character.Miniland == session.Character.MapInstance)
                                            {
                                                ServerManager.Instance.JoinMiniland(session, session);
                                            }
                                            else
                                            {
                                                ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                         session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                         true);
                                                session.SendPacket(StaticPacketHelper.Cancel(2));
                                            }
                                        }
                                    }
                                    else
                                    {
                                        if (mate.Level >= 30 && mate.NpcMonsterVNum == 660 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                        {
                                            mate.Level          = 1;
                                            mate.NpcMonsterVNum = 661;
                                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                            session.SendPackets(session.Character.GenerateScP());
                                            session.SendPackets(session.Character.GenerateScN());
                                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                            if (session?.Character != null)
                                            {
                                                if (session.Character.Miniland == session.Character.MapInstance)
                                                {
                                                    ServerManager.Instance.JoinMiniland(session, session);
                                                }
                                                else
                                                {
                                                    ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                             session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                             true);
                                                    session.SendPacket(StaticPacketHelper.Cancel(2));
                                                }
                                            }
                                        }
                                        else
                                        {
                                            if (mate.Level >= 30 && mate.NpcMonsterVNum == 661 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                            {
                                                mate.Level          = 1;
                                                mate.NpcMonsterVNum = 662;
                                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                session.SendPackets(session.Character.GenerateScP());
                                                session.SendPackets(session.Character.GenerateScN());
                                                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                if (session?.Character != null)
                                                {
                                                    if (session.Character.Miniland == session.Character.MapInstance)
                                                    {
                                                        ServerManager.Instance.JoinMiniland(session, session);
                                                    }
                                                    else
                                                    {
                                                        ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                 session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                 true);
                                                        session.SendPacket(StaticPacketHelper.Cancel(2));
                                                    }
                                                }
                                            }
                                            else
                                            {
                                                if (mate.Level >= 30 && mate.NpcMonsterVNum == 657 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                {
                                                    mate.Level          = 1;
                                                    mate.NpcMonsterVNum = 658;
                                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                    session.SendPackets(session.Character.GenerateScP());
                                                    session.SendPackets(session.Character.GenerateScN());
                                                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                    if (session?.Character != null)
                                                    {
                                                        if (session.Character.Miniland == session.Character.MapInstance)
                                                        {
                                                            ServerManager.Instance.JoinMiniland(session, session);
                                                        }
                                                        else
                                                        {
                                                            ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                     session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                     true);
                                                            session.SendPacket(StaticPacketHelper.Cancel(2));
                                                        }
                                                    }
                                                }
                                                else
                                                {
                                                    if (mate.Level >= 30 && mate.NpcMonsterVNum == 658 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                    {
                                                        mate.Level          = 1;
                                                        mate.NpcMonsterVNum = 659;
                                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                        session.SendPackets(session.Character.GenerateScP());
                                                        session.SendPackets(session.Character.GenerateScN());
                                                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                        if (session?.Character != null)
                                                        {
                                                            if (session.Character.Miniland == session.Character.MapInstance)
                                                            {
                                                                ServerManager.Instance.JoinMiniland(session, session);
                                                            }
                                                            else
                                                            {
                                                                ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                         session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                         true);
                                                                session.SendPacket(StaticPacketHelper.Cancel(2));
                                                            }
                                                        }
                                                    }
                                                    else
                                                    {
                                                        if (mate.Level >= 30 && mate.NpcMonsterVNum == 660 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                        {
                                                            mate.Level          = 1;
                                                            mate.NpcMonsterVNum = 661;
                                                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                            session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                            session.SendPackets(session.Character.GenerateScP());
                                                            session.SendPackets(session.Character.GenerateScN());
                                                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                            if (session?.Character != null)
                                                            {
                                                                if (session.Character.Miniland == session.Character.MapInstance)
                                                                {
                                                                    ServerManager.Instance.JoinMiniland(session, session);
                                                                }
                                                                else
                                                                {
                                                                    ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                             session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                             true);
                                                                    session.SendPacket(StaticPacketHelper.Cancel(2));
                                                                }
                                                            }
                                                        }
                                                        else
                                                        {
                                                            if (mate.Level >= 30 && mate.NpcMonsterVNum == 988 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                            {
                                                                mate.Level          = 1;
                                                                mate.NpcMonsterVNum = 416;
                                                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                                session.SendPackets(session.Character.GenerateScP());
                                                                session.SendPackets(session.Character.GenerateScN());
                                                                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                                if (session?.Character != null)
                                                                {
                                                                    if (session.Character.Miniland == session.Character.MapInstance)
                                                                    {
                                                                        ServerManager.Instance.JoinMiniland(session, session);
                                                                    }
                                                                    else
                                                                    {
                                                                        ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                                 session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                                 true);
                                                                        session.SendPacket(StaticPacketHelper.Cancel(2));
                                                                    }
                                                                }
                                                            }
                                                            else
                                                            {
                                                                if (mate.Level >= 30 && mate.NpcMonsterVNum == 416 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                                {
                                                                    mate.Level          = 1;
                                                                    mate.NpcMonsterVNum = 412;
                                                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                                    session.SendPackets(session.Character.GenerateScP());
                                                                    session.SendPackets(session.Character.GenerateScN());
                                                                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                                    if (session?.Character != null)
                                                                    {
                                                                        if (session.Character.Miniland == session.Character.MapInstance)
                                                                        {
                                                                            ServerManager.Instance.JoinMiniland(session, session);
                                                                        }
                                                                        else
                                                                        {
                                                                            ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                                     session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                                     true);
                                                                            session.SendPacket(StaticPacketHelper.Cancel(2));
                                                                        }
                                                                    }
                                                                }
                                                                else
                                                                {
                                                                    if (mate.Level >= 30 && mate.NpcMonsterVNum == 412 && mate.IsTeamMember == true && mate.MateType == MateType.Pet)
                                                                    {
                                                                        mate.Level          = 1;
                                                                        mate.NpcMonsterVNum = 414;
                                                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5));
                                                                        session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Npc, mate.MateTransportId, 5002));
                                                                        session.SendPackets(session.Character.GenerateScP());
                                                                        session.SendPackets(session.Character.GenerateScN());
                                                                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_EVOLED"), 10));
                                                                        if (session?.Character != null)
                                                                        {
                                                                            if (session.Character.Miniland == session.Character.MapInstance)
                                                                            {
                                                                                ServerManager.Instance.JoinMiniland(session, session);
                                                                            }
                                                                            else
                                                                            {
                                                                                ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId,
                                                                                                                         session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY,
                                                                                                                         true);
                                                                                session.SendPacket(StaticPacketHelper.Cancel(2));
                                                                            }
                                                                        }
                                                                    }
                                                                    else
                                                                    {
                                                                    }
                                                                }
                                                            }
                                                        }
                                                        break;
                                                    }
                                                    break;
                                                }
                                                break;
                                            }
                                            break;
                                        }
                                        break;
                                    }
                                    break;
                                }
                                break;
                            }
                            break;
                        }
                        break;
                    }
                    else
                    {
                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_NOT_EVOLED"), 10));
                    }
                    break;
                }
                else
                {
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_NOT_EVOLED"), 10));
                }
                break;

            case 2137:
                int rnd = ServerManager.RandomNumber(0, 1000);
                {
                    if (int.TryParse(packetsplit[3], out mateTransportId))
                    {
                        Mate mate = session.Character.Mates.Find(s => s.MateTransportId == mateTransportId);
                        if (mate == null)
                        {
                            session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("PICK_PET"), 10));
                        }
                        else
                        if (mate.Defence <= 9 || mate.Attack <= 9)
                        {
                            if (rnd >= 600 && rnd <= 800)
                            {
                                mate.Attack++;
                                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("ATTACK_PLUS"), 10));
                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3004), session.Character.MapX, session.Character.MapY);
                            }
                            else if (rnd >= 801 && rnd <= 1000)
                            {
                                mate.Defence++;
                                session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("DEF_PLUS"), 10));
                                session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3004), session.Character.MapX, session.Character.MapY);
                            }
                            else if (rnd <= 800 && rnd >= 400)
                            {
                                if (mate.Defence == 0)
                                {
                                    return;
                                }
                                else
                                {
                                    mate.Defence--;
                                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("DEF_MINUS"), 10));
                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3005), session.Character.MapX, session.Character.MapY);
                                }
                            }
                            else if (rnd <= 399 && rnd >= 0)
                            {
                                if (mate.Attack == 0)
                                {
                                    return;
                                }
                                else
                                {
                                    mate.Attack--;
                                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("ATTACK_MINUS"), 10));
                                    session.CurrentMapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3005), session.Character.MapX, session.Character.MapY);
                                }
                            }
                            else
                            {
                                return;
                            }
                        }
                        else
                        {
                            return;
                        }
                    }
                    else
                    {
                        return;
                    }
                    session.Character.Inventory.RemoveItemAmount(2079, 1);
                }
                break;

            default:
                Logger.Warn(string.Format(Language.Instance.GetMessageFromKey("NO_HANDLER_ITEM"), GetType(), VNum, Effect, EffectValue));
                break;
            }
        }
Beispiel #7
0
        /// <summary>
        /// Handle any kind of Monster interaction
        /// </summary>
        private void monsterLife()
        {
            if (Monster == null)
            {
                return;
            }
            if ((DateTime.Now - LastEffect).TotalSeconds >= 5)
            {
                LastEffect = DateTime.Now;
                if (IsTarget)
                {
                    MapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Monster, MapMonsterId, 824));
                }
                if (IsBonus)
                {
                    MapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Monster, MapMonsterId, 826));
                }
            }

            if (IsBoss && IsAlive)
            {
                MapInstance.Broadcast(GenerateBoss());
            }

            // handle hit queue
            while (HitQueue.TryDequeue(out HitRequest hitRequest))
            {
                if (IsAlive && hitRequest.Session.Character.Hp > 0 && (ServerManager.Instance.ChannelId != 51 || MonsterVNum - (byte)hitRequest.Session.Character.Faction != 678))
                {
                    int  hitmode        = 0;
                    bool isCaptureSkill = hitRequest.Skill.BCards.Any(s => s.Type.Equals((byte)CardType.Capture));

                    // calculate damage
                    bool         onyxWings    = false;
                    BattleEntity battleEntity = new BattleEntity(hitRequest.Session.Character, hitRequest.Skill);
                    int          damage       = DamageHelper.Instance.CalculateDamage(battleEntity, new BattleEntity(this), hitRequest.Skill, ref hitmode, ref onyxWings);
                    if (onyxWings)
                    {
                        short      onyxX  = (short)(hitRequest.Session.Character.PositionX + 2);
                        short      onyxY  = (short)(hitRequest.Session.Character.PositionY + 2);
                        int        onyxId = MapInstance.GetNextMonsterId();
                        MapMonster onyx   = new MapMonster()
                        {
                            MonsterVNum = 2371, MapX = onyxX, MapY = onyxY, MapMonsterId = onyxId, IsHostile = false, IsMoving = false, ShouldRespawn = false
                        };
                        MapInstance.Broadcast(UserInterfaceHelper.Instance.GenerateGuri(31, 1, hitRequest.Session.Character.CharacterId, onyxX, onyxY));
                        onyx.Initialize(MapInstance);
                        MapInstance.AddMonster(onyx);
                        MapInstance.Broadcast(onyx.GenerateIn());
                        CurrentHp -= damage / 2;
                        Observable.Timer(TimeSpan.FromMilliseconds(350)).Subscribe(o =>
                        {
                            MapInstance.Broadcast(StaticPacketHelper.SkillUsed(UserType.Monster, onyxId, 3, MapMonsterId, -1, 0, -1, hitRequest.Skill.Effect, -1, -1, true, 92, damage / 2, 0, 0));
                            MapInstance.RemoveMonster(onyx);
                            MapInstance.Broadcast(StaticPacketHelper.Out(UserType.Monster, onyx.MapMonsterId));
                        });
                    }
                    if (hitmode != 1)
                    {
                        hitRequest.Skill.BCards.Where(s => s.Type.Equals((byte)CardType.Buff)).ToList().ForEach(s => s.ApplyBCards(this, hitRequest.Session));
                        hitRequest.Skill.BCards.Where(s => s.Type.Equals((byte)CardType.Capture)).ToList().ForEach(s => s.ApplyBCards(this, hitRequest.Session));
                        if (battleEntity?.ShellWeaponEffects != null)
                        {
                            foreach (ShellEffectDTO shell in battleEntity.ShellWeaponEffects)
                            {
                                switch (shell.Effect)
                                {
                                case (byte)ShellWeaponEffectType.Blackout:
                                {
                                    Buff buff = new Buff(7, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }

                                case (byte)ShellWeaponEffectType.DeadlyBlackout:
                                {
                                    Buff buff = new Buff(66, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }

                                case (byte)ShellWeaponEffectType.MinorBleeding:
                                {
                                    Buff buff = new Buff(1, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }

                                case (byte)ShellWeaponEffectType.Bleeding:
                                {
                                    Buff buff = new Buff(21, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }

                                case (byte)ShellWeaponEffectType.HeavyBleeding:
                                {
                                    Buff buff = new Buff(42, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }

                                case (byte)ShellWeaponEffectType.Freeze:
                                {
                                    Buff buff = new Buff(27, battleEntity.Level);
                                    if (ServerManager.Instance.RandomNumber() < shell.Value)
                                    {
                                        AddBuff(buff);
                                    }
                                    break;
                                }
                                }
                            }
                        }
                    }
                    if (DamageList.ContainsKey(hitRequest.Session.Character.CharacterId))
                    {
                        DamageList[hitRequest.Session.Character.CharacterId] += damage;
                    }
                    else
                    {
                        DamageList.Add(hitRequest.Session.Character.CharacterId, damage);
                    }
                    if (isCaptureSkill)
                    {
                        damage = 0;
                    }
                    if (CurrentHp <= damage)
                    {
                        SetDeathStatement();
                    }
                    else
                    {
                        CurrentHp -= damage;
                    }

                    // only set the hit delay if we become the monsters target with this hit
                    if (Target == -1)
                    {
                        LastSkill = DateTime.Now;
                    }

                    int nearestDistance = 100;
                    foreach (KeyValuePair <long, long> kvp in DamageList)
                    {
                        ClientSession session = MapInstance.GetSessionByCharacterId(kvp.Key);
                        if (session != null)
                        {
                            int distance = Map.GetDistance(new MapCell
                            {
                                X = MapX,
                                Y = MapY
                            }, new MapCell
                            {
                                X = session.Character.PositionX,
                                Y = session.Character.PositionY
                            });
                            if (distance < nearestDistance)
                            {
                                nearestDistance = distance;
                                Target          = session.Character.CharacterId;
                            }
                        }
                    }

                    switch (hitRequest.TargetHitType)
                    {
                    case TargetHitType.SingleTargetHit:
                        if (!isCaptureSkill)
                        {
                            MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        }
                        break;

                    case TargetHitType.SingleTargetHitCombo:
                        MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.SkillCombo.Animation, hitRequest.SkillCombo.Effect, hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        break;

                    case TargetHitType.SingleAOETargetHit:
                        switch (hitmode)
                        {
                        case 1:
                            hitmode = 4;
                            break;

                        case 3:
                            hitmode = 6;
                            break;

                        default:
                            hitmode = 5;
                            break;
                        }
                        if (hitRequest.ShowTargetHitAnimation)
                        {
                            MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        }
                        else
                        {
                            MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, 0, 0, 0, 0, 0, 0, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        }
                        break;

                    case TargetHitType.AOETargetHit:
                        switch (hitmode)
                        {
                        case 1:
                            hitmode = 4;
                            break;

                        case 3:
                            hitmode = 6;
                            break;

                        default:
                            hitmode = 5;
                            break;
                        }
                        MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        break;

                    case TargetHitType.ZoneHit:
                        MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.MapX, hitRequest.MapY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, 5, (byte)(hitRequest.Skill.SkillType - 1)));
                        break;

                    case TargetHitType.SpecialZoneHit:
                        MapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, hitRequest.Session.Character.CharacterId, 3, MapMonsterId, hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY, IsAlive, (int)((float)CurrentHp / (float)MaxHp * 100), damage, hitmode, (byte)(hitRequest.Skill.SkillType - 1)));
                        break;
                    }

                    if (CurrentHp <= 0 && !isCaptureSkill)
                    {
                        // generate the kill bonus
                        hitRequest.Session.Character.GenerateKillBonus(this);
                    }
                }
                else
                {
                    // monster already has been killed, send cancel
                    hitRequest.Session.SendPacket(StaticPacketHelper.Cancel(2, MapMonsterId));
                }
                if (IsBoss)
                {
                    MapInstance.Broadcast(GenerateBoss());
                }
            }

            // Respawn
            if (!IsAlive && ShouldRespawn != null && !ShouldRespawn.Value)
            {
                MapInstance.RemoveMonster(this);
            }
            if (!IsAlive && ShouldRespawn != null && ShouldRespawn.Value)
            {
                double timeDeath = (DateTime.Now - Death).TotalSeconds;
                if (timeDeath >= Monster.RespawnTime / 10d)
                {
                    respawn();
                }
            }

            // normal movement
            else if (Target == -1)
            {
                move();
            }

            // target following
            else if (MapInstance != null)
            {
                GetNearestOponent();
                HostilityTarget();

                ClientSession targetSession = MapInstance.GetSessionByCharacterId(Target);

                // remove target in some situations
                if (targetSession == null || targetSession.Character.Invisible || targetSession.Character.Hp <= 0 || CurrentHp <= 0)
                {
                    RemoveTarget();
                    return;
                }

                NpcMonsterSkill npcMonsterSkill = null;
                if (Skills != null && ServerManager.Instance.RandomNumber(0, 10) > 8)
                {
                    npcMonsterSkill = Skills.Where(s => (DateTime.Now - s.LastSkillUse).TotalMilliseconds >= 100 * s.Skill?.Cooldown)?.OrderBy(rnd => _random.Next())?.FirstOrDefault();
                }

                if (npcMonsterSkill?.Skill.TargetType == 1 && npcMonsterSkill?.Skill.HitType == 0)
                {
                    targetHit(targetSession, npcMonsterSkill);
                }

                // check if target is in range
                if (!targetSession.Character.InvisibleGm && !targetSession.Character.Invisible && targetSession.Character.Hp > 0)
                {
                    if (npcMonsterSkill != null && CurrentMp >= npcMonsterSkill.Skill.MpCost &&
                        Map.GetDistance(new MapCell
                    {
                        X = MapX,
                        Y = MapY
                    },
                                        new MapCell
                    {
                        X = targetSession.Character.PositionX,
                        Y = targetSession.Character.PositionY
                    }) < npcMonsterSkill.Skill.Range)
                    {
                        targetHit(targetSession, npcMonsterSkill);
                    }
                    else if (Map.GetDistance(new MapCell
                    {
                        X = MapX,
                        Y = MapY
                    },
                                             new MapCell
                    {
                        X = targetSession.Character.PositionX,
                        Y = targetSession.Character.PositionY
                    }) <= Monster.BasicRange)
                    {
                        targetHit(targetSession, npcMonsterSkill);
                    }
                    else
                    {
                        followTarget(targetSession);
                    }
                }
                else
                {
                    followTarget(targetSession);
                }
            }
        }
Beispiel #8
0
        internal static void AttackCharacter(this ClientSession session, Mate attacker, NpcMonsterSkill skill, Character target)
        {
            if (attacker == null || target == null)
            {
                return;
            }

            if (target.Hp > 0 && attacker.Hp > 0)
            {
                if ((session.CurrentMapInstance.MapInstanceId == ServerManager.Instance.ArenaInstance.MapInstanceId ||
                     session.CurrentMapInstance.MapInstanceId
                     == ServerManager.Instance.FamilyArenaInstance.MapInstanceId) &&
                    (session.CurrentMapInstance.Map.JaggedGrid[session.Character.PositionX][
                         session.Character.PositionY]?.Value != 0 ||
                     target.Session.CurrentMapInstance.Map.JaggedGrid[target.PositionX][
                         target.PositionY]
                     ?.Value != 0))
                {
                    // User in SafeZone
                    session.SendPacket(StaticPacketHelper.Cancel(2, target.CharacterId));
                    return;
                }

                if (target.IsSitting)
                {
                    target.Rest();
                }

                short castAnimation = -1;
                short castEffect    = -1;
                short skillVnum     = 0;
                short cooldown      = 0;
                byte  type          = 0;

                if (skill != null)
                {
                    castAnimation = skill.Skill.CastAnimation;
                    castEffect    = skill.Skill.CastEffect;
                    skillVnum     = skill.SkillVNum;
                    cooldown      = skill.Skill.Cooldown;
                    type          = skill.Skill.Type;
                }

                var          hitmode             = 0;
                var          onyxWings           = false;
                BattleEntity battleEntity        = new BattleEntity(attacker);
                BattleEntity battleEntityDefense = new BattleEntity(target);
                session.CurrentMapInstance?.Broadcast(StaticPacketHelper.CastOnTarget(UserType.Npc,
                                                                                      attacker.MateTransportId, 3, target.CharacterId, castAnimation, castEffect, skillVnum));
                session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Npc, attacker.MateTransportId, 3, target.CharacterId, skillVnum, cooldown, castAnimation, castEffect, target.MapX, target.MapY, target.Hp > 0, (int)(target.Hp / (double)target.HPMax * 100), 0, 0, type));
                var damage = DamageHelper.Instance.CalculateDamage(battleEntity, battleEntityDefense, skill?.Skill,
                                                                   ref hitmode, ref onyxWings);
                if (target.HasGodMode)
                {
                    damage  = 0;
                    hitmode = 1;
                }
                else if (target.LastPvpRevive > DateTime.Now.AddSeconds(-10) ||
                         session.Character.LastPvpRevive > DateTime.Now.AddSeconds(-10))
                {
                    damage  = 0;
                    hitmode = 1;
                }

                int[] manaShield = target.GetBuff(BCardType.CardType.LightAndShadow,
                                                  (byte)AdditionalTypes.LightAndShadow.InflictDamageToMP);
                if (manaShield[0] != 0 && hitmode != 1)
                {
                    var reduce = damage / 100 * manaShield[0];
                    if (target.Mp < reduce)
                    {
                        target.Mp = 0;
                    }
                    else
                    {
                        target.Mp -= reduce;
                    }
                }

                target.GetDamage(damage / 2);
                target.LastDefence = DateTime.Now;
                target.Session.SendPacket(target.GenerateStat());
                var isAlive = target.Hp > 0;
                if (!isAlive && target.Session.HasCurrentMapInstance)
                {
                    if (target.Session.CurrentMapInstance.Map?.MapTypes.Any(
                            s => s.MapTypeId == (short)MapTypeEnum.Act4)
                        == true)
                    {
                        if (ServerManager.Instance.ChannelId == 51 && ServerManager.Instance.Act4DemonStat.Mode == 0 &&
                            ServerManager.Instance.Act4AngelStat.Mode == 0)
                        {
                            switch (session.Character.Faction)
                            {
                            case FactionType.Angel:
                                ServerManager.Instance.Act4AngelStat.Percentage += 100;
                                break;

                            case FactionType.Demon:
                                ServerManager.Instance.Act4DemonStat.Percentage += 100;
                                break;
                            }
                        }

                        session.Character.Act4Kill++;
                        target.Act4Dead++;
                        target.GetAct4Points(-1);
                        if (target.Level + 10 >= session.Character.Level &&
                            session.Character.Level <= target.Level - 10)
                        {
                            session.Character.GetAct4Points(2);
                        }

                        if (target.Reputation < 50000)
                        {
                            target.Session.SendPacket(session.Character.GenerateSay(
                                                          string.Format(Language.Instance.GetMessageFromKey("LOSE_REP"), 0), 11));
                        }
                        else
                        {
                            target.Reputation            -= target.Level * 50;
                            session.Character.Reputation += target.Level * 50;
                            session.SendPacket(session.Character.GenerateLev());
                            target.Session.SendPacket(target.GenerateSay(
                                                          string.Format(Language.Instance.GetMessageFromKey("LOSE_REP"),
                                                                        (short)(target.Level * 50)), 11));
                        }

                        foreach (ClientSession sess in ServerManager.Instance.Sessions.Where(
                                     s => s.HasSelectedCharacter))
                        {
                            if (sess.Character.Faction == session.Character.Faction)
                            {
                                sess.SendPacket(sess.Character.GenerateSay(
                                                    string.Format(
                                                        Language.Instance.GetMessageFromKey(
                                                            $"ACT4_PVP_KILL{(int)target.Faction}"), session.Character.Name),
                                                    12));
                            }
                            else if (sess.Character.Faction == target.Faction)
                            {
                                sess.SendPacket(sess.Character.GenerateSay(
                                                    string.Format(
                                                        Language.Instance.GetMessageFromKey(
                                                            $"ACT4_PVP_DEATH{(int)target.Faction}"), target.Name),
                                                    11));
                            }
                        }

                        target.Session.SendPacket(target.GenerateFd());
                        target.DisableBuffs(BuffType.All, force: true);
                        target.Session.CurrentMapInstance.Broadcast(target.Session, target.GenerateIn(),
                                                                    ReceiverType.AllExceptMe);
                        target.Session.CurrentMapInstance.Broadcast(target.Session, target.GenerateGidx(),
                                                                    ReceiverType.AllExceptMe);
                        target.Session.SendPacket(
                            target.GenerateSay(Language.Instance.GetMessageFromKey("ACT4_PVP_DIE"), 11));
                        target.Session.SendPacket(
                            UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ACT4_PVP_DIE"), 0));
                        Observable.Timer(TimeSpan.FromMilliseconds(2000)).Subscribe(o =>
                        {
                            target.Session.CurrentMapInstance?.Broadcast(target.Session,
                                                                         $"c_mode 1 {target.CharacterId} 1564 0 0 0");
                            target.Session.CurrentMapInstance?.Broadcast(target.GenerateRevive());
                        });
                        Observable.Timer(TimeSpan.FromMilliseconds(30000)).Subscribe(o =>
                        {
                            target.Hp = (int)target.HPLoad();
                            target.Mp = (int)target.MPLoad();
                            var x     = (short)(39 + ServerManager.RandomNumber <short>(-2, 3));
                            var y     = (short)(42 + ServerManager.RandomNumber <short>(-2, 3));
                            switch (target.Faction)
                            {
                            case FactionType.Angel:
                                ServerManager.Instance.ChangeMap(target.CharacterId, 130, x, y);
                                break;

                            case FactionType.Demon:
                                ServerManager.Instance.ChangeMap(target.CharacterId, 131, x, y);
                                break;

                            default:
                                {
                                    target.MapId   = 145;
                                    target.MapX    = 51;
                                    target.MapY    = 41;
                                    var connection =
                                        CommunicationServiceClient.Instance.RetrieveOriginWorld(session.Account.AccountId);
                                    if (string.IsNullOrWhiteSpace(connection))
                                    {
                                        return;
                                    }

                                    var port = Convert.ToInt32(connection.Split(':')[1]);
                                    session.Character.ChangeChannel(connection.Split(':')[0], port, 3);
                                    return;
                                }
                            }

                            target.Session.CurrentMapInstance?.Broadcast(target.Session, target.GenerateTp());
                            target.Session.CurrentMapInstance?.Broadcast(target.GenerateRevive());
                            target.Session.SendPacket(target.GenerateStat());
                        });
                    }
                }

                if (hitmode != 1)
                {
                    skill?.Skill?.BCards.Where(s => s.Type.Equals((byte)BCardType.CardType.Buff)).ToList()
                    .ForEach(s => s.ApplyBCards(target, session.Character));
                }

                session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Npc,
                                                                                   attacker.MateTransportId, 1, target.CharacterId, 0, 12, 11, 200, 0, 0, isAlive,
                                                                                   (int)(target.Hp / target.HPLoad() * 100), damage, hitmode, 0));
            }
            else
            {
                // monster already has been killed, send cancel
                session.SendPacket(StaticPacketHelper.Cancel(2, target.CharacterId));
            }
        }
Beispiel #9
0
        internal static void AttackCharacter(this ClientSession session, Mate attacker, Skill skil, Character target)
        {
            if (attacker == null || target == null)
            {
                return;
            }

            if (skil == null)
            {
                skil = ServerManager.GetSkill(200);
            }

            if (target.Hp > 0 && attacker.IsAlive)
            {
                if ((session.CurrentMapInstance.MapInstanceId == ServerManager.Instance.ArenaInstance.MapInstanceId ||
                     session.CurrentMapInstance.MapInstanceId
                     == ServerManager.Instance.FamilyArenaInstance.MapInstanceId) &&
                    (session.CurrentMapInstance.Map.JaggedGrid[session.Character.PositionX][
                         session.Character.PositionY]?.Value != 0 ||
                     target.Session.CurrentMapInstance.Map.JaggedGrid[target.PositionX][
                         target.PositionY]
                     ?.Value != 0))
                {
                    // User in SafeZone
                    session.SendPacket(StaticPacketHelper.Cancel(2, target.CharacterId));
                    return;
                }

                if (target.IsSitting)
                {
                    target.Rest();
                }

                int  hitmode   = 0;
                bool onyxWings = false;
                attacker.LastSkillUse = DateTime.UtcNow;
                BattleEntity battleEntity        = new BattleEntity(attacker);
                BattleEntity battleEntityDefense = new BattleEntity(target, null);
                session.CurrentMapInstance?.Broadcast(StaticPacketHelper.CastOnTarget(UserType.Npc,
                                                                                      attacker.MateTransportId, 1, target.CharacterId, skil.CastAnimation, skil.CastEffect, skil.SkillVNum));
                int damage = DamageHelper.Instance.CalculateDamage(battleEntity, battleEntityDefense, skil,
                                                                   ref hitmode, ref onyxWings);
                if (target.HasGodMode)
                {
                    damage  = 0;
                    hitmode = 1;
                }
                else if (target.LastPvpRevive > DateTime.UtcNow.AddSeconds(-10) ||
                         session.Character.LastPvpRevive > DateTime.UtcNow.AddSeconds(-10))
                {
                    damage  = 0;
                    hitmode = 1;
                }

                int[] manaShield = target.GetBuff(BCardType.CardType.LightAndShadow,
                                                  (byte)AdditionalTypes.LightAndShadow.InflictDamageToMP);
                if (manaShield[0] != 0 && hitmode != 1)
                {
                    int reduce = damage / 100 * manaShield[0];
                    if (target.Mp < reduce)
                    {
                        target.Mp = 0;
                    }
                    else
                    {
                        target.Mp -= reduce;
                    }
                }

                target.GetDamage(damage / 2);
                target.LastDefence = DateTime.UtcNow;
                target.Session.SendPacket(target.GenerateStat());
                bool isAlive = target.Hp > 0;
                if (!isAlive && target.Session.HasCurrentMapInstance)
                {
                    if (target.Session.CurrentMapInstance.Map?.MapTypes.Any(
                            s => s.MapTypeId == (short)MapTypeEnum.Act4)
                        == true)
                    {
                        if (ServerManager.Instance.ChannelId == 51 && ServerManager.Instance.Act4DemonStat.Mode == 0 &&
                            ServerManager.Instance.Act4AngelStat.Mode == 0)
                        {
                            switch (session.Character.Faction)
                            {
                            case FactionType.Angel:
                                ServerManager.Instance.Act4AngelStat.Percentage += 500;
                                break;

                            case FactionType.Demon:
                                ServerManager.Instance.Act4DemonStat.Percentage += 500;
                                break;
                            }
                        }

                        session.Character.Act4Kill++;
                        target.Act4Dead++;
                        target.GetAct4Points(-1);
                        if (target.Level + 20 >= session.Character.Level &&
                            session.Character.Level <= target.Level - 20)
                        {
                            session.Character.GetAct4Points(2);
                        }

                        if (target.Reputation < 9999999999)
                        {
                            target.Session.SendPacket(session.Character.GenerateSay(
                                                          string.Format(Language.Instance.GetMessageFromKey("LOSE_REP"), 0), 11));
                        }
                        else
                        {
                            target.Reputation            -= target.Level * 0;
                            session.Character.Reputation += target.Level * 150;
                            session.SendPacket(session.Character.GenerateLev());
                            target.Session.SendPacket(target.GenerateSay(
                                                          string.Format(Language.Instance.GetMessageFromKey("LOSE_REP"),
                                                                        (short)(target.Level * 0)), 11));
                        }

                        foreach (ClientSession sess in ServerManager.Instance.Sessions.Where(
                                     s => s.HasSelectedCharacter))
                        {
                            if (sess.Character.Faction == session.Character.Faction)
                            {
                                sess.SendPacket(sess.Character.GenerateSay(
                                                    string.Format(
                                                        Language.Instance.GetMessageFromKey(
                                                            $"ACT4_PVP_KILL{(int)target.Faction}"), session.Character.Name),
                                                    12));
                            }
                            else if (sess.Character.Faction == target.Faction)
                            {
                                sess.SendPacket(sess.Character.GenerateSay(
                                                    string.Format(
                                                        Language.Instance.GetMessageFromKey(
                                                            $"ACT4_PVP_DEATH{(int)target.Faction}"), target.Name),
                                                    11));
                            }
                        }

                        target.Session.SendPacket(target.GenerateFd());
                        target.DisableBuffs(BuffType.All, force: true);
                        target.Session.CurrentMapInstance.Broadcast(target.Session, target.GenerateIn(),
                                                                    ReceiverType.AllExceptMe);
                        target.Session.CurrentMapInstance.Broadcast(target.Session, target.GenerateGidx(),
                                                                    ReceiverType.AllExceptMe);
                        target.Session.SendPacket(
                            target.GenerateSay(Language.Instance.GetMessageFromKey("ACT4_PVP_DIE"), 11));
                        target.Session.SendPacket(
                            UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ACT4_PVP_DIE"), 0));
                        if (target.MapInstanceId == CaligorRaid.CaligorMapInstance?.MapInstanceId)
                        {
                            target.Hp = (int)target.HPLoad();
                            target.Mp = (int)target.MPLoad();
                            if (target.Faction == FactionType.Angel)
                            {
                                ServerManager.Instance.ChangeMapInstance(target.CharacterId, CaligorRaid.CaligorMapInstance.MapInstanceId, 70, 159);
                            }
                            else if (target.Faction == FactionType.Demon)
                            {
                                ServerManager.Instance.ChangeMapInstance(target.CharacterId, CaligorRaid.CaligorMapInstance.MapInstanceId, 110, 159);
                            }

                            target.Session.CurrentMapInstance?.Broadcast(target.Session, target.GenerateTp());
                            target.Session.CurrentMapInstance?.Broadcast(target.GenerateRevive());
                            target.Session.SendPacket(target.GenerateStat());
                            return;
                        }
                        Observable.Timer(TimeSpan.FromMilliseconds(2000)).Subscribe(o =>
                        {
                            target.Session.CurrentMapInstance?.Broadcast(target.Session,
                                                                         $"c_mode 1 {target.CharacterId} 1564 0 0 0");
                            target.Session.CurrentMapInstance?.Broadcast(target.GenerateRevive());
                        });
                        Observable.Timer(TimeSpan.FromMilliseconds(30000)).Subscribe(o =>
                        {
                            target.Hp = (int)target.HPLoad();
                            target.Mp = (int)target.MPLoad();
                            short x   = (short)(39 + ServerManager.RandomNumber(-2, 3));
                            short y   = (short)(42 + ServerManager.RandomNumber(-2, 3));
                            if (target.Faction == FactionType.Angel)
                            {
                                ServerManager.Instance.ChangeMap(target.CharacterId, 130, x, y);
                            }
                            else if (target.Faction == FactionType.Demon)
                            {
                                ServerManager.Instance.ChangeMap(target.CharacterId, 131, x, y);
                            }
                            else
                            {
                                target.MapId      = 145;
                                target.MapX       = 51;
                                target.MapY       = 41;
                                string connection =
                                    CommunicationServiceClient.Instance.RetrieveOriginWorld(session.Account.AccountId);
                                if (string.IsNullOrWhiteSpace(connection))
                                {
                                    return;
                                }

                                int port = Convert.ToInt32(connection.Split(':')[1]);
                                session.Character.ChangeChannel(connection.Split(':')[0], port, 3);
                                return;
                            }

                            target.Session.CurrentMapInstance?.Broadcast(target.Session, target.GenerateTp());
                            target.Session.CurrentMapInstance?.Broadcast(target.GenerateRevive());
                            target.Session.SendPacket(target.GenerateStat());
                        });
                    }
                    else
                    {
                        session.Character.TalentWin++;
                        target.TalentLose++;
                        session.CurrentMapInstance?.Broadcast(session.Character.GenerateSay(
                                                                  string.Format(Language.Instance.GetMessageFromKey("PVP_KILL"),
                                                                                session.Character.Name, target.Name), 10));
                        Observable.Timer(TimeSpan.FromMilliseconds(1000)).Subscribe(o =>
                                                                                    ServerManager.Instance.AskPvpRevive(target.CharacterId));
                    }
                }

                if (hitmode != 1)
                {
                    skil.BCards.Where(s => s.Type.Equals((byte)BCardType.CardType.Buff)).ToList()
                    .ForEach(s => s.ApplyBCards(target, session.Character));
                }

                session.SendPacket(StaticPacketHelper.GenerateEff(UserType.Npc, attacker.MateTransportId, 5005));
                Observable.Timer(TimeSpan.FromMilliseconds(skil.CastTime)).Subscribe(o =>
                {
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Npc,
                                                                                       attacker.MateTransportId, 1, target.CharacterId, skil.SkillVNum, skil.Cooldown,
                                                                                       skil.AttackAnimation, skil.Effect, 0, 0, target.Hp > 0,
                                                                                       (int)(target.Hp / (float)target.HPLoad() * 100), damage, hitmode, 0));
                });
                // switch (hitRequest.TargetHitType) { case TargetHitType.SingleTargetHit:
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect,
                // hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY,
                // isAlive, (int) (target.Character.Hp / (float) target.Character.HPLoad() * 100),
                // damage, hitmode, (byte) (hitRequest.Skill.SkillType - 1))); break;
                //
                // case TargetHitType.SingleTargetHitCombo:
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.SkillCombo.Animation, hitRequest.SkillCombo.Effect,
                // hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY,
                // isAlive, (int) (target.Character.Hp / (float) target.Character.HPLoad() * 100),
                // damage, hitmode, (byte) (hitRequest.Skill.SkillType - 1))); break;
                //
                // case TargetHitType.SingleAOETargetHit: switch (hitmode) { case 1: hitmode = 4; break;
                //
                // case 3: hitmode = 6; break;
                //
                // default: hitmode = 5; break; }
                //
                // if (hitRequest.ShowTargetHitAnimation) {
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(
                // UserType.Player, hitRequest.Session.Character.CharacterId, 1,
                // target.Character.CharacterId, hitRequest.Skill.SkillVNum,
                // hitRequest.Skill.Cooldown, hitRequest.Skill.AttackAnimation,
                // hitRequest.SkillEffect, 0, 0, isAlive, (int) (target.Character.Hp / (float)
                // target.Character.HPLoad() * 100), 0, 0, (byte) (hitRequest.Skill.SkillType - 1))); }
                //
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect,
                // hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY,
                // isAlive, (int) (target.Character.Hp / (float) target.Character.HPLoad() * 100),
                // damage, hitmode, (byte) (hitRequest.Skill.SkillType - 1))); break;
                //
                // case TargetHitType.AOETargetHit: switch (hitmode) { case 1: hitmode = 4; break;
                //
                // case 3: hitmode = 6; break;
                //
                // default: hitmode = 5; break; }
                //
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect,
                // hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY,
                // isAlive, (int) (target.Character.Hp / (float) target.Character.HPLoad() * 100),
                // damage, hitmode, (byte) (hitRequest.Skill.SkillType - 1))); break;
                //
                // case TargetHitType.ZoneHit:
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect, hitRequest.MapX,
                // hitRequest.MapY, isAlive, (int) (target.Character.Hp / (float)
                // target.Character.HPLoad() * 100), damage, 5, (byte) (hitRequest.Skill.SkillType -
                // 1))); break;
                //
                // case TargetHitType.SpecialZoneHit:
                // hitRequest.Session.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player,
                // hitRequest.Session.Character.CharacterId, 1, target.Character.CharacterId,
                // hitRequest.Skill.SkillVNum, hitRequest.Skill.Cooldown,
                // hitRequest.Skill.AttackAnimation, hitRequest.SkillEffect,
                // hitRequest.Session.Character.PositionX, hitRequest.Session.Character.PositionY,
                // isAlive, (int) (target.Character.Hp / target.Character.HPLoad() * 100), damage, 0,
                // (byte) (hitRequest.Skill.SkillType - 1))); break;
                //
                // default: Logger.Warn("Not Implemented TargetHitType Handling!"); break; }
            }
            else
            {
                // player already has been killed, send cancel
                session.SendPacket(StaticPacketHelper.Cancel(2, target.CharacterId));
            }
        }
        public override void Use(ClientSession session, ref ItemInstance inv, byte Option = 0, string[] packetsplit = null)
        {
            inv.Item.BCards.ForEach(c => c.ApplyBCards(session.Character));

            switch (Effect)
            {
            // Honour Medals
            case 69:
                session.Character.Reputation += ReputPrice;
                session.SendPacket(session.Character.GenerateFd());
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                break;

            // SP Potions
            case 150:
            case 151:
                session.Character.SpAdditionPoint += EffectValue;
                if (session.Character.SpAdditionPoint > 1000000)
                {
                    session.Character.SpAdditionPoint = 1000000;
                }
                session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("SP_POINTSADDED"), EffectValue), 0));
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                session.SendPacket(session.Character.GenerateSpPoint());
                break;

            // Specialist Medal
            case 204:
                session.Character.SpPoint         += EffectValue;
                session.Character.SpAdditionPoint += EffectValue * 3;
                if (session.Character.SpAdditionPoint > 1000000)
                {
                    session.Character.SpAdditionPoint = 1000000;
                }
                if (session.Character.SpPoint > 10000)
                {
                    session.Character.SpPoint = 10000;
                }
                session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("SP_POINTSADDEDBOTH"), EffectValue, EffectValue * 3), 0));
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                session.SendPacket(session.Character.GenerateSpPoint());
                break;

            // Raid Seals
            case 301:
                if (ServerManager.Instance.IsCharacterMemberOfGroup(session.Character.CharacterId))
                {
                    //TODO you are in group
                    return;
                }
                ItemInstance raidSeal = session.Character.Inventory.LoadBySlotAndType <ItemInstance>(inv.Slot, InventoryType.Main);
                session.Character.Inventory.RemoveItemFromInventory(raidSeal.Id);

                ScriptedInstance raid = ServerManager.Instance.Raids.FirstOrDefault(s => s.RequiredItems?.Any(obj => obj?.VNum == raidSeal.ItemVNum) == true)?.Copy();
                if (raid != null)
                {
                    Group group = new Group()
                    {
                        GroupType = GroupType.BigTeam,
                        Raid      = raid
                    };
                    group.JoinGroup(session.Character.CharacterId);
                    ServerManager.Instance.AddGroup(group);
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("RAID_LEADER"), session.Character.Name), 0));
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("RAID_LEADER"), session.Character.Name), 10));
                    if (session.Character.Level > raid.LevelMaximum || session.Character.Level < raid.LevelMinimum)
                    {
                        session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("RAID_LEVEL_INCORRECT"), 10));
                    }
                    session.SendPacket(session.Character.GenerateRaid(2, false));
                    session.SendPacket(session.Character.GenerateRaid(0, false));
                    session.SendPacket(session.Character.GenerateRaid(1, false));
                    session.SendPacket(group.GenerateRdlst());
                }
                break;

            case 1169:
            {
                if (session?.Character != null)
                {
                    if (session.Character.Miniland == session.Character.MapInstance)
                    {
                        ServerManager.Instance.JoinMiniland(session, session);
                    }
                    else
                    {
                        ServerManager.Shout($"GRACIAS POR USAR SERVICIOS HEAT!");
                        ServerManager.Instance.ChangeMapInstance(session.Character.CharacterId, session.Character.MapInstanceId, session.Character.PositionX, session.Character.PositionY);
                        session.SendPacket(StaticPacketHelper.Cancel(2));
                        session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    }
                }
            }
            break;

            case 1574:
                if (EffectValue == 1574)
                {
                    int rnd = ServerManager.RandomNumber(0, 1);
                    if (rnd < 1)
                    {
                        short[] vnums =
                        {
                            //ID's of the Items, you will get
                            4129, 4130, 4131, 4132
                        };
                        //This Code counts the Items, you inserted
                        byte[] counts = { 1, 1, 1, 1 };
                        int    item   = ServerManager.RandomNumber(0, 4);
                        session.Character.GiftAdd(vnums[item], counts[item]);
                    }
                    //This Code, deltes the Item from the Inventory
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket("msg 5 Success! You recieved your Items.");
                }
                break;



            // Partner Suits/Skins
            case 305:
                Mate mate = session.Character.Mates.Find(s => s.MateTransportId == int.Parse(packetsplit[3]));
                if (mate != null && EffectValue == mate.NpcMonsterVNum && mate.Skin == 0)
                {
                    mate.Skin = Morph;
                    session.SendPacket(mate.GenerateCMode(mate.Skin));
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            // Fairy Booster
            case 250:
                if (!session.Character.Buff.ContainsKey(131))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 131
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3011), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Fairy booster 2
            case 253:
                if (!session.Character.Buff.ContainsKey(131))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 131
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3011), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // exp/job booster
            case 251:
                if (!session.Character.Buff.ContainsKey(121))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 121
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3011), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            //sp job booster
            case 1362:
                if (!session.Character.Buff.ContainsKey(146))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 146
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3011), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Ice oil
            case 252:
                if (!session.Character.Buff.ContainsKey(340))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 340
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 16), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Valentin Buff
            case 254:
                if (!session.Character.Buff.ContainsKey(109))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 109
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 3410), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Buff exp 20%
            case 256:
                if (!session.Character.Buff.ContainsKey(119))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 119
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 4756), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Ancella fate
            case 258:
                if (!session.Character.Buff.ContainsKey(393))
                {
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 393
                    });
                    session.CurrentMapInstance?.Broadcast(session.Character.GeneratePairy());
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), inv.Item.Name), 0));
                    session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 4756), session.Character.MapX, session.Character.MapY);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Speedbooster
            case 260:
                if (!session.Character.IsVehicled || session.Character.Buff.Any(s => s.Card.CardId == 336))
                {
                    return;
                }
                session.CurrentMapInstance?.Broadcast(session.Character.GenerateEff(885), session.Character.MapX, session.Character.MapY);

                session.Character.Speed += 5;
                switch (session.Character.Morph)
                {
                case 2517:         // Nossi M
                case 2518:         // Nossi F
                case 2522:         // Roller M
                case 2523:         // Roller F
                                   // Removes <= lv 4 debuffs
                    List <BuffType> bufftodisable = new List <BuffType> {
                        BuffType.Bad
                    };
                    session.Character.DisableBuffs(bufftodisable, 4);
                    break;
                }
                Observable.Timer(TimeSpan.FromSeconds(session.Character.BuffRandomTime * 0.1D)).Subscribe(o =>
                {
                    session.Character.Speed -= 5;
                    session.Character.LoadSpeed();
                    switch (session.Character.Morph)
                    {
                    case 2526:         // White male unicorn
                    case 2527:         // White female unicorn
                    case 2528:         // Pink male unicorn
                    case 2529:         // Pink female unicorn
                    case 2530:         // Black male unicorn
                    case 2531:         // Black Female Unicorn
                    case 2928:         // Male UFO
                    case 2929:         // Female UFO
                    case 3679:         // Male squelettic dragon
                    case 3680:         // Female squelettic dragon
                        ServerManager.Instance.TeleportOnRandomPlaceInMap(session, session.Character.MapInstanceId, true);
                        break;

                    case 2432:         // Magic broom
                    case 2433:         // Magic broom F
                    case 2520:         // VTT M
                    case 2521:         // VTT F
                        switch (session.Character.Direction)
                        {
                        case 0:
                            // -y
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, session.Character.PositionX, (short)(session.Character.PositionY - 5));
                            break;

                        case 1:
                            // +x
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX + 5), session.Character.PositionY);
                            break;

                        case 2:
                            // +y
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, session.Character.PositionX, (short)(session.Character.PositionY + 5));
                            break;

                        case 3:
                            // -x
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX - 5), session.Character.PositionY);
                            break;

                        case 4:
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX - 5), (short)(session.Character.PositionY - 5));
                            // -x -y
                            break;

                        case 5:
                            // +x +y
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX - 5), (short)(session.Character.PositionY - 5));
                            break;

                        case 6:
                            // +x -y
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX + 5), (short)(session.Character.PositionY + 5));
                            break;

                        case 7:
                            // -x +y
                            ServerManager.Instance.TeleportForward(session, session.Character.MapInstanceId, (short)(session.Character.PositionX - 5), (short)(session.Character.PositionY + 5));
                            break;
                        }
                        break;
                    }
                });
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                break;



            // Rainbow Pearl/Magic Eraser
            case 666:
                if (EffectValue == 1 && byte.TryParse(packetsplit[9], out byte islot))
                {
                    ItemInstance wearInstance = session.Character.Inventory.LoadBySlotAndType(islot, InventoryType.Equipment);

                    if (wearInstance != null && (wearInstance.Item.ItemType == ItemType.Weapon || wearInstance.Item.ItemType == ItemType.Armor) && wearInstance.ShellEffects.Count != 0 && wearInstance.Item.IsHeroic)
                    {
                        wearInstance.ShellEffects.Clear();
                        DAOFactory.ShellEffectDAO.DeleteByEquipmentSerialId(wearInstance.EquipmentSerialId);
                        if (wearInstance.EquipmentSerialId == Guid.Empty)
                        {
                            wearInstance.EquipmentSerialId = Guid.NewGuid();
                        }
                        session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                        session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("OPTION_DELETE"), 0));
                    }
                }
                else
                {
                    session.SendPacket("guri 18 0");
                }
                break;

            // Atk/Def/HP/Exp potions
            case 6600:
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                break;

            // Ancelloan's Blessing
            case 208:
                if (!session.Character.Buff.ContainsKey(121))
                {
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.Character.AddStaticBuff(new StaticBuffDTO()
                    {
                        CardId = 121
                    });
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("ITEM_IN_USE"), 0));
                }
                break;

            // Divorce letter
            case 6969:     // this is imaginary number I = √(-1)
                var rel = session.Character.CharacterRelations.FirstOrDefault(s => s.RelationType == CharacterRelationType.Spouse);
                if (rel != null)
                {
                    session.Character.DeleteRelation(rel.CharacterId == session.Character.CharacterId ? rel.RelatedCharacterId : rel.CharacterId);
                    session.SendPacket(UserInterfaceHelper.GenerateInfo(Language.Instance.GetMessageFromKey("DIVORCED")));

                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }

                break;

            // Cupid's arrow
            case 34:     // this is imaginary number I = √(-1)
                         // Cupid's arrow
                if (packetsplit != null && packetsplit.Length > 3)
                {
                    if (long.TryParse(packetsplit[3], out long characterId))
                    {
                        if (session.Character.CharacterRelations.Any(s => s.RelationType == CharacterRelationType.Spouse))
                        {
                            session.SendPacket($"info {Language.Instance.GetMessageFromKey("ALREADY_MARRIED")}");
                            return;
                        }
                        ClientSession otherSession = ServerManager.Instance.GetSessionByCharacterId(characterId);
                        if (otherSession != null)
                        {
                            otherSession.SendPacket(UserInterfaceHelper.GenerateDialog(
                                                        $"#fins^-34^{session.Character.CharacterId} #fins^-69^{session.Character.CharacterId} {string.Format(Language.Instance.GetMessageFromKey("MARRY_REQUEST"), session.Character.Name)}"));
                            session.Character.FriendRequestCharacters.Add(characterId);
                            session.Character.Inventory.RemoveItemFromInventory(inv.Id, 1);
                            session.Character.AddStaticBuff(new StaticBuffDTO {
                                CardId = 319
                            });
                        }
                    }
                }
                break;


            case 100:
            {
            }
            break;

            case 5836:
            {
                session.SendPacket($"gb 0 {session.Account.BankGold / 1000} {session.Character.Gold} 0 0");
                session.SendPacket($"s_memo 6 [Account balance]: {session.Account.BankGold} gold; [Owned]: {session.Character.Gold} gold\nWe will do our best. Thank you for using the services of Cuarry Bank.");
            }
            break;

            // Faction Egg
            case 570:
                if (session.Character.Faction == (FactionType)EffectValue)
                {
                    return;
                }
                if (EffectValue < 3)
                {
                    session.SendPacket(session.Character.Family == null
                            ? $"qna #guri^750^{EffectValue} {Language.Instance.GetMessageFromKey($"ASK_CHANGE_FACTION{EffectValue}")}"
                            : UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("IN_FAMILY"),
                                                              0));
                }
                else
                {
                    session.SendPacket(session.Character.Family != null
                            ? $"qna #guri^750^{EffectValue} {Language.Instance.GetMessageFromKey($"ASK_CHANGE_FACTION{EffectValue}")}"
                            : UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("NO_FAMILY"),
                                                              0));
                }

                break;

            // SP Wings
            case 650:
                ItemInstance specialistInstance = session.Character.Inventory.LoadBySlotAndType((byte)EquipmentType.Sp, InventoryType.Wear);
                if (session.Character.UseSp && specialistInstance != null)
                {
                    if (Option == 0)
                    {
                        session.SendPacket($"qna #u_i^1^{session.Character.CharacterId}^{(byte)inv.Type}^{inv.Slot}^3 {Language.Instance.GetMessageFromKey("ASK_WINGS_CHANGE")}");
                    }
                    else
                    {
                        void disposeBuff(short vNum)
                        {
                            if (session.Character.BuffObservables.ContainsKey(vNum))
                            {
                                session.Character.BuffObservables[vNum].Dispose();
                                session.Character.BuffObservables.Remove(vNum);
                            }
                            session.Character.RemoveBuff(vNum);
                        }

                        disposeBuff(387);
                        disposeBuff(395);
                        disposeBuff(396);
                        disposeBuff(397);
                        disposeBuff(398);
                        disposeBuff(410);
                        disposeBuff(411);
                        disposeBuff(444);

                        specialistInstance.Design = (byte)EffectValue;

                        session.Character.MorphUpgrade2 = EffectValue;
                        session.CurrentMapInstance?.Broadcast(session.Character.GenerateCMode());
                        session.SendPacket(session.Character.GenerateStat());
                        session.SendPacket(session.Character.GenerateStatChar());
                        session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    }
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("NO_SP"), 0));
                }
                break;

            // Self-Introduction
            case 203:
                if (!session.Character.IsVehicled && Option == 0)
                {
                    session.SendPacket(UserInterfaceHelper.GenerateGuri(10, 2, session.Character.CharacterId, 1));
                }
                break;

            // Magic Lamp
            case 651:
                if (session.Character.Inventory.All(i => i.Type != InventoryType.Wear))
                {
                    if (Option == 0)
                    {
                        session.SendPacket($"qna #u_i^1^{session.Character.CharacterId}^{(byte)inv.Type}^{inv.Slot}^3 {Language.Instance.GetMessageFromKey("ASK_USE")}");
                    }
                    else
                    {
                        session.Character.ChangeSex();
                        session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    }
                }
                else
                {
                    session.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("EQ_NOT_EMPTY"), 0));
                }
                break;

            // Vehicles
            case 1000:
                if (EffectValue != 0 || ServerManager.Instance.ChannelId == 51 || session.CurrentMapInstance?.MapInstanceType == MapInstanceType.EventGameInstance)
                {
                    return;
                }

                if (session.Character.HasShopOpened)
                {
                    return;
                }

                if (Morph > 0)
                {
                    if (Option == 0 && !session.Character.IsVehicled)
                    {
                        if (session.Character.IsSitting)
                        {
                            session.Character.IsSitting = false;
                            session.CurrentMapInstance?.Broadcast(session.Character.GenerateRest());
                        }
                        session.Character.LastDelay = DateTime.Now;
                        session.SendPacket(UserInterfaceHelper.GenerateDelay(3000, 3, $"#u_i^1^{session.Character.CharacterId}^{(byte)inv.Type}^{inv.Slot}^2"));
                    }
                    else
                    {
                        if (!session.Character.IsVehicled && Option != 0)
                        {
                            DateTime delay = DateTime.Now.AddSeconds(-4);
                            if (session.Character.LastDelay > delay && session.Character.LastDelay < delay.AddSeconds(2))
                            {
                                session.Character.Speed         = Speed;
                                session.Character.IsVehicled    = true;
                                session.Character.VehicleSpeed  = Speed;
                                session.Character.MorphUpgrade  = 0;
                                session.Character.MorphUpgrade2 = 0;
                                session.Character.Morph         = Morph + (byte)session.Character.Gender;
                                session.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, session.Character.CharacterId, 4809), session.Character.MapX, session.Character.MapY);
                                session.CurrentMapInstance?.Broadcast(session.Character.GenerateCMode());
                                session.SendPacket(session.Character.GenerateCond());
                                session.Character.LastSpeedChange = DateTime.Now;
                            }
                        }
                        else if (session.Character.IsVehicled)
                        {
                            session.Character.Mates?.Where(s => s.IsTeamMember).ToList().ForEach(x =>
                            {
                                x.PositionX = session.Character.PositionX;
                                x.PositionY = session.Character.PositionY;
                                session.CurrentMapInstance?.Broadcast(x.GenerateIn());
                            });
                            session.Character.RemoveVehicle();
                        }
                    }
                }
                break;

            // Sealed Vessel
            case 1002:
                if (EffectValue == 69)
                {
                    int rnd = ServerManager.RandomNumber(0, 1000);
                    if (rnd < 5)
                    {
                        short[] vnums =
                        {
                            5560, 5591, 4099, 907, 1160, 4705, 4706, 4707, 4708, 4709, 4710, 4711, 4712, 4713, 4714,
                            4715, 4716
                        };
                        byte[] counts = { 1, 1, 1, 1, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 };
                        int    item   = ServerManager.RandomNumber(0, 17);
                        session.Character.GiftAdd(vnums[item], counts[item]);
                    }
                    else if (rnd < 30)
                    {
                        short[] vnums = { 361, 362, 363, 366, 367, 368, 371, 372, 373 };
                        session.Character.GiftAdd(vnums[ServerManager.RandomNumber(0, 9)], 1);
                    }
                    else
                    {
                        short[] vnums =
                        {
                            1161, 2282, 1030, 1244, 1218, 5369, 1012, 1363, 1364, 2160, 2173, 5959, 5983, 2514,
                            2515, 2516, 2517, 2518, 2519, 2520, 2521, 1685, 1686, 5087, 5203, 2418, 2310, 2303,
                            2169, 2280, 5892, 5893, 5894, 5895, 5896, 5897, 5898, 5899, 5332, 5105, 2161, 2162
                        };
                        byte[] counts =
                        {
                            10, 10, 20, 5, 1, 1, 99, 1, 1, 5, 5, 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 5, 20,
                            20,  1,  1, 1, 1, 1,  1, 1, 1, 1, 1, 1, 1, 1, 1
                        };
                        int item = ServerManager.RandomNumber(0, 42);
                        session.Character.GiftAdd(vnums[item], counts[item]);
                    }
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                else if (session.HasCurrentMapInstance && session.CurrentMapInstance.Map.MapTypes.All(m => m.MapTypeId != (short)MapTypeEnum.Act4))
                {
                    short[] vnums = { 1386, 1387, 1388, 1389, 1390, 1391, 1392, 1393, 1394, 1395, 1396, 1397, 1398, 1399, 1400, 1401, 1402, 1403, 1404, 1405 };
                    short   vnum  = vnums[ServerManager.RandomNumber(0, 20)];

                    NpcMonster npcmonster = ServerManager.GetNpc(vnum);
                    if (npcmonster == null)
                    {
                        return;
                    }
                    MapMonster monster = new MapMonster
                    {
                        MonsterVNum   = vnum,
                        MapY          = session.Character.MapY,
                        MapX          = session.Character.MapX,
                        MapId         = session.Character.MapInstance.Map.MapId,
                        Position      = session.Character.Direction,
                        IsMoving      = true,
                        MapMonsterId  = session.CurrentMapInstance.GetNextMonsterId(),
                        ShouldRespawn = false
                    };
                    monster.Initialize(session.CurrentMapInstance);
                    session.CurrentMapInstance.AddMonster(monster);
                    session.CurrentMapInstance.Broadcast(monster.GenerateIn());
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            // Golden Bazaar Medal
            case 1003:
                if (!session.Character.StaticBonusList.Any(s => s.StaticBonusType == StaticBonusType.BazaarMedalGold || s.StaticBonusType == StaticBonusType.BazaarMedalSilver))
                {
                    session.Character.StaticBonusList.Add(new StaticBonusDTO
                    {
                        CharacterId     = session.Character.CharacterId,
                        DateEnd         = DateTime.Now.AddDays(EffectValue),
                        StaticBonusType = StaticBonusType.BazaarMedalGold
                    });
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), Name), 12));
                }
                break;

            // Silver Bazaar Medal
            case 1004:
                if (!session.Character.StaticBonusList.Any(s => s.StaticBonusType == StaticBonusType.BazaarMedalGold || s.StaticBonusType == StaticBonusType.BazaarMedalGold))
                {
                    session.Character.StaticBonusList.Add(new StaticBonusDTO
                    {
                        CharacterId     = session.Character.CharacterId,
                        DateEnd         = DateTime.Now.AddDays(EffectValue),
                        StaticBonusType = StaticBonusType.BazaarMedalSilver
                    });
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), Name), 12));
                }
                break;

            // Pet Slot Expansion
            case 1006:
                if (Option == 0)
                {
                    session.SendPacket($"qna #u_i^1^{session.Character.CharacterId}^{(byte)inv.Type}^{inv.Slot}^2 {Language.Instance.GetMessageFromKey("ASK_PET_MAX")}");
                }
                else if (session.Character.MaxMateCount < 30)
                {
                    session.SendPacket(session.Character.GenerateSay(Language.Instance.GetMessageFromKey("GET_PET_PLACES"), 10));
                    session.SendPacket(session.Character.GenerateScpStc());
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            // Pet Basket
            case 1007:
                if (session.Character.StaticBonusList.All(s => s.StaticBonusType != StaticBonusType.PetBasket))
                {
                    session.Character.StaticBonusList.Add(new StaticBonusDTO
                    {
                        CharacterId     = session.Character.CharacterId,
                        DateEnd         = DateTime.Now.AddDays(EffectValue),
                        StaticBonusType = StaticBonusType.PetBasket
                    });
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateExts());
                    session.SendPacket("ib 1278 1");
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), Name), 12));
                }
                break;

            // Partner's Backpack
            case 1008:
                if (session.Character.StaticBonusList.All(s => s.StaticBonusType != StaticBonusType.PetBackPack))
                {
                    session.Character.StaticBonusList.Add(new StaticBonusDTO
                    {
                        CharacterId     = session.Character.CharacterId,
                        DateEnd         = DateTime.Now.AddDays(EffectValue),
                        StaticBonusType = StaticBonusType.PetBackPack
                    });
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateExts());
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), Name), 12));
                }
                break;

            // Backpack Expansion
            case 1009:
                if (session.Character.StaticBonusList.All(s => s.StaticBonusType != StaticBonusType.BackPack))
                {
                    session.Character.StaticBonusList.Add(new StaticBonusDTO
                    {
                        CharacterId     = session.Character.CharacterId,
                        DateEnd         = DateTime.Now.AddDays(EffectValue),
                        StaticBonusType = StaticBonusType.BackPack
                    });
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    session.SendPacket(session.Character.GenerateExts());
                    session.SendPacket(session.Character.GenerateSay(string.Format(Language.Instance.GetMessageFromKey("EFFECT_ACTIVATED"), Name), 12));
                }
                break;

            // Sealed Tarot Card
            case 1005:
                session.Character.GiftAdd((short)(VNum - Effect), 1);
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                break;

            // Tarot Card Game
            case 1894:
                if (EffectValue == 0)
                {
                    for (int i = 0; i < 5; i++)
                    {
                        session.Character.GiftAdd((short)(Effect + ServerManager.RandomNumber(0, 10)), 1);
                    }
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                }
                break;

            // Sealed Tarot Card
            case 2152:
                session.Character.GiftAdd((short)(VNum + Effect), 1);
                session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                break;

            default:
                switch (VNum)
                {
                case 5841:
                    int     rnd   = ServerManager.RandomNumber(0, 1000);
                    short[] vnums = null;
                    if (rnd < 900)
                    {
                        vnums = new short[] { 4356, 4357, 4358, 4359 };
                    }
                    else
                    {
                        vnums = new short[] { 4360, 4361, 4362, 4363 };
                    }
                    session.Character.GiftAdd(vnums[ServerManager.RandomNumber(0, 4)], 1);
                    session.Character.Inventory.RemoveItemFromInventory(inv.Id);
                    break;

                default:
                    Logger.Warn(string.Format(Language.Instance.GetMessageFromKey("NO_HANDLER_ITEM"), GetType()) + $" ItemVNum: {VNum} Effect: {Effect} EffectValue: {EffectValue}");
                    break;
                }
                break;
            }
        }
Beispiel #11
0
        public void ApplyBCards(object session, object sender = null)
        {
            //Console.WriteLine($"BCardId: {BCardId} Type: {(BCardType.CardType)Type} SubType: {SubType} CardId: {CardId?.ToString() ?? "null"} ItemVNum: {ItemVNum?.ToString() ?? "null"} SkillVNum: {SkillVNum?.ToString() ?? "null"} SessionType: {session?.GetType().ToString() ?? "null"} SenderType: {sender?.GetType().ToString() ?? "null"}");

            switch ((BCardType.CardType)Type)
            {
            case BCardType.CardType.Buff:
            {
                if (ServerManager.RandomNumber() < FirstData)
                {
                    Character senderCharacter = sender is ClientSession senderSession
                                ? senderSession.Character : sender as Character;

                    if (session is Character character)
                    {
                        short cardId = (short)SecondData;

                        // If either Berserk Spirit or Strong Berserk Spirit is active
                        // then don't add Weak Berserk Spirit

                        if (cardId == 601 &&
                            character.Buff?.Any(s => s?.Card?.CardId == 602 || s?.Card?.CardId == 603) == true)
                        {
                            break;
                        }

                        if (senderCharacter != null)
                        {
                            // TODO: Get anti stats from BCard

                            character.AddBuff(new Buff((short)SecondData, senderCharacter.Level, senderCharacter));
                        }
                        else
                        {
                            character.AddBuff(new Buff((short)SecondData, character.Level));
                        }
                    }
                    else if (session is MapMonster mapMonster)
                    {
                        if (senderCharacter != null)
                        {
                            mapMonster.AddBuff(new Buff((short)SecondData, senderCharacter.Level, senderCharacter));
                        }
                        else
                        {
                            mapMonster.AddBuff(new Buff((short)SecondData, mapMonster.Monster.Level));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.Move:
            {
                if (session is Character character)
                {
                    character.LastSpeedChange = DateTime.Now;
                    character.Session.SendPacket(character.GenerateCond());
                }
            }
            break;

            case BCardType.CardType.Summons:
            {
                if (session is Character character)
                {
                    if (character.MapInstance != null)
                    {
                        List <MonsterToSummon> monsterList = new List <MonsterToSummon>();

                        if (SubType == (byte)AdditionalTypes.Summons.Summons / 10)
                        {
                            int aliveTime = ServerManager.GetNpc((short)SecondData).RespawnTime;

                            for (int i = 0; i < FirstData; i++)
                            {
                                MapCell mapCell = new MapCell
                                {
                                    X = (short)(ServerManager.RandomNumber(-1, 2) + character.PositionX),
                                    Y = (short)(ServerManager.RandomNumber(-1, 2) + character.PositionY),
                                };

                                monsterList.Add(new MonsterToSummon((short)SecondData, mapCell, -1, true, false, false, true, false, -1, character, aliveTime, false));
                            }
                        }

                        if (monsterList.Any())
                        {
                            EventHelper.Instance.RunEvent(new EventContainer(character.MapInstance,
                                                                             EventActionType.SPAWNMONSTERS, monsterList));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SpecialAttack:
                break;

            case BCardType.CardType.SpecialDefence:
                break;

            case BCardType.CardType.AttackPower:
                break;

            case BCardType.CardType.Target:
                break;

            case BCardType.CardType.Critical:
                break;

            case BCardType.CardType.SpecialCritical:
                break;

            case BCardType.CardType.Element:
                break;

            case BCardType.CardType.IncreaseDamage:
                break;

            case BCardType.CardType.Defence:
                break;

            case BCardType.CardType.DodgeAndDefencePercent:
                break;

            case BCardType.CardType.Block:
                break;

            case BCardType.CardType.Absorption:
                break;

            case BCardType.CardType.ElementResistance:
                break;

            case BCardType.CardType.EnemyElementResistance:
                break;

            case BCardType.CardType.Damage:
                break;

            case BCardType.CardType.GuarantedDodgeRangedAttack:
                break;

            case BCardType.CardType.Morale:
                break;

            case BCardType.CardType.Casting:
                break;

            case BCardType.CardType.Reflection:
                break;

            case BCardType.CardType.DrainAndSteal:
                break;

            case BCardType.CardType.HealingBurningAndCasting:
            {
                Character senderCharacter = sender is ClientSession senderSession
                            ? senderSession.Character : sender as Character;

                if (senderCharacter != null)
                {
                    #region Character

                    if (session is Character character)
                    {
                        void HealingBurningAndCastingAction()
                        {
                            if (!character.IsAlive ||
                                character.MapInstance == null ||
                                character.Session == null)
                            {
                                return;
                            }

                            int amount = 0;

                            if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreHP / 10 ||
                                SubType == (byte)AdditionalTypes.HealingBurningAndCasting.DecreaseHP / 10)
                            {
                                if (FirstData > 0)
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * FirstData;
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    if (character.Hp + amount > character.HPMax)
                                    {
                                        amount = character.HPMax - character.Hp;
                                    }

                                    character.Hp += amount;

                                    character.MapInstance.Broadcast(character.GenerateRc(amount));
                                }
                                else
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * (FirstData - 1);
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    amount *= -1;

                                    if (character.Hp - amount < 1)
                                    {
                                        amount = character.Hp - 1;
                                    }

                                    character.GetDamage(amount);

                                    character.MapInstance.Broadcast(character.GenerateDm(amount));
                                }

                                character.Session.SendPacket(character.GenerateStat());
                            }
                            else if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreMP / 10 ||
                                     SubType == (byte)AdditionalTypes.HealingBurningAndCasting.DecreaseMP / 10)
                            {
                                if (FirstData > 0)
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * FirstData;
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    if (character.Mp + amount > character.MPMax)
                                    {
                                        amount = character.MPMax - character.Mp;
                                    }

                                    character.Mp += amount;
                                }
                                else
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * (FirstData - 1);
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    amount *= -1;

                                    if (character.Mp - amount < 1)
                                    {
                                        amount = character.Mp - 1;
                                    }

                                    character.DecreaseMp(amount);
                                }

                                character.Session.SendPacket(character.GenerateStat());
                            }
                        }

                        HealingBurningAndCastingAction();

                        if (ThirdData > 0 &&
                            CardId != null)
                        {
                            IDisposable disposable = Observable.Interval(TimeSpan.FromSeconds(ThirdData * 2))
                                                     .Subscribe(s => HealingBurningAndCastingAction());

                            character.DisposeBCard(BCardId);
                            character.BCardDisposables[BCardId] = disposable;
                        }
                    }

                    #endregion

                    #region MapMonster

                    else if (session is MapMonster mapMonster)
                    {
                        void HealingBurningAndCastingAction()
                        {
                            if (!mapMonster.IsAlive ||
                                mapMonster.MapInstance == null)
                            {
                                return;
                            }

                            int amount = 0;

                            if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreHP / 10 ||
                                SubType == (byte)AdditionalTypes.HealingBurningAndCasting.DecreaseHP / 10)
                            {
                                if (FirstData > 0)
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * FirstData;
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    if (mapMonster.CurrentHp + amount > mapMonster.MaxHp)
                                    {
                                        amount = mapMonster.MaxHp - mapMonster.CurrentHp;
                                    }

                                    mapMonster.CurrentHp += amount;

                                    mapMonster.MapInstance.Broadcast(mapMonster.GenerateRc(amount));
                                }
                                else
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * (FirstData - 1);
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    amount *= -1;

                                    if (mapMonster.CurrentHp - amount < 1)
                                    {
                                        amount = mapMonster.CurrentHp - 1;
                                    }

                                    mapMonster.CurrentHp -= amount;

                                    mapMonster.MapInstance.Broadcast(mapMonster.GenerateDm(amount));
                                }
                            }

                            if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreMP / 10 ||
                                SubType == (byte)AdditionalTypes.HealingBurningAndCasting.DecreaseMP / 10)
                            {
                                if (FirstData > 0)
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * FirstData;
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    if (mapMonster.CurrentMp + amount > mapMonster.MaxMp)
                                    {
                                        amount = mapMonster.MaxMp - mapMonster.CurrentMp;
                                    }

                                    mapMonster.CurrentMp += amount;
                                }
                                else
                                {
                                    if (IsLevelScaled)
                                    {
                                        amount = senderCharacter.Level * (FirstData - 1);
                                    }
                                    else
                                    {
                                        amount = FirstData;
                                    }

                                    amount *= -1;

                                    if (mapMonster.CurrentMp - amount < 1)
                                    {
                                        amount = mapMonster.CurrentMp - 1;
                                    }

                                    mapMonster.CurrentMp -= amount;
                                }
                            }
                        }

                        HealingBurningAndCastingAction();

                        if (ThirdData > 0 &&
                            CardId != null)
                        {
                            IDisposable disposable = Observable.Interval(TimeSpan.FromSeconds(ThirdData * 2))
                                                     .Subscribe(s => HealingBurningAndCastingAction());

                            mapMonster.DisposeBCard(BCardId);
                            mapMonster.BCardDisposables[BCardId] = disposable;
                        }
                    }

                    #endregion
                }
            }
            break;

            case BCardType.CardType.HPMP:
            {
                if (SubType == (byte)AdditionalTypes.HPMP.DecreaseRemainingMP / 10)
                {
                    if (FirstData < 0)
                    {
                        double multiplier = (FirstData * -1) / 100D;

                        if (session is Character character)
                        {
                            character.DecreaseMp((int)(character.Mp * multiplier));
                            character.Session?.SendPacket(character.GenerateStat());
                        }
                        else if (session is MapMonster mapMonster)
                        {
                            mapMonster.DecreaseMp((int)(mapMonster.CurrentMp * multiplier));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SpecializationBuffResistance:
            {
                if (SubType == (byte)AdditionalTypes.SpecializationBuffResistance.RemoveGoodEffects / 10)
                {
                    if (session is Character character)
                    {
                        if (FirstData < 0)
                        {
                            if (ServerManager.RandomNumber() < (FirstData * -1))
                            {
                                character.Buff?.GetAllItems()?.Where(s => s?.Card?.BuffType == BuffType.Bad && s.Card.Level < SecondData)?
                                .ToList()?.ForEach(s => character.RemoveBuff(s.Card.CardId));
                            }
                        }
                        else
                        {
                            if (ServerManager.RandomNumber() < FirstData)
                            {
                                character.Buff?.GetAllItems()?.Where(s => s?.Card?.BuffType == BuffType.Good && s.Card.Level < SecondData)?
                                .ToList()?.ForEach(s => character.RemoveBuff(s.Card.CardId));
                            }
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SpecialEffects:
            {
                if (SubType == (byte)AdditionalTypes.SpecialEffects.ShadowAppears / 10)
                {
                    if (session is Character character)
                    {
                        character.NumberOfShadows = FirstData;
                        character.ShadowsDistance = SecondData;
                        character.MapInstance?.Broadcast(character.GenerateSpeed());
                    }
                }
            }
            break;

            case BCardType.CardType.Capture:
            {
                if (session is MapMonster mapMonster &&
                    sender is ClientSession senderSession)
                {
                    NpcMonster mateNpc = ServerManager.GetNpc(mapMonster.MonsterVNum);

                    if (mateNpc != null)
                    {
                        if (mapMonster.Monster.Catch)
                        {
                            if (mapMonster.IsAlive && mapMonster.CurrentHp <= (int)((double)mapMonster.MaxHp / 2))
                            {
                                if (mapMonster.Monster.Level < senderSession.Character.Level)
                                {
                                    // TODO: Find a new algorithm
                                    int[] chance = { 100, 80, 60, 40, 20, 0 };
                                    if (ServerManager.RandomNumber() < chance[ServerManager.RandomNumber(0, 5)])
                                    {
                                        Mate mate = new Mate(senderSession.Character, mateNpc, (byte)(mapMonster.Monster.Level - 15 > 0 ? mapMonster.Monster.Level - 15 : 1), MateType.Pet);
                                        if (senderSession.Character.CanAddMate(mate))
                                        {
                                            senderSession.Character.AddPetWithSkill(mate);
                                            senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CATCH_SUCCESS"), 0));
                                            senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, senderSession.Character.CharacterId, 197));
                                            senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, senderSession.Character.CharacterId, 3, mapMonster.MapMonsterId, -1, 0, 15, -1, -1, -1, true, (int)((float)mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100), 0, -1, 0));
                                            mapMonster.SetDeathStatement();
                                            senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.Out(UserType.Monster, mapMonster.MapMonsterId));
                                        }
                                        else
                                        {
                                            senderSession.SendPacket(senderSession.Character.GenerateSay(Language.Instance.GetMessageFromKey("PET_SLOT_FULL"), 10));
                                            senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                        }
                                    }
                                    else
                                    {
                                        senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CATCH_FAIL"), 0));
                                        senderSession.CurrentMapInstance?.Broadcast(StaticPacketHelper.SkillUsed(UserType.Player, senderSession.Character.CharacterId, 3, mapMonster.MapMonsterId, -1, 0, 15, -1, -1, -1, true, (int)((float)mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100), 0, -1, 0));
                                    }
                                }
                                else
                                {
                                    senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("LEVEL_LOWER_THAN_MONSTER"), 0));
                                    senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                }
                            }
                            else
                            {
                                senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("CURRENT_HP_TOO_HIGH"), 0));
                                senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                            }
                        }
                        else
                        {
                            senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(Language.Instance.GetMessageFromKey("MONSTER_CANT_BE_CAPTURED"), 0));
                            senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SpecialDamageAndExplosions:
                break;

            case BCardType.CardType.SpecialEffects2:
            {
                if (SubType == (byte)AdditionalTypes.SpecialEffects2.TeleportInRadius / 10)
                {
                    if (session is Character character)
                    {
                        character.Teleport((short)FirstData);
                    }
                }
            }
            break;

            case BCardType.CardType.CalculatingLevel:
                break;

            case BCardType.CardType.Recovery:
                break;

            case BCardType.CardType.MaxHPMP:
            {
                if (session is Character character)
                {
                    if (SubType == (byte)AdditionalTypes.MaxHPMP.IncreasesMaximumHP / 10)
                    {
                        character.HPLoad();
                        character.Session?.SendPacket(character.GenerateStat());
                    }
                    else if (SubType == (byte)AdditionalTypes.MaxHPMP.IncreasesMaximumMP / 10)
                    {
                        character.MPLoad();
                        character.Session?.SendPacket(character.GenerateStat());
                    }
                }
            }
            break;

            case BCardType.CardType.MultAttack:
                break;

            case BCardType.CardType.MultDefence:
                break;

            case BCardType.CardType.TimeCircleSkills:
                break;

            case BCardType.CardType.RecoveryAndDamagePercent:
                break;

            case BCardType.CardType.Count:
                break;

            case BCardType.CardType.NoDefeatAndNoDamage:
                break;

            case BCardType.CardType.SpecialActions:
            {
                Character senderCharacter = sender is ClientSession senderSession
                            ? senderSession.Character : sender as Character;

                if (SubType == (byte)AdditionalTypes.SpecialActions.PushBack / 10)
                {
                    if (senderCharacter != null)
                    {
                        if (session is Character character)
                        {
                            if (character.ResistForcedMovementChance <= 0 ||
                                ServerManager.RandomNumber() < character.ResistForcedMovementChance)
                            {
                                character.PushBack((short)FirstData, senderCharacter);
                            }
                        }
                        else if (session is MapMonster mapMonster)
                        {
                            mapMonster.PushBack((short)FirstData, senderCharacter);
                        }
                    }
                }
                else if (SubType == (byte)AdditionalTypes.SpecialActions.FocusEnemies / 10)
                {
                    if (senderCharacter != null)
                    {
                        if (session is Character character)
                        {
                            if (character.ResistForcedMovementChance <= 0 ||
                                ServerManager.RandomNumber() < character.ResistForcedMovementChance)
                            {
                                character.Focus((short)FirstData, senderCharacter);
                            }
                        }
                        else if (session is MapMonster mapMonster)
                        {
                            mapMonster.Focus((short)FirstData, senderCharacter);
                        }
                    }
                }
                else if (SubType == (byte)AdditionalTypes.SpecialActions.Hide / 10)
                {
                    if (session is Character character)
                    {
                        character.SetInvisible(true);
                    }
                }
            }
            break;

            case BCardType.CardType.Transform:
                break;

            case BCardType.CardType.Mode:
                break;

            case BCardType.CardType.NoCharacteristicValue:
                break;

            case BCardType.CardType.LightAndShadow:
            {
                if (SubType == (byte)AdditionalTypes.LightAndShadow.RemoveBadEffects / 10)
                {
                    if (session is Character character)
                    {
                        character.Buff?.GetAllItems()?.Where(s => s?.Card?.BuffType == BuffType.Bad && s.Card.Level < FirstData)?
                        .ToList()?.ForEach(s => character.RemoveBuff(s.Card.CardId));
                    }
                }
            }
            break;

            case BCardType.CardType.Item:
                break;

            case BCardType.CardType.DebuffResistance:
                break;

            case BCardType.CardType.SpecialBehaviour:
                break;

            case BCardType.CardType.Quest:
                break;

            case BCardType.CardType.SecondSPCard:
            {
                if (session is Character character)
                {
                    if (character.MapInstance != null)
                    {
                        List <MonsterToSummon> monsterList = new List <MonsterToSummon>();

                        if (SubType == (byte)AdditionalTypes.SecondSPCard.PlantBomb / 10)
                        {
                            MapMonster bomb = character.MapInstance.Monsters.FirstOrDefault(m => m?.Owner?.CharacterId == character.CharacterId &&
                                                                                            m.MonsterVNum == (short)SecondData);

                            if (bomb == null)
                            {
                                for (int i = 0; i < FirstData; i++)
                                {
                                    monsterList.Add(new MonsterToSummon((short)SecondData, new MapCell {
                                            X = character.PositionX, Y = character.PositionY
                                        },
                                                                        -1, false, false, false, false, false, -1, character, 0, false));
                                }
                            }
                            else
                            {
                                bomb.Explode();
                                break;
                            }
                        }
                        else if (SubType == (byte)AdditionalTypes.SecondSPCard.PlantSelfDestructionBomb / 10)
                        {
                            int aliveTime = ServerManager.GetNpc((short)SecondData).RespawnTime;

                            for (int i = 0; i < FirstData; i++)
                            {
                                MapCell mapCell = new MapCell
                                {
                                    X = (short)(ServerManager.RandomNumber(-1, 2) + character.PositionX),
                                    Y = (short)(ServerManager.RandomNumber(-1, 2) + character.PositionY),
                                };

                                monsterList.Add(new MonsterToSummon((short)SecondData, mapCell, -1, true, false, false, true, false, -1, character, aliveTime, true));
                            }
                        }

                        if (monsterList.Any())
                        {
                            EventHelper.Instance.RunEvent(new EventContainer(character.MapInstance,
                                                                             EventActionType.SPAWNMONSTERS, monsterList));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SPCardUpgrade:
                break;

            case BCardType.CardType.HugeSnowman:
                break;

            case BCardType.CardType.Drain:
                break;

            case BCardType.CardType.BossMonstersSkill:
                break;

            case BCardType.CardType.LordHatus:
                break;

            case BCardType.CardType.LordCalvinas:
                break;

            case BCardType.CardType.SESpecialist:
            {
                if (SubType == (byte)AdditionalTypes.SESpecialist.LowerHPStrongerEffect / 10)
                {
                    Character senderCharacter = sender is ClientSession senderSession
                                ? senderSession.Character : sender as Character;

                    if (senderCharacter != null)
                    {
                        if (session is Character character)
                        {
                            double percentage = (character.Hp * 100) / character.HPMax;

                            if (percentage < 35)
                            {
                                character.AddBuff(new Buff(274, senderCharacter.Level, senderCharacter));
                            }
                            else if (percentage < 67)
                            {
                                character.AddBuff(new Buff(273, senderCharacter.Level, senderCharacter));
                            }
                            else
                            {
                                character.AddBuff(new Buff(272, senderCharacter.Level, senderCharacter));
                            }
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.FourthGlacernonFamilyRaid:
                break;

            case BCardType.CardType.SummonedMonsterAttack:
                break;

            case BCardType.CardType.BearSpirit:
            {
                if (session is Character character)
                {
                    if (SubType == (byte)AdditionalTypes.BearSpirit.IncreaseMaximumHP / 10)
                    {
                        character.HPLoad();
                        character.Session?.SendPacket(character.GenerateStat());
                    }
                    else if (SubType == (byte)AdditionalTypes.BearSpirit.IncreaseMaximumMP / 10)
                    {
                        character.MPLoad();
                        character.Session?.SendPacket(character.GenerateStat());
                    }
                }
            }
            break;

            case BCardType.CardType.SummonSkill:
                break;

            case BCardType.CardType.InflictSkill:
                break;

            case BCardType.CardType.HideBarrelSkill:
                break;

            case BCardType.CardType.FocusEnemyAttentionSkill:
                break;

            case BCardType.CardType.TauntSkill:
                break;

            case BCardType.CardType.FireCannoneerRangeBuff:
                break;

            case BCardType.CardType.VulcanoElementBuff:
                break;

            case BCardType.CardType.DamageConvertingSkill:
                break;

            case BCardType.CardType.MeditationSkill:
            {
                if (session is Character character)
                {
                    if (SkillVNum.HasValue && SubType.Equals((byte)AdditionalTypes.MeditationSkill.CausingChance / 10) && ServerManager.RandomNumber() < FirstData)
                    {
                        Skill skill    = ServerManager.GetSkill(SkillVNum.Value);
                        Skill newSkill = ServerManager.GetSkill((short)SecondData);

                        Observable.Timer(TimeSpan.FromMilliseconds(100)).Subscribe(observer =>
                            {
                                foreach (QuicklistEntryDTO quicklistEntry in character.QuicklistEntries.Where(s => s.Pos.Equals(skill.CastId)))
                                {
                                    character.Session.SendPacket($"qset {quicklistEntry.Q1} {quicklistEntry.Q2} {quicklistEntry.Type}.{quicklistEntry.Slot}.{newSkill.CastId}.0");
                                }

                                character.Session.SendPacket($"mslot {newSkill.CastId} -1");
                            });

                        character.SkillComboCount++;
                        character.LastSkillComboUse = DateTime.Now;

                        if (skill.CastId > 10)
                        {
                            Observable.Timer(TimeSpan.FromMilliseconds((skill.GetCooldown(character) * 100) + 500)).Subscribe(observer => character.Session.SendPacket(StaticPacketHelper.SkillReset(skill.CastId)));
                        }
                    }

                    switch (SubType)
                    {
                    case 2:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(4);
                        break;

                    case 3:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(8);
                        break;

                    case 4:
                        character.MeditationDictionary[(short)SecondData] = DateTime.Now.AddSeconds(12);
                        break;
                    }
                }
            }
            break;

            case BCardType.CardType.FalconSkill:
                break;

            case BCardType.CardType.AbsorptionAndPowerSkill:
                break;

            case BCardType.CardType.LeonaPassiveSkill:
                break;

            case BCardType.CardType.FearSkill:
                break;

            case BCardType.CardType.SniperAttack:
                break;

            case BCardType.CardType.FrozenDebuff:
                break;

            case BCardType.CardType.JumpBackPush:
                break;

            case BCardType.CardType.FairyXPIncrease:
                break;

            case BCardType.CardType.SummonAndRecoverHP:
                break;

            case BCardType.CardType.TeamArenaBuff:
                break;

            case BCardType.CardType.ArenaCamera:
                break;

            case BCardType.CardType.DarkCloneSummon:
                break;

            case BCardType.CardType.AbsorbedSpirit:
                break;

            case BCardType.CardType.AngerSkill:
                break;

            case BCardType.CardType.MeteoriteTeleport:
                break;

            case BCardType.CardType.StealBuff:
                break;

            case BCardType.CardType.Unknown:
                break;

            case BCardType.CardType.EffectSummon:
                break;

            default:
                Logger.Warn($"Card Type {Type} Not Found!");
                break;
            }
        }
Beispiel #12
0
        public void ApplyBCards(object session, object sender = null, short buffLevel = 0)
        {
            Type type = session.GetType();

            // int counterBuff = 0;

            switch ((BCardType.CardType)Type)
            {
            case BCardType.CardType.Buff:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    Buff buff = null;
                    if (sender != null)
                    {
                        Type sType = sender.GetType();
                        if (sType == typeof(Character) && sender is Character sendingCharacter)
                        {
                            buff = new Buff((short)((short)SecondData + buffLevel), sendingCharacter.Level);

                            //Todo: Get anti stats from BCard
                        }
                    }
                    else
                    {
                        buff = new Buff((short)((short)SecondData + buffLevel), character.Level);
                    }

                    int anti = 0;
                    if (buff?.Card.BuffType == BuffType.Bad)
                    {
                        anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                           s.Effect == (byte)ShellArmorEffectType.ReducedAllNegativeEffect)?.Value ??
                                0;
                        switch (SecondData)
                        {
                        case 1:
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType
                                                                               .ReducedBleedingAndMinorBleeding)
                                    ?.Value ?? 0;
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedAllBleedingType)
                                    ?.Value ?? 0;
                            break;

                        case 7:
                            anti += character.ShellEffectArmor
                                    ?.FirstOrDefault(s =>
                                                     s.Effect == (byte)ShellArmorEffectType.ReducedStun)?.Value ?? 0;
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedAllStun)?.Value ?? 0;
                            break;

                        case 21:
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedMinorBleeding)?.Value ??
                                    0;
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType
                                                                               .ReducedBleedingAndMinorBleeding)
                                    ?.Value ?? 0;
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedAllBleedingType)
                                    ?.Value ?? 0;
                            break;

                        case 27:
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedFreeze)?.Value ?? 0;
                            break;

                        case 42:
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedAllBleedingType)
                                    ?.Value ?? 0;
                            break;

                        case 66:
                            anti += character.ShellEffectArmor?.FirstOrDefault(s =>
                                                                               s.Effect == (byte)ShellArmorEffectType.ReducedAllStun)?.Value ?? 0;
                            break;
                        }
                    }

                    if (ServerManager.RandomNumber() < FirstData / 100D * (100 - anti))
                    {
                        character.AddBuff(buff);
                    }
                }
                else if (type == typeof(MapMonster))
                {
                    if (ServerManager.RandomNumber() < FirstData && session is MapMonster mapMonster)
                    {
                        mapMonster.AddBuff(new Buff((short)((short)SecondData + buffLevel), mapMonster.Monster.Level));
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
            }
            break;

            case BCardType.CardType.Move:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    character.LastSpeedChange = DateTime.UtcNow;
                    character.Session.SendPacket(character.GenerateCond());
                }
            }
            break;

            case BCardType.CardType.Summons:
            {
                if (type == typeof(Character))
                {
                    // jajamaru spawn
                    if (session is Character character && character.MapInstance != null)
                    {
                        List <MonsterToSummon> summonParameters = new List <MonsterToSummon>();
                        for (int i = 0; i < FirstData; i++)
                        {
                            short x, y;
                            byte  t = 0;
                            do
                            {
                                x = (short)(ServerManager.RandomNumber(-3, 3) + character.PositionX);
                                y = (short)(ServerManager.RandomNumber(-3, 3) + character.PositionY);
                                t++;
                            } while (!character.MapInstance.Map.IsBlockedZone(x, y) && t < byte.MaxValue);
                            summonParameters.Add(new MonsterToSummon((short)SecondData, new MapCell {
                                    X = x, Y = y
                                },
                                                                     -1, true));
                        }

                        if (ServerManager.RandomNumber() <= Math.Abs(ThirdData) || ThirdData == 0)
                        {
                            switch (SubType)
                            {
                            case 2:
                                EventHelper.Instance.RunEvent(new EventContainer(
                                                                  character.Session.CurrentMapInstance, EventActionType.SpawnMonsters,
                                                                  summonParameters));
                                break;
                            }
                        }
                    }
                }
                else if (type == typeof(MapMonster))
                {
                    if (session is MapMonster mapMonster && mapMonster.MapInstance != null)
                    {
                        List <MonsterToSummon> summonParameters = new List <MonsterToSummon>();
                        for (int i = 0; i < FirstData; i++)
                        {
                            short x, y;
                            byte  t = 0;
                            do
                            {
                                x = (short)(ServerManager.RandomNumber(-3, 3) + mapMonster.MapX);
                                y = (short)(ServerManager.RandomNumber(-3, 3) + mapMonster.MapY);
                                t++;
                            } while (!mapMonster.MapInstance.Map.IsBlockedZone(x, y) && t < byte.MaxValue);
                            summonParameters.Add(new MonsterToSummon((short)SecondData, new MapCell {
                                    X = x, Y = y
                                },
                                                                     -1, true));
                        }

                        if (ServerManager.RandomNumber() <= Math.Abs(ThirdData) || ThirdData == 0)
                        {
                            switch (SubType)
                            {
                            case 2:
                                EventHelper.Instance.RunEvent(new EventContainer(mapMonster.MapInstance,
                                                                                 EventActionType.SpawnMonsters, summonParameters));
                                break;

                            default:
                                if (mapMonster.OnDeathEvents.All(s =>
                                                                 s.EventActionType != EventActionType.SpawnMonsters))
                                {
                                    mapMonster.OnDeathEvents.Add(new EventContainer(mapMonster.MapInstance,
                                                                                    EventActionType.SpawnMonsters, summonParameters));
                                }

                                break;
                            }
                        }
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
            }
            break;

            case BCardType.CardType.SpecialAttack:
                break;

            case BCardType.CardType.SpecialDefence:
                break;

            case BCardType.CardType.AttackPower:
                break;

            case BCardType.CardType.Target:
                break;

            case BCardType.CardType.Critical:
                break;

            case BCardType.CardType.SpecialCritical:
                break;

            case BCardType.CardType.Element:
                break;

            case BCardType.CardType.IncreaseDamage:
                break;

            case BCardType.CardType.Defence:
                break;

            case BCardType.CardType.DodgeAndDefencePercent:
                break;

            case BCardType.CardType.Block:
                break;

            case BCardType.CardType.Absorption:
                break;

            case BCardType.CardType.ElementResistance:
                break;

            case BCardType.CardType.EnemyElementResistance:
                break;

            case BCardType.CardType.Damage:
                break;

            case BCardType.CardType.GuarantedDodgeRangedAttack:
                break;

            case BCardType.CardType.Morale:
                break;

            case BCardType.CardType.Casting:
                break;

            case BCardType.CardType.Reflection:
                break;

            case BCardType.CardType.DrainAndSteal:
                break;

            case BCardType.CardType.HealingBurningAndCasting:
            {
                if (type == typeof(Character))
                {
                    if (session is Character character && character.Hp > 0)
                    {
                        int bonus;
                        if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreHP / 10)
                        {
                            if (IsLevelScaled)
                            {
                                bonus = character.Level * FirstData;
                            }
                            else
                            {
                                bonus = FirstData;
                            }

                            if (character.Hp + bonus <= character.HPLoad())
                            {
                                character.Hp += bonus;
                            }
                            else
                            {
                                bonus        = (int)character.HPLoad() - character.Hp;
                                character.Hp = (int)character.HPLoad();
                            }

                            character.Session.CurrentMapInstance?.Broadcast(character.Session,
                                                                            character.GenerateRc(bonus));
                        }

                        if (SubType == (byte)AdditionalTypes.HealingBurningAndCasting.RestoreMP / 10)
                        {
                            if (IsLevelScaled)
                            {
                                bonus = character.Level * FirstData;
                            }
                            else
                            {
                                bonus = FirstData;
                            }

                            if (character.Mp + bonus <= character.MPLoad())
                            {
                                character.Mp += bonus;
                            }
                            else
                            {
                                character.Mp = (int)character.MPLoad();
                            }
                        }

                        character.Session.SendPacket(character.GenerateStat());
                    }
                }
                else if (type == typeof(MapMonster))
                {
                    if (ServerManager.RandomNumber() < FirstData && session is MapMonster mapMonster)
                    {
                        mapMonster.AddBuff(new Buff((short)SecondData, mapMonster.Monster.Level));
                    }
                }
                else if (type == typeof(MapNpc))
                {
                }
                else if (type == typeof(Mate))
                {
                }
            }
            break;

            case BCardType.CardType.Hpmp:
                if (type == typeof(Character))
                {
                    if (session is Character c)
                    {
                        switch (SubType)
                        {
                        case (byte)AdditionalTypes.Hpmp.RestoreDecreasedMP / 10:
                        {
                            int bonus = (int)(FirstData * c.MPLoad() / 100);

                            c.Mp = c.Mp + bonus > 1 ? c.Mp + bonus : c.Mp = 1;
                        }
                        break;
                        }
                    }
                }

                break;

            case BCardType.CardType.SpecialisationBuffResistance:
            {
                switch (SubType)
                {
                case (byte)AdditionalTypes.SpecialisationBuffResistance.RemoveBadEffects / 10:
                {
                    if (session is Character c &&              /*&& sender is ClientSession senderSession*/
                        ServerManager.RandomNumber() < Math.Abs(FirstData))
                    {
                        c.DisableBuffs(FirstData > 0 ? BuffType.Good : BuffType.Bad, SecondData);
                    }
                }
                break;
                }
            }
            break;

            case BCardType.CardType.SpecialEffects:
                break;

            case BCardType.CardType.Capture:
            {
                if (type == typeof(MapMonster) && session is MapMonster mapMonster &&
                    sender is ClientSession senderSession)
                {
                    NpcMonster mateNpc = ServerManager.GetNpcMonster(mapMonster.MonsterVNum);
                    if (mateNpc != null)
                    {
                        if (mapMonster.Monster.Catch)
                        {
                            if (mapMonster.IsAlive &&
                                mapMonster.CurrentHp <= (int)((double)mapMonster.MaxHp / 2))
                            {
                                if (mapMonster.Monster.Level < senderSession.Character.Level)
                                {
                                    // TODO: find a new algorithm
                                    int[] chance = { 100, 80, 60, 40, 20, 0 };
                                    if (ServerManager.RandomNumber() < chance[ServerManager.RandomNumber(0, 5)])
                                    {
                                        Mate mate = new Mate(senderSession.Character, mateNpc,
                                                             (byte)(mapMonster.Monster.Level - 15 > 0
                                                        ? mapMonster.Monster.Level - 15
                                                        : 1), MateType.Pet);
                                        if (senderSession.Character.CanAddMate(mate))
                                        {
                                            senderSession.Character.AddPetWithSkill(mate);
                                            senderSession.SendPacket(
                                                UserInterfaceHelper.GenerateMsg(
                                                    Language.Instance.GetMessageFromKey("CATCH_SUCCESS"), 0));
                                            senderSession.CurrentMapInstance?.Broadcast(
                                                StaticPacketHelper.GenerateEff(UserType.Player,
                                                                               senderSession.Character.CharacterId, 197));
                                            senderSession.CurrentMapInstance?.Broadcast(
                                                StaticPacketHelper.SkillUsed(UserType.Player,
                                                                             senderSession.Character.CharacterId, 3,
                                                                             mapMonster.MapMonsterId, -1, 0, 15, -1, -1, -1, true,
                                                                             (int)(mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100
                                                                                   ), 0, -1, 0));
                                            mapMonster.SetDeathStatement();
                                            senderSession.CurrentMapInstance?.Broadcast(
                                                StaticPacketHelper.Out(UserType.Monster,
                                                                       mapMonster.MapMonsterId));
                                        }
                                        else
                                        {
                                            senderSession.SendPacket(
                                                senderSession.Character.GenerateSay(
                                                    Language.Instance.GetMessageFromKey("PET_SLOT_FULL"), 10));
                                            senderSession.SendPacket(
                                                StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                        }
                                    }
                                    else
                                    {
                                        senderSession.SendPacket(
                                            UserInterfaceHelper.GenerateMsg(
                                                Language.Instance.GetMessageFromKey("CATCH_FAIL"), 0));
                                        senderSession.CurrentMapInstance?.Broadcast(
                                            StaticPacketHelper.SkillUsed(UserType.Player,
                                                                         senderSession.Character.CharacterId, 3, mapMonster.MapMonsterId,
                                                                         -1, 0, 15, -1, -1, -1, true,
                                                                         (int)(mapMonster.CurrentHp / (float)mapMonster.MaxHp * 100),
                                                                         0, -1, 0));
                                    }
                                }
                                else
                                {
                                    senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(
                                                                 Language.Instance.GetMessageFromKey("LEVEL_LOWER_THAN_MONSTER"), 0));
                                    senderSession.SendPacket(
                                        StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                                }
                            }
                            else
                            {
                                senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(
                                                             Language.Instance.GetMessageFromKey("CURRENT_HP_TOO_HIGH"), 0));
                                senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                            }
                        }
                        else
                        {
                            senderSession.SendPacket(UserInterfaceHelper.GenerateMsg(
                                                         Language.Instance.GetMessageFromKey("MONSTER_CANT_BE_CAPTURED"), 0));
                            senderSession.SendPacket(StaticPacketHelper.Cancel(2, mapMonster.MapMonsterId));
                        }
                    }
                }
            }
            break;

            case BCardType.CardType.SpecialDamageAndExplosions:
                break;

            case BCardType.CardType.SpecialEffects2:
                if (type == typeof(Character))
                {
                    if (session is Character c)
                    {
                        short destinationX = c.PositionX;
                        short destinationY = c.PositionY;
                        switch (SubType)
                        {
                        case (byte)AdditionalTypes.SpecialEffects2.TeleportInRadius / 10:
                        {
                            switch (c.Direction)
                            {
                            case 0:
                                // -y
                                destinationY -= (short)FirstData;
                                break;

                            case 1:
                                // +x
                                destinationX += (short)FirstData;
                                break;

                            case 2:
                                // +y
                                destinationY += (short)FirstData;
                                break;

                            case 3:
                                // -x
                                destinationX -= (short)FirstData;
                                break;

                            case 4:
                                // -x -y
                                destinationX -= (short)FirstData;
                                destinationY -= (short)FirstData;
                                break;

                            case 5:
                                // +x +y
                                destinationX += (short)FirstData;
                                destinationY += (short)FirstData;
                                break;

                            case 6:
                                // +x -y
                                destinationX += (short)FirstData;
                                destinationY -= (short)FirstData;
                                break;

                            case 7:
                                // -x +y
                                destinationX -= (short)FirstData;
                                destinationY += (short)FirstData;
                                break;
                            }

                            ServerManager.Instance.TeleportForward(c.Session, c.MapInstanceId, destinationX,
                                                                   destinationY);
                        }
                        break;
                        }
                    }
                }

                break;

            case BCardType.CardType.CalculatingLevel:
                break;

            case BCardType.CardType.Recovery:
                break;

            case BCardType.CardType.MaxHpmp:
                break;

            case BCardType.CardType.MultAttack:
                break;

            case BCardType.CardType.MultDefence:
                break;

            case BCardType.CardType.TimeCircleSkills:
                break;

            case BCardType.CardType.RecoveryAndDamagePercent:
                break;

            case BCardType.CardType.Count:
                break;

            case BCardType.CardType.NoDefeatAndNoDamage:
                break;

            case BCardType.CardType.SpecialActions:
            {
                switch (SubType)
                {
                case (byte)AdditionalTypes.SpecialActions.RunAway / 10:
                    if (session is MapMonster m)
                    {
                        m.MapInstance.Broadcast(StaticPacketHelper.Say(UserType.Monster, m.MapMonsterId, 0, "!!!"));
                        m.RemoveTarget();
                        for (int i = 0; i < 10; i++)
                        {
                            Observable.Timer(TimeSpan.FromSeconds(i)).Subscribe(o =>
                                {
                                    m.MapX++;
                                    m.MapY++;
                                    m.IgnoreTargetsUntil = DateTime.UtcNow.AddSeconds(10);
                                    m.RemoveTarget();
                                });
                        }
                    }
                    break;
                }
            }
            break;

            case BCardType.CardType.Mode:
                break;

            case BCardType.CardType.NoCharacteristicValue:
                break;

            case BCardType.CardType.LightAndShadow:
            {
                switch (SubType)
                {
                case (byte)AdditionalTypes.LightAndShadow.RemoveBadEffects / 10:
                {
                    if (session is Character c /*&& sender is ClientSession senderSession*/)
                    {
                        c.DisableBuffs(BuffType.Bad, FirstData);
                    }
                }
                break;
                }
            }
            break;

            case BCardType.CardType.Item:
                break;

            case BCardType.CardType.DebuffResistance:
                break;

            case BCardType.CardType.SpecialBehaviour:
                break;

            case BCardType.CardType.Quest:
                break;

            case BCardType.CardType.SecondSpCard:
                break;

            case BCardType.CardType.SpCardUpgrade:
                break;

            case BCardType.CardType.HugeSnowman:
                break;

            case BCardType.CardType.Drain:
                break;

            case BCardType.CardType.BossMonstersSkill:
                break;

            case BCardType.CardType.LordHatus:
                break;

            case BCardType.CardType.LordCalvinas:
                break;

            case BCardType.CardType.SeSpecialist:
                break;

            case BCardType.CardType.FourthGlacernonFamilyRaid:
                break;

            case BCardType.CardType.SummonedMonsterAttack:
                break;

            case BCardType.CardType.BearSpirit:
                break;

            case BCardType.CardType.SummonSkill:
                break;

            case BCardType.CardType.InflictSkill:
                break;

            case BCardType.CardType.HideBarrelSkill:
                break;

            case BCardType.CardType.FocusEnemyAttentionSkill:
                break;

            case BCardType.CardType.TauntSkill:
                break;

            case BCardType.CardType.FireCannoneerRangeBuff:
                break;

            case BCardType.CardType.VulcanoElementBuff:
                break;

            case BCardType.CardType.DamageConvertingSkill:
                break;

            case BCardType.CardType.MeditationSkill:
            {
                if (type == typeof(Character) && session is Character character)
                {
                    if (SkillVNum.HasValue &&
                        SubType.Equals((byte)AdditionalTypes.MeditationSkill.CausingChance / 10) &&
                        ServerManager.RandomNumber() < FirstData)
                    {
                        Skill skill    = ServerManager.GetSkill(SkillVNum.Value);
                        Skill newSkill = ServerManager.GetSkill((short)SecondData);
                        Observable.Timer(TimeSpan.FromMilliseconds(100)).Subscribe(observer =>
                            {
                                foreach (QuicklistEntryDTO quicklistEntry in character.QuicklistEntries.Where(s =>
                                                                                                              s.Morph == character.Morph && s.Pos.Equals(skill.CastId)))
                                {
                                    character.Session.SendPacket(
                                        $"qset {quicklistEntry.Q1} {quicklistEntry.Q2} {quicklistEntry.Type}.{quicklistEntry.Slot}.{newSkill.CastId}.0");
                                }

                                character.Session.SendPacket($"mslot {newSkill.CastId} -1");
                            });
                        character.SkillComboCount++;
                        character.LastSkillComboUse = DateTime.UtcNow;
                        if (skill.CastId > 10)
                        {
                            // HACK this way
                            Observable.Timer(TimeSpan.FromMilliseconds((skill.Cooldown * 100) + 500))
                            .Subscribe(observer =>
                                       character.Session.SendPacket(StaticPacketHelper.SkillReset(skill.CastId)));
                        }
                    }

                    switch (SubType)
                    {
                    case 2:
                        character.MeditationDictionary[(short)SecondData] = DateTime.UtcNow.AddSeconds(4);
                        break;

                    case 3:
                        character.MeditationDictionary[(short)SecondData] = DateTime.UtcNow.AddSeconds(8);
                        break;

                    case 4:
                        character.MeditationDictionary[(short)SecondData] = DateTime.UtcNow.AddSeconds(12);
                        break;
                    }
                }
            }
            break;

            case BCardType.CardType.FalconSkill:
            {
                if (session is Character c)
                {
                    switch (SubType)
                    {
                    case (byte)AdditionalTypes.FalconSkill.Hide:
                        c.Invisible = true;
                        c.Mates.Where(s => s.IsTeamMember).ToList().ForEach(s =>
                                                                            c.Session.CurrentMapInstance?.Broadcast(s.GenerateOut()));
                        c.Session.CurrentMapInstance?.Broadcast(c.GenerateInvisible());
                        c.Session.SendPacket(c.GenerateEq());
                        break;
                    }
                }
            }
            break;

            case BCardType.CardType.AbsorptionAndPowerSkill:
                break;

            case BCardType.CardType.LeonaPassiveSkill:
                break;

            case BCardType.CardType.FearSkill:
                break;

            case BCardType.CardType.SniperAttack:
                break;

            case BCardType.CardType.FrozenDebuff:
                break;

            case BCardType.CardType.JumpBackPush:
                break;

            case BCardType.CardType.FairyXPIncrease:
                break;

            case BCardType.CardType.SummonAndRecoverHP:
                break;

            case BCardType.CardType.TeamArenaBuff:
                break;

            case BCardType.CardType.ArenaCamera:
                break;

            case BCardType.CardType.DarkCloneSummon:
                break;

            case BCardType.CardType.AbsorbedSpirit:
                break;

            case BCardType.CardType.AngerSkill:
                break;

            case BCardType.CardType.MeteoriteTeleport:
                if (type == typeof(Character))
                {
                    if (session is Character character)
                    {
                        switch (SubType)
                        {
                        case ((byte)AdditionalTypes.MeteoriteTeleport.TeleportYouAndGroupToSavedLocation / 10):
                            if (character.TeleportSet == false)
                            {
                                character.TeleportX   = character.PositionX;
                                character.TeleportY   = character.PositionY;
                                character.TeleportMap = character.MapId;
                                character.MapInstance.Broadcast(StaticPacketHelper.GenerateEff(UserType.Player, character.CharacterId, 4497));
                                character.TeleportSet = true;
                                Observable.Timer(TimeSpan.FromSeconds(40)).Subscribe(o => character.TeleportSet = false);
                            }
                            else
                            {
                                if (character.MapInstance.IsPvp)
                                {
                                    if (character.MapInstance.MapInstanceType != MapInstanceType.BaseMapInstance)
                                    {
                                        character.TeleportSet = false;
                                        return;
                                    }

                                    character.MapInstance.Broadcast($"tp 1 {character.CharacterId} {character.TeleportX} {character.TeleportY} 0");
                                    character.PositionX   = character.TeleportX;
                                    character.PositionY   = character.TeleportY;
                                    character.TeleportSet = false;
                                }
                                else
                                {
                                    if (character.MapId == character.TeleportMap)
                                    {
                                        if (character.MapInstance.MapInstanceType == MapInstanceType.CaligorInstance)
                                        {
                                            character.TeleportSet = false;
                                            return;
                                        }
                                        character.MapInstance.Broadcast($"tp 1 {character.CharacterId} {character.TeleportX} {character.TeleportY} 0");
                                        character.PositionX   = character.TeleportX;
                                        character.PositionY   = character.TeleportY;
                                        character.TeleportSet = false;
                                    }
                                    else
                                    {
                                        character.TeleportSet = false;
                                    }
                                }
                            }
                            break;

                        case (byte)AdditionalTypes.MeteoriteTeleport.CauseMeteoriteFall / 10:
                        {
                            int amount = 10 + (character.Level / FirstData);

                            for (int i = 0; i < amount; i++)
                            {
                                Observable.Timer(TimeSpan.FromMilliseconds(i * 500)).Subscribe(o => character.SpawnMeteorite());
                            }
                        }
                        break;
                        }
                    }
                }
                break;

            case BCardType.CardType.StealBuff:
                break;

            case BCardType.CardType.Unknown:
                break;

            case BCardType.CardType.EffectSummon:
                break;

            default:
                Logger.Warn($"Card Type {Type} not defined!");
                break;
            }
        }