public static SMSG_UPDATE_OBJECT_VANILLA CreateUnit(Creature unit) { var update = new SMSG_UPDATE_OBJECT_VANILLA(); var entity = new UnitEntity(unit, ClientBuild.Vanilla); update.Writer .WriteUInt32(1) // blocks.Count .WriteUInt8(0) // hasTransport .WriteUInt8((byte)ObjectUpdateType.UPDATETYPE_CREATE_OBJECT) .WriteBytes(unit.ID.ToPackedUInt64()) .WriteUInt8((byte)TypeId.TypeidUnit) .WriteUInt8((byte)(ObjectUpdateFlag_VANILLA.All | ObjectUpdateFlag_VANILLA.HasPosition | ObjectUpdateFlag_VANILLA.Living)) .WriteUInt32((uint)MovementFlags.None) .WriteUInt32((uint)Environment.TickCount) .WriteMap(unit.Position) .WriteFloat(0) // ?? .WriteFloat(2.5f) // WalkSpeed .WriteFloat(7f) // RunSpeed .WriteFloat(4.5f) // Backwards WalkSpeed .WriteFloat(4.72f) // SwimSpeed .WriteFloat(2.5f) // Backwards SwimSpeed .WriteFloat(3.14f) // TurnSpeed .WriteInt32(0); // ?? entity.WriteUpdateFields(update.Writer); return(update); }
// UNUSED FOR NOW public static SMSG_UPDATE_OBJECT_VANILLA UpdateValues(PlayerEntity player) { var update = new SMSG_UPDATE_OBJECT_VANILLA(); update.Writer .WriteUInt32(1) // blocks.Count .WriteUInt8(0) // hasTransport .WriteUInt8((byte)ObjectUpdateType.UPDATETYPE_VALUES) .WriteBytes(player.CharacterId.ToPackedUInt64()); // CharacterId is NOT set player.WriteUpdateFields(update.Writer); return(update); }
public async Task SpawnCreature(Creature creature) { this.Creatures.Add(creature); foreach (var connection in this.Connections) { var character = this.CharacterService.GetCharacter(connection.CharacterId); if (character is null) { continue; } if (!IsInRange(character, creature)) { continue; } await connection.SendPacket(SMSG_UPDATE_OBJECT_VANILLA.CreateUnit(creature)); } }
public static async Task OnMessageChat(PacketHandlerContext c) { var request = new CMSG_MESSAGECHAT(c.Packet); // debugging stuff :D if (request.Message == ".update") { if (c.IsVanilla()) { await c.Client.SendPacket(SMSG_UPDATE_OBJECT_VANILLA.UpdateValues(c.World.Creatures)); } return; } if (request.Message.StartsWith(".spawn")) { var spawnId = int.Parse(request.Message.Split(" ")[1]); var creature = new Creature { Model = spawnId, Position = c.GetCharacter().Position.Copy() }; await c.World.SpawnCreature(creature); } }
public static SMSG_UPDATE_OBJECT_VANILLA UpdateValues(List <Creature> units) { var update = new SMSG_UPDATE_OBJECT_VANILLA(); update.Writer .WriteUInt32((uint)units.Count) // blocks.Count .WriteUInt8(0) // hasTransport ; foreach (var unit in units) { var entity = new UnitEntity(unit, ClientBuild.Vanilla); update.Writer .WriteUInt8((byte)ObjectUpdateType.UPDATETYPE_VALUES) .WriteBytes(unit.ID.ToPackedUInt64()); entity.WriteUpdateFields(update.Writer); } return(update); }
public static async Task OnPlayerLogin(PacketHandlerContext c) { var request = new CMSG_PLAYER_LOGIN(c.Packet); var character = c.GetCharacter(request.CharacterID); var account = c.AccountService.GetAccount(c.Client.Identifier); // Login with a deleted character or a character from another account. // TODO: Split for different log messages. if (character is null || !account.Characters.Contains(character.Id)) { c.Client.Log( $"{account.Identifier} tried to login with a deleted character or a character from another account.", LogLevel.Warning); return; } c.Client.Log($"Player logged in with char {character.Name}"); if (c.IsTBC()) { await c.SendPacket <MSG_SET_DUNGEON_DIFFICULTY>(); } await c.Client.SendPacket(new SMSG_LOGIN_VERIFY_WORLD(character)); await c.SendPacket <SMSG_ACCOUNT_DATA_TIMES>(); if (c.IsTBC()) { await c.SendPacket <SMSG_FEATURE_SYSTEM_STATUS>(); } await c.Client.SendPacket(new SMSG_EXPECTED_SPAM_RECORDS(Enumerable.Empty <string>())); if (c.IsVanilla()) { await c.Client.SendPacket(new SMSG_MESSAGECHAT(character.Id, MessageOfTheDay)); } else if (c.IsTBC()) { await c.Client.SendPacket(new SMSG_MOTD(MessageOfTheDay)); } // await args.Client.SendPacket(new SMSG_NAME_QUERY_RESPONSE(character, args.Client.Build)); // if (GUILD) -> SMSG_GUILD_EVENT if (character.Stats.Life == 0) { await c.SendPacket <SMSG_CORPSE_RECLAIM_DELAY>(); } await c.SendPacket <SMSG_SET_REST_START>(); await c.Client.SendPacket(new SMSG_BINDPOINTUPDATE(character)); await c.SendPacket <SMSG_TUTORIAL_FLAGS>(); if (c.IsTBC()) { await c.SendPacket <SMSG_INSTANCE_DIFFICULTY>(); } await c.Client.SendPacket(new SMSG_INITIAL_SPELLS(character.Spells)); // SMSG_SEND_UNLEARN_SPELLS await c.Client.SendPacket(new SMSG_ACTION_BUTTONS(character.ActionBar)); await c.Client.SendPacket(new SMSG_INITIALIZE_FACTIONS(ClientBuild.Vanilla)); // BUG?? await c.SendPacket <SMSG_LOGIN_SETTIMESPEED>(); // await args.Client.SendPacket(new SMSG_TRIGGER_CINEMATIC(CinematicID.NightElf)); c.Client.CharacterId = character.Id; await c.Client.SendPacket(SMSG_UPDATE_OBJECT.CreateOwnPlayerObject(character, c.Client.Build, out var player)); c.Client.Player = player; // TODO: Implement for TBC if (c.IsVanilla()) { // Initially spawn all creatures foreach (var unit in c.World.Creatures) { // TODO: Add range check await c.Client.SendPacket(SMSG_UPDATE_OBJECT_VANILLA.CreateUnit(unit)); } } await c.World.SpawnPlayer(character, c.Client.Build); // if (GROUP) -> SMSG_GROUP_LIST // if Vanilla // SMSG_FRIEND_LIST // SMSG_IGNORE_LIST // if TBC // SMSG_CONTACT_LIST if (c.IsTBC()) { await c.SendPacket <SMSG_TIME_SYNC_REQ>(); } // SMSG_ITEM_ENCHANT_TIME_UPDATE // SMSG_ITEM_TIME_UPDATE // SMSG_FRIEND_STATUS }