Ejemplo n.º 1
0
        public static void HandleSelectRealm(WorldSession session, ClientSelectRealm selectRealm)
        {
            ServerInfo server = ServerManager.Servers.SingleOrDefault(s => s.Model.Id == selectRealm.RealmId);

            if (server == null)
            {
                throw new InvalidPacketValueException();
            }

            // clicking back or selecting the current realm also triggers this packet, client crashes if we don't ignore it
            if (server.Model.Id == WorldServer.RealmId)
            {
                return;
            }

            byte[] sessionKey = RandomProvider.GetBytes(16u);
            session.EnqueueEvent(new TaskEvent(AuthDatabase.UpdateAccountSessionKey(session.Account, sessionKey),
                                               () =>
            {
                session.EnqueueMessageEncrypted(new ServerNewRealm
                {
                    SessionKey  = sessionKey,
                    GatewayData = new ServerNewRealm.Gateway
                    {
                        Address = server.Address,
                        Port    = server.Model.Port
                    },
                    RealmName = server.Model.Name,
                    Type      = (RealmType)server.Model.Type
                });
            }));
        }
Ejemplo n.º 2
0
        public static void HandlePlayerInfoRequest(WorldSession session, ClientPlayerInfoRequest request)
        {
            session.EnqueueEvent(new TaskGenericEvent <Character>(CharacterDatabase.GetCharacterById(request.Identity.CharacterId),
                                                                  character =>
            {
                if (character == null)
                {
                    throw new InvalidPacketValueException();
                }

                session.EnqueueMessageEncrypted(new ServerPlayerInfoFullResponse
                {
                    BaseData = new ServerPlayerInfoFullResponse.Base
                    {
                        ResultCode = 0,
                        Identity   = new TargetPlayerIdentity
                        {
                            RealmId     = WorldServer.RealmId,
                            CharacterId = character.Id
                        },
                        Name    = character.Name,
                        Faction = (Faction)character.FactionId
                    },
                    IsClassPathSet          = true,
                    Path                    = (Path)character.ActivePath,
                    Class                   = (Class)character.Class,
                    Level                   = character.Level,
                    IsLastLoggedOnInDaysSet = false,
                    LastLoggedInDays        = -1f
                });
            }));
        }
Ejemplo n.º 3
0
        public static void HandleItemUseDecor(WorldSession session, ClientItemUseDecor itemUseDecor)
        {
            Item item = session.Player.Inventory.GetItem(itemUseDecor.ItemGuid);

            if (item == null)
            {
                throw new InvalidPacketValueException();
            }

            HousingDecorInfoEntry entry = GameTableManager.HousingDecorInfo.GetEntry(item.Entry.HousingDecorInfoId);

            if (entry == null)
            {
                throw new InvalidPacketValueException();
            }

            Task <Residence> task = ResidenceManager.GetResidence(session.Player.Name);

            session.EnqueueEvent(new TaskGenericEvent <Residence>(task,
                                                                  residence =>
            {
                if (residence == null)
                {
                    residence = ResidenceManager.CreateResidence(session.Player);
                }

                if (session.Player.Inventory.ItemUse(item))
                {
                    residence.DecorCreate(entry);
                }
            }));
        }
Ejemplo n.º 4
0
        public static void HandleHousingVisit(WorldSession session, ClientHousingVisit housingVisit)
        {
            if (!(session.Player.Map is ResidenceMap))
            {
                throw new InvalidPacketValueException();
            }

            if (!session.Player.CanTeleport())
            {
                return;
            }

            Task <Residence> residenceTask;

            if (housingVisit.TargetResidenceName != "")
            {
                residenceTask = ResidenceManager.Instance.GetResidence(housingVisit.TargetResidenceName);
            }
            else if (housingVisit.TargetResidence.ResidenceId != 0ul)
            {
                residenceTask = ResidenceManager.Instance.GetResidence(housingVisit.TargetResidence.ResidenceId);
            }
            else
            {
                throw new NotImplementedException();
            }

            session.EnqueueEvent(new TaskGenericEvent <Residence>(residenceTask,
                                                                  residence =>
            {
                if (residence == null)
                {
                    // TODO: show error
                    return;
                }

                switch (residence.PrivacyLevel)
                {
                case ResidencePrivacyLevel.Private:
                    {
                        // TODO: show error
                        return;
                    }

                // TODO: check if player is either a neighbour or roommate
                case ResidencePrivacyLevel.NeighborsOnly:
                    break;

                case ResidencePrivacyLevel.RoommatesOnly:
                    break;
                }

                // teleport player to correct residence instance
                ResidenceEntrance entrance = ResidenceManager.Instance.GetResidenceEntrance(residence);
                session.Player.TeleportTo(entrance.Entry, entrance.Position, 0u, residence.Id);
            }));
        }
Ejemplo n.º 5
0
        public static void HandleCharacterSelect(WorldSession session, ClientCharacterSelect characterSelect)
        {
            Character character = session.Characters.SingleOrDefault(c => c.Id == characterSelect.CharacterId);

            if (character == null)
            {
                session.EnqueueMessageEncrypted(new ServerCharacterSelectFail
                {
                    Result = CharacterSelectResult.Failed
                });
                return;
            }

            session.Player = new Player(session, character);

            WorldEntry entry = GameTableManager.World.GetEntry(character.WorldId);

            if (entry == null)
            {
                throw new ArgumentOutOfRangeException();
            }

            switch (entry.Type)
            {
            // housing map
            case 5:
            {
                // characters logging in to a housing map are returned to their own residence
                session.EnqueueEvent(new TaskGenericEvent <Residence>(ResidenceManager.GetResidence(session.Player.Name),
                                                                      residence =>
                    {
                        if (residence == null)
                        {
                            residence = ResidenceManager.CreateResidence(session.Player);
                        }

                        ResidenceEntrance entrance = ResidenceManager.GetResidenceEntrance(residence);
                        var mapInfo = new MapInfo(entrance.Entry, 0u, residence.Id);
                        MapManager.AddToMap(session.Player, mapInfo, entrance.Position);
                    }));

                break;
            }

            default:
            {
                var mapInfo = new MapInfo(entry);
                var vector3 = new Vector3(character.LocationX, character.LocationY, character.LocationZ);
                MapManager.AddToMap(session.Player, mapInfo, vector3);
                break;
            }
            }
        }
Ejemplo n.º 6
0
        public static void HandleHelloRealm(WorldSession session, ClientHelloRealm helloRealm)
        {
            // prevent packets from being processed until asynchronous account select task is complete
            session.CanProcessPackets = false;

            session.EnqueueEvent(new TaskGenericEvent <Account>(AuthDatabase.GetAccountAsync(helloRealm.Email, helloRealm.SessionKey),
                                                                account =>
            {
                if (account == null)
                {
                    throw new InvalidPacketValueException($"Failed to find account, Id:{helloRealm.AccountId}, Email:{helloRealm.Email}, SessionKey:{helloRealm.SessionKey}!");
                }

                session.Initialise(account);
                session.SetEncryptionKey(helloRealm.SessionKey);
                session.CanProcessPackets = true;
            }));
        }
Ejemplo n.º 7
0
        public static void HandleSelectRealm(WorldSession session, ClientSelectRealm selectRealm)
        {
            ServerInfo server = ServerManager.Instance.Servers.SingleOrDefault(s => s.Model.Id == selectRealm.RealmId);

            if (server == null)
            {
                throw new InvalidPacketValueException();
            }

            // clicking back or selecting the current realm also triggers this packet, client crashes if we don't ignore it
            if (server.Model.Id == WorldServer.RealmId)
            {
                return;
            }

            // TODO: Return proper error packet if server is not online
            if (!server.IsOnline)
            {
                session.EnqueueMessageEncrypted(new ServerForceKick());
                return;
            }

            byte[] sessionKeyBytes  = RandomProvider.GetBytes(16u);
            string sessionKeyString = BitConverter.ToString(sessionKeyBytes).Replace("-", "");

            session.EnqueueEvent(new TaskEvent(DatabaseManager.Instance.AuthDatabase.UpdateAccountSessionKey(session.Account, sessionKeyString),
                                               () =>
            {
                session.EnqueueMessageEncrypted(new ServerNewRealm
                {
                    SessionKey  = sessionKeyBytes,
                    GatewayData = new ServerNewRealm.Gateway
                    {
                        Address = server.Address,
                        Port    = server.Model.Port
                    },
                    RealmName = server.Model.Name,
                    Type      = (RealmType)server.Model.Type
                });
            }));
        }
Ejemplo n.º 8
0
        public static void HandleCharacterList(WorldSession session, ClientCharacterList characterList)
        {
            session.EnqueueEvent(new TaskGenericEvent <List <Character> >(CharacterDatabase.GetCharacters(session.Account.Id),
                                                                          characters =>
            {
                session.Characters.Clear();
                session.Characters.AddRange(characters);

                session.EnqueueMessageEncrypted(new ServerAccountEntitlements
                {
                    Entitlements =
                    {
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.BaseCharacterSlots,
                            Count       = 12
                        },
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.ChuaWarriorUnlock,
                            Count       = 1
                        },
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.AurinEngineerUnlock,
                            Count       = 1
                        }
                    }
                });

                session.EnqueueMessageEncrypted(new ServerMaxCharacterLevelAchieved
                {
                    Level = 50
                });

                var serverCharacterList = new ServerCharacterList
                {
                    RealmId = WorldServer.RealmId
                };
                foreach (Character character in characters)
                {
                    var listCharacter = new ServerCharacterList.Character
                    {
                        Id          = character.Id,
                        Name        = character.Name,
                        Sex         = (Sex)character.Sex,
                        Race        = (Race)character.Race,
                        Class       = (Class)character.Class,
                        Faction     = character.FactionId,
                        Level       = character.Level,
                        WorldId     = 3460,
                        WorldZoneId = 5967,
                        RealmId     = WorldServer.RealmId
                    };

                    // create a temporary inventory to show equipped gear
                    var inventory = new Inventory(null, character);
                    foreach (ItemVisual itemVisual in inventory.GetItemVisuals())
                    {
                        listCharacter.Gear.Add(itemVisual);
                    }

                    foreach (CharacterAppearance appearance in character.CharacterAppearance)
                    {
                        listCharacter.Appearance.Add(new ItemVisual
                        {
                            Slot      = (ItemSlot)appearance.Slot,
                            DisplayId = appearance.DisplayId
                        });
                    }

                    foreach (CharacterCustomisation customisation in character.CharacterCustomisation)
                    {
                        listCharacter.Labels.Add(customisation.Label);
                        listCharacter.Values.Add(customisation.Value);
                    }

                    foreach (CharacterBone bone in character.CharacterBone.OrderBy(bone => bone.BoneIndex))
                    {
                        listCharacter.Bones.Add(bone.Bone);
                    }

                    serverCharacterList.Characters.Add(listCharacter);
                }

                session.EnqueueMessageEncrypted(serverCharacterList);
            }));
        }
Ejemplo n.º 9
0
        public static void HandleCharacterCreate(WorldSession session, ClientCharacterCreate characterCreate)
        {
            try
            {
                // TODO: validate name and path

                CharacterCreationEntry creationEntry = GameTableManager.CharacterCreation.GetEntry(characterCreate.CharacterCreationId);
                if (creationEntry == null)
                {
                    throw new InvalidPacketValueException();
                }

                if (creationEntry.EntitlementIdRequired != 0u)
                {
                    // TODO: Aurin engineer has this
                }

                var character = new Character
                {
                    AccountId  = session.Account.Id,
                    Id         = AssetManager.NextCharacterId,
                    Name       = characterCreate.Name,
                    Race       = (byte)creationEntry.RaceId,
                    Sex        = (byte)creationEntry.Sex,
                    Class      = (byte)creationEntry.ClassId,
                    Level      = 1,
                    FactionId  = (ushort)creationEntry.FactionId,
                    ActivePath = characterCreate.Path
                };

                for (Path path = Path.Soldier; path <= Path.Explorer; path++)
                {
                    character.CharacterPath.Add(new CharacterPath
                    {
                        Path     = (byte)path,
                        Unlocked = Convert.ToByte(characterCreate.Path == (byte)path)
                    });
                }

                // merge seperate label and value lists into a single dictonary
                Dictionary <uint, uint> customisations = characterCreate.Labels
                                                         .Zip(characterCreate.Values, (l, v) => new { l, v })
                                                         .ToDictionary(p => p.l, p => p.v);

                foreach ((uint label, uint value) in customisations)
                {
                    character.CharacterCustomisation.Add(new CharacterCustomisation
                    {
                        Label = label,
                        Value = value
                    });

                    CharacterCustomizationEntry entry = GetCharacterCustomisation(customisations, creationEntry.RaceId, creationEntry.Sex, label, value);
                    if (entry == null)
                    {
                        continue;
                    }

                    character.CharacterAppearance.Add(new CharacterAppearance
                    {
                        Slot      = (byte)entry.ItemSlotId,
                        DisplayId = (ushort)entry.ItemDisplayId
                    });
                }

                for (int i = 0; i < characterCreate.Bones.Count; ++i)
                {
                    character.CharacterBone.Add(new CharacterBone
                    {
                        BoneIndex = (byte)(i),
                        Bone      = characterCreate.Bones[i]
                    });
                }
                //TODO: handle starting locations per race
                character.LocationX = -7683.809f;
                character.LocationY = -942.5914f;
                character.LocationZ = -666.6343f;
                character.WorldId   = 870;

                // create a temporary inventory to create starting gear
                var inventory = new Inventory(character.Id, creationEntry);
                var items     = inventory
                                .SelectMany(b => b)
                                .Select(i => i);

                // TODO: actually error check this
                session.EnqueueEvent(new TaskEvent(CharacterDatabase.CreateCharacter(character, items),
                                                   () =>
                {
                    session.Characters.Add(character);
                    session.EnqueueMessageEncrypted(new ServerCharacterCreate
                    {
                        CharacterId = character.Id,
                        WorldId     = character.WorldId,
                        Result      = 3
                    });
                }));
            }
            catch
            {
                session.EnqueueMessageEncrypted(new ServerCharacterCreate
                {
                    Result = 0
                });

                throw;
            }

            CharacterCustomizationEntry GetCharacterCustomisation(Dictionary <uint, uint> customisations, uint race, uint sex, uint primaryLabel, uint primaryValue)
            {
                ImmutableList <CharacterCustomizationEntry> entries = AssetManager.GetPrimaryCharacterCustomisation(race, sex, primaryLabel, primaryValue);

                if (entries == null)
                {
                    return(null);
                }
                if (entries.Count == 1)
                {
                    return(entries[0]);
                }

                // customisation has multiple results, filter with secondary label and value
                uint secondaryLabel = entries.First(e => e.CharacterCustomizationLabelId01 != 0).CharacterCustomizationLabelId01;
                uint secondaryValue = customisations[secondaryLabel];

                CharacterCustomizationEntry entry = entries.SingleOrDefault(e => e.CharacterCustomizationLabelId01 == secondaryLabel && e.Value01 == secondaryValue);

                return(entry ?? entries.Single(e => e.CharacterCustomizationLabelId01 == 0 && e.Value01 == 0));
            }
        }
Ejemplo n.º 10
0
        public static void HandleCharacterDelete(WorldSession session, ClientCharacterDelete characterDelete)
        {
            CharacterModel characterToDelete = session.Characters.FirstOrDefault(c => c.Id == characterDelete.CharacterId);

            (CharacterModifyResult, uint) GetResult()
            {
                if (characterToDelete == null)
                {
                    return(CharacterModifyResult.DeleteFailed, 0);
                }

                // TODO: Not sure if this is definitely the case, but put it in for good measure
                if (characterToDelete.Mail.Count > 0)
                {
                    foreach (CharacterMailModel characterMail in characterToDelete.Mail)
                    {
                        if (characterMail.Attachment.Count > 0)
                        {
                            return(CharacterModifyResult.DeleteFailed, 0);
                        }
                    }
                }

                uint leaderCount = (uint)GlobalGuildManager.Instance.GetCharacterGuilds(characterToDelete.Id)
                                   .Count(g => g.LeaderId == characterDelete.CharacterId);

                if (leaderCount > 0)
                {
                    return(CharacterModifyResult.DeleteFailed, leaderCount);
                }

                return(CharacterModifyResult.DeleteOk, 0);
            }

            (CharacterModifyResult result, uint data)deleteCheck = GetResult();
            if (deleteCheck.result != CharacterModifyResult.DeleteOk)
            {
                session.EnqueueMessageEncrypted(new ServerCharacterDeleteResult
                {
                    Result = deleteCheck.result,
                    Data   = deleteCheck.data
                });
                return;
            }

            session.CanProcessPackets = false;

            void Save(CharacterContext context)
            {
                var model = new CharacterModel
                {
                    Id = characterToDelete.Id
                };

                EntityEntry <CharacterModel> entity = context.Attach(model);

                model.DeleteTime = DateTime.UtcNow;
                entity.Property(e => e.DeleteTime).IsModified = true;

                model.OriginalName = characterToDelete.Name;
                entity.Property(e => e.OriginalName).IsModified = true;

                model.Name = null;
                entity.Property(e => e.Name).IsModified = true;
            }

            session.EnqueueEvent(new TaskEvent(DatabaseManager.Instance.CharacterDatabase.Save(Save),
                                               () =>
            {
                session.CanProcessPackets = true;

                ResidenceManager.Instance.RemoveResidence(characterToDelete.Name);
                CharacterManager.Instance.DeleteCharacter(characterToDelete.Id, characterToDelete.Name);

                session.EnqueueMessageEncrypted(new ServerCharacterDeleteResult
                {
                    Result = deleteCheck.result
                });
            }));
        }
Ejemplo n.º 11
0
        public static void HandleCharacterCreate(WorldSession session, ClientCharacterCreate characterCreate)
        {
            try
            {
                // TODO: validate name and path
                if (DatabaseManager.Instance.CharacterDatabase.CharacterNameExists(characterCreate.Name))
                {
                    session.EnqueueMessageEncrypted(new ServerCharacterCreate
                    {
                        Result = CharacterModifyResult.CreateFailed_UniqueName
                    });

                    return;
                }

                CharacterCreationEntry creationEntry = GameTableManager.Instance.CharacterCreation.GetEntry(characterCreate.CharacterCreationId);
                if (creationEntry == null)
                {
                    throw new InvalidPacketValueException();
                }

                if (creationEntry.EntitlementIdRequired != 0u)
                {
                    // TODO: Aurin engineer has this
                }

                var character = new CharacterModel
                {
                    AccountId  = session.Account.Id,
                    Id         = AssetManager.Instance.NextCharacterId,
                    Name       = characterCreate.Name,
                    Race       = (byte)creationEntry.RaceId,
                    Sex        = (byte)creationEntry.Sex,
                    Class      = (byte)creationEntry.ClassId,
                    FactionId  = (ushort)creationEntry.FactionId,
                    ActivePath = characterCreate.Path
                };

                for (Path path = Path.Soldier; path <= Path.Explorer; path++)
                {
                    character.Path.Add(new CharacterPathModel
                    {
                        Path     = (byte)path,
                        Unlocked = Convert.ToByte(characterCreate.Path == (byte)path)
                    });
                }

                // merge seperate label and value lists into a single dictonary
                Dictionary <uint, uint> customisations = characterCreate.Labels
                                                         .Zip(characterCreate.Values, (l, v) => new { l, v })
                                                         .ToDictionary(p => p.l, p => p.v);

                foreach ((uint label, uint value) in customisations)
                {
                    character.Customisation.Add(new CharacterCustomisationModel
                    {
                        Label = label,
                        Value = value
                    });

                    CharacterCustomizationEntry entry = GetCharacterCustomisation(customisations, creationEntry.RaceId, creationEntry.Sex, label, value);
                    if (entry == null)
                    {
                        continue;
                    }

                    character.Appearance.Add(new CharacterAppearanceModel
                    {
                        Slot      = (byte)entry.ItemSlotId,
                        DisplayId = (ushort)entry.ItemDisplayId
                    });
                }

                for (int i = 0; i < characterCreate.Bones.Count; ++i)
                {
                    character.Bone.Add(new CharacterBoneModel
                    {
                        BoneIndex = (byte)(i),
                        Bone      = characterCreate.Bones[i]
                    });
                }

                //TODO: handle starting locations per race
                character.LocationX = -7683.809f;
                character.LocationY = -942.5914f;
                character.LocationZ = -666.6343f;
                character.WorldId   = 870;

                character.ActiveSpec = 0;

                // create initial LAS abilities
                UILocation location = 0;
                foreach (SpellLevelEntry spellLevelEntry in GameTableManager.Instance.SpellLevel.Entries
                         .Where(s => s.ClassId == character.Class && s.CharacterLevel == 1))
                {
                    Spell4Entry spell4Entry = GameTableManager.Instance.Spell4.GetEntry(spellLevelEntry.Spell4Id);
                    if (spell4Entry == null)
                    {
                        continue;
                    }

                    character.Spell.Add(new CharacterSpellModel
                    {
                        Id           = character.Id,
                        Spell4BaseId = spell4Entry.Spell4BaseIdBaseSpell,
                        Tier         = 1
                    });

                    character.ActionSetShortcut.Add(new CharacterActionSetShortcutModel
                    {
                        Id           = character.Id,
                        SpecIndex    = 0,
                        Location     = (ushort)location,
                        ShortcutType = (byte)ShortcutType.Spell,
                        ObjectId     = spell4Entry.Spell4BaseIdBaseSpell,
                        Tier         = 1
                    });

                    location++;
                }

                // create a temporary inventory to create starting gear
                var inventory            = new Inventory(character.Id, creationEntry);
                IEnumerable <Item> items = inventory
                                           .SelectMany(b => b)
                                           .Select(i => i);

                //TODO: handle starting stats per class/race
                character.Stat.Add(new CharacterStatModel
                {
                    Id    = character.Id,
                    Stat  = (byte)Stat.Health,
                    Value = 800
                });
                character.Stat.Add(new CharacterStatModel
                {
                    Id    = character.Id,
                    Stat  = (byte)Stat.Shield,
                    Value = 450
                });
                character.Stat.Add(new CharacterStatModel
                {
                    Id    = character.Id,
                    Stat  = (byte)Stat.Dash,
                    Value = 200
                });
                character.Stat.Add(new CharacterStatModel
                {
                    Id    = character.Id,
                    Stat  = (byte)Stat.Level,
                    Value = 1
                });
                character.Stat.Add(new CharacterStatModel
                {
                    Id    = character.Id,
                    Stat  = (byte)Stat.StandState,
                    Value = 3
                });

                // TODO: actually error check this
                session.EnqueueEvent(new TaskEvent(DatabaseManager.Instance.CharacterDatabase.Save(c =>
                {
                    c.Character.Add(character);
                    foreach (Item item in items)
                    {
                        item.Save(c);
                    }
                }),
                                                   () =>
                {
                    session.Characters.Add(character);
                    session.EnqueueMessageEncrypted(new ServerCharacterCreate
                    {
                        CharacterId = character.Id,
                        WorldId     = character.WorldId,
                        Result      = CharacterModifyResult.CreateOk
                    });
                }));
            }
            catch
            {
                session.EnqueueMessageEncrypted(new ServerCharacterCreate
                {
                    Result = CharacterModifyResult.CreateFailed
                });

                throw;
            }

            CharacterCustomizationEntry GetCharacterCustomisation(Dictionary <uint, uint> customisations, uint race, uint sex, uint primaryLabel, uint primaryValue)
            {
                ImmutableList <CharacterCustomizationEntry> entries = AssetManager.Instance.GetPrimaryCharacterCustomisation(race, sex, primaryLabel, primaryValue);

                if (entries == null)
                {
                    return(null);
                }
                if (entries.Count == 1)
                {
                    return(entries[0]);
                }

                // customisation has multiple results, filter with secondary label and value
                uint secondaryLabel = entries.First(e => e.CharacterCustomizationLabelId01 != 0).CharacterCustomizationLabelId01;
                uint secondaryValue = customisations[secondaryLabel];

                CharacterCustomizationEntry entry = entries.SingleOrDefault(e => e.CharacterCustomizationLabelId01 == secondaryLabel && e.Value01 == secondaryValue);

                return(entry ?? entries.Single(e => e.CharacterCustomizationLabelId01 == 0 && e.Value01 == 0));
            }
        }
Ejemplo n.º 12
0
        public static void HandleCharacterList(WorldSession session, ClientCharacterList characterList)
        {
            session.EnqueueEvent(new TaskGenericEvent <List <CharacterModel> >(DatabaseManager.Instance.CharacterDatabase.GetCharacters(session.Account.Id),
                                                                               characters =>
            {
                byte maxCharacterLevelAchieved = 1;

                session.Characters.Clear();
                session.Characters.AddRange(characters);

                session.AccountCurrencyManager.SendCharacterListPacket();
                session.GenericUnlockManager.SendUnlockList();

                session.EnqueueMessageEncrypted(new ServerAccountEntitlements
                {
                    Entitlements = session.EntitlementManager.GetAccountEntitlements()
                                   .Select(e => new ServerAccountEntitlements.AccountEntitlementInfo
                    {
                        Entitlement = e.Type,
                        Count       = e.Amount
                    })
                                   .ToList()
                });
                session.EnqueueMessageEncrypted(new ServerAccountTier
                {
                    Tier = session.AccountTier
                });

                // 2 is just a fail safe for the minimum amount of character slots
                // this is set in the tbl files so a value should always exist
                uint characterSlots = (uint)(session.EntitlementManager.GetRewardProperty(RewardPropertyType.CharacterSlots).GetValue(0u) ?? 2u);
                uint characterCount = (uint)characters.Count(c => c.DeleteTime == null);

                var serverCharacterList = new ServerCharacterList
                {
                    RealmId = WorldServer.RealmId,
                    // no longer used as replaced by entitlements but retail server still used to send this
                    AdditionalCount = characterCount,
                    AdditionalAllowedCharCreations = (uint)Math.Max(0, (int)(characterSlots - characterCount))
                };

                foreach (CharacterModel character in characters.Where(c => c.DeleteTime == null))
                {
                    var listCharacter = new ServerCharacterList.Character
                    {
                        Id                = character.Id,
                        Name              = character.Name,
                        Sex               = (Sex)character.Sex,
                        Race              = (Race)character.Race,
                        Class             = (Class)character.Class,
                        Faction           = character.FactionId,
                        Level             = character.Level,
                        WorldId           = character.WorldId,
                        WorldZoneId       = character.WorldZoneId,
                        RealmId           = WorldServer.RealmId,
                        Path              = (byte)character.ActivePath,
                        LastLoggedOutDays = (float)DateTime.UtcNow.Subtract(character.LastOnline ?? DateTime.UtcNow).TotalDays * -1f
                    };

                    maxCharacterLevelAchieved = Math.Max(maxCharacterLevelAchieved, character.Level);

                    try
                    {
                        // create a temporary Inventory and CostumeManager to show equipped gear
                        var inventory      = new Inventory(null, character);
                        var costumeManager = new CostumeManager(null, session.Account, character);

                        CostumeEntity costume = null;
                        if (character.ActiveCostumeIndex >= 0)
                        {
                            costume = costumeManager.GetCostume((byte)character.ActiveCostumeIndex);
                        }

                        listCharacter.GearMask = costume?.Mask ?? 0xFFFFFFFF;

                        foreach (ItemVisual itemVisual in inventory.GetItemVisuals(costume))
                        {
                            listCharacter.Gear.Add(itemVisual);
                        }

                        foreach (CharacterAppearanceModel appearance in character.Appearance)
                        {
                            listCharacter.Appearance.Add(new ItemVisual
                            {
                                Slot      = (ItemSlot)appearance.Slot,
                                DisplayId = appearance.DisplayId
                            });
                        }

                        /*foreach (CharacterCustomisation customisation in character.CharacterCustomisation)
                         * {
                         *  listCharacter.Labels.Add(customisation.Label);
                         *  listCharacter.Values.Add(customisation.Value);
                         * }*/

                        foreach (CharacterBoneModel bone in character.Bone.OrderBy(bone => bone.BoneIndex))
                        {
                            listCharacter.Bones.Add(bone.Bone);
                        }

                        foreach (CharacterStatModel stat in character.Stat)
                        {
                            if ((Stat)stat.Stat == Stat.Level)
                            {
                                listCharacter.Level = (uint)stat.Value;
                                break;
                            }
                        }

                        serverCharacterList.Characters.Add(listCharacter);
                    }
                    catch (Exception ex)
                    {
                        log.Fatal(ex, $"An error has occured while loading character '{character.Name}'");
                        continue;
                    }
                }

                session.EnqueueMessageEncrypted(new ServerMaxCharacterLevelAchieved
                {
                    Level = maxCharacterLevelAchieved
                });

                session.EnqueueMessageEncrypted(serverCharacterList);
            }));
        }
Ejemplo n.º 13
0
        public static void HandleCharacterList(WorldSession session, ClientCharacterList characterList)
        {
            session.EnqueueEvent(new TaskGenericEvent <List <Character> >(CharacterDatabase.GetCharacters(session.Account.Id),
                                                                          characters =>
            {
                byte MaxCharacterLevelAchieved = 1;

                session.Characters.Clear();
                session.Characters.AddRange(characters);

                session.GenericUnlockManager.SendUnlockList();
                session.EnqueueMessageEncrypted(new ServerAccountEntitlements
                {
                    Entitlements =
                    {
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.BaseCharacterSlots,
                            Count       = 12
                        },
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.ExtraDecorSlots,
                            Count       = 2000
                        },
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.ChuaWarriorUnlock,
                            Count       = 1
                        },
                        new ServerAccountEntitlements.AccountEntitlementInfo
                        {
                            Entitlement = Entitlement.AurinEngineerUnlock,
                            Count       = 1
                        }
                    }
                });

                var serverCharacterList = new ServerCharacterList
                {
                    RealmId = WorldServer.RealmId
                };

                foreach (Character character in characters)
                {
                    var listCharacter = new ServerCharacterList.Character
                    {
                        Id          = character.Id,
                        Name        = character.Name,
                        Sex         = (Sex)character.Sex,
                        Race        = (Race)character.Race,
                        Class       = (Class)character.Class,
                        Faction     = character.FactionId,
                        Level       = character.Level,
                        WorldId     = character.WorldId,
                        WorldZoneId = character.WorldZoneId,
                        RealmId     = WorldServer.RealmId,
                        Path        = (byte)character.ActivePath
                    };

                    MaxCharacterLevelAchieved = (byte)Math.Max(MaxCharacterLevelAchieved, character.Level);

                    // create a temporary Inventory and CostumeManager to show equipped gear
                    var inventory      = new Inventory(null, character);
                    var costumeManager = new CostumeManager(null, session.Account, character);

                    CostumeEntity costume = null;
                    if (character.ActiveCostumeIndex >= 0)
                    {
                        costume = costumeManager.GetCostume((byte)character.ActiveCostumeIndex);
                    }

                    listCharacter.GearMask = costume?.Mask ?? 0xFFFFFFFF;

                    foreach (ItemVisual itemVisual in inventory.GetItemVisuals(costume))
                    {
                        listCharacter.Gear.Add(itemVisual);
                    }

                    foreach (CharacterAppearance appearance in character.CharacterAppearance)
                    {
                        listCharacter.Appearance.Add(new ItemVisual
                        {
                            Slot      = (ItemSlot)appearance.Slot,
                            DisplayId = appearance.DisplayId
                        });
                    }

                    /*foreach (CharacterCustomisation customisation in character.CharacterCustomisation)
                     * {
                     *  listCharacter.Labels.Add(customisation.Label);
                     *  listCharacter.Values.Add(customisation.Value);
                     * }*/

                    foreach (CharacterBone bone in character.CharacterBone.OrderBy(bone => bone.BoneIndex))
                    {
                        listCharacter.Bones.Add(bone.Bone);
                    }

                    foreach (CharacterStat stat in character.CharacterStat)
                    {
                        if ((Stat)stat.Stat == Stat.Level)
                        {
                            listCharacter.Level = (uint)stat.Value;
                            break;
                        }
                    }

                    serverCharacterList.Characters.Add(listCharacter);
                }

                session.EnqueueMessageEncrypted(new ServerMaxCharacterLevelAchieved
                {
                    Level = MaxCharacterLevelAchieved
                });

                session.EnqueueMessageEncrypted(serverCharacterList);
            }));
        }
Ejemplo n.º 14
0
        public static void HandleCharacterDelete(WorldSession session, ClientCharacterDelete characterDelete)
        {
            Character characterToDelete = session.Characters.FirstOrDefault(c => c.Id == characterDelete.CharacterId);

            CharacterModifyResult GetResult()
            {
                if (characterToDelete == null)
                {
                    return(CharacterModifyResult.DeleteFailed);
                }

                // TODO: Not sure if this is definitely the case, but put it in for good measure
                if (characterToDelete.CharacterMail.Count > 0)
                {
                    foreach (CharacterMail characterMail in characterToDelete.CharacterMail)
                    {
                        if (characterMail.CharacterMailAttachment.Count > 0)
                        {
                            return(CharacterModifyResult.DeleteFailed);
                        }
                    }
                }

                // TODO: Ensure character is not a guild master

                return(CharacterModifyResult.DeleteOk);
            }

            CharacterModifyResult result = GetResult();

            if (result != CharacterModifyResult.DeleteOk)
            {
                session.EnqueueMessageEncrypted(new ServerCharacterDeleteResult
                {
                    Result = result
                });
                return;
            }

            session.CanProcessPackets = false;

            void Save(CharacterContextExtended context)
            {
                var model = new Character
                {
                    Id = characterToDelete.Id
                };

                EntityEntry <Character> entity = context.Attach(model);

                model.DeleteTime = DateTime.UtcNow;
                entity.Property(e => e.DeleteTime).IsModified = true;

                model.OriginalName = characterToDelete.Name;
                entity.Property(e => e.OriginalName).IsModified = true;

                model.Name = null;
                entity.Property(e => e.Name).IsModified = true;
            }

            session.EnqueueEvent(new TaskEvent(CharacterDatabase.Save(Save),
                                               () =>
            {
                session.CanProcessPackets = true;

                CharacterManager.Instance.DeleteCharacter(characterToDelete.Id);

                session.EnqueueMessageEncrypted(new ServerCharacterDeleteResult
                {
                    Result = result
                });
            }));
        }
Ejemplo n.º 15
0
        public static void HandleCharacterList(WorldSession session, ClientCharacterList characterList)
        {
            session.EnqueueEvent(new TaskGenericEvent <List <CharacterModel> >(DatabaseManager.Instance.CharacterDatabase.GetCharacters(session.Account.Id),
                                                                               characters =>
            {
                byte maxCharacterLevelAchieved = 1;

                session.Characters.Clear();
                session.Characters.AddRange(characters);

                session.AccountCurrencyManager.SendCharacterListPacket();
                session.GenericUnlockManager.SendUnlockList();

                session.EnqueueMessageEncrypted(new ServerAccountEntitlements
                {
                    Entitlements = session.EntitlementManager.GetAccountEntitlements()
                                   .Select(e => new ServerAccountEntitlements.AccountEntitlementInfo
                    {
                        Entitlement = e.Type,
                        Count       = e.Amount
                    })
                                   .ToList()
                });

                var serverCharacterList = new ServerCharacterList
                {
                    RealmId = WorldServer.RealmId
                };

                foreach (CharacterModel character in characters)
                {
                    if (character.DeleteTime != null)
                    {
                        continue;
                    }

                    var listCharacter = new ServerCharacterList.Character
                    {
                        Id          = character.Id,
                        Name        = character.Name,
                        Sex         = (Sex)character.Sex,
                        Race        = (Race)character.Race,
                        Class       = (Class)character.Class,
                        Faction     = character.FactionId,
                        Level       = character.Level,
                        WorldId     = character.WorldId,
                        WorldZoneId = character.WorldZoneId,
                        RealmId     = WorldServer.RealmId,
                        Path        = (byte)character.ActivePath
                    };

                    maxCharacterLevelAchieved = (byte)Math.Max(maxCharacterLevelAchieved, character.Level);

                    // create a temporary Inventory and CostumeManager to show equipped gear
                    var inventory      = new Inventory(null, character);
                    var costumeManager = new CostumeManager(null, session.Account, character);

                    CostumeEntity costume = null;
                    if (character.ActiveCostumeIndex >= 0)
                    {
                        costume = costumeManager.GetCostume((byte)character.ActiveCostumeIndex);
                    }

                    listCharacter.GearMask = costume?.Mask ?? 0xFFFFFFFF;

                    foreach (ItemVisual itemVisual in inventory.GetItemVisuals(costume))
                    {
                        listCharacter.Gear.Add(itemVisual);
                    }

                    foreach (CharacterAppearanceModel appearance in character.Appearance)
                    {
                        listCharacter.Appearance.Add(new ItemVisual
                        {
                            Slot      = (ItemSlot)appearance.Slot,
                            DisplayId = appearance.DisplayId
                        });
                    }

                    /*foreach (CharacterCustomisation customisation in character.CharacterCustomisation)
                     * {
                     *  listCharacter.Labels.Add(customisation.Label);
                     *  listCharacter.Values.Add(customisation.Value);
                     * }*/

                    foreach (CharacterBoneModel bone in character.Bone.OrderBy(bone => bone.BoneIndex))
                    {
                        listCharacter.Bones.Add(bone.Bone);
                    }

                    foreach (CharacterStatModel stat in character.Stat)
                    {
                        if ((Stat)stat.Stat == Stat.Level)
                        {
                            listCharacter.Level = (uint)stat.Value;
                            break;
                        }
                    }

                    serverCharacterList.Characters.Add(listCharacter);
                }

                session.EnqueueMessageEncrypted(new ServerMaxCharacterLevelAchieved
                {
                    Level = maxCharacterLevelAchieved
                });

                session.EnqueueMessageEncrypted(serverCharacterList);
            }));
        }