public override void BanListListDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 1) { int startOffset = 0; if (request.Packet.Words.Count >= 2) { if (int.TryParse(request.Packet.Words[1], out startOffset) == false) { startOffset = 0; } } // We've just started requesting the banlist, clear it. if (startOffset == 0) { this.State.Bans.Clear(); } List<BanModel> banList = SecondFrostbiteBanList.Parse(response.Packet.Words.GetRange(1, response.Packet.Words.Count - 1)); if (banList.Count > 0) { foreach (BanModel ban in banList) { if (ban.Scope.Times.Count > 0 && ban.Scope.Players.Count > 0) { var closureBan = ban; var key = String.Format("{0}/{1}", ban.Scope.Times.First().Context, ban.Scope.Players.First().Uid ?? ban.Scope.Players.First().Name ?? ban.Scope.Players.First().Ip); this.State.Bans.AddOrUpdate(key, id => closureBan, (id, model) => closureBan); } } this.Send(this.CreatePacket("banList.list {0}", startOffset + 100)); } else { IProtocolStateDifference difference = new ProtocolStateDifference() { Override = true, Modified = { Bans = this.State.Bans } }; this.ApplyProtocolStateDifference(difference); // We have recieved the whole banlist in 100 ban increments.. throw event. this.OnProtocolEvent( ProtocolEventType.ProtocolBanlistUpdated, difference ); } } }
public override void MapListListDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 1) { ConcurrentDictionary<String, MapModel> modified = new ConcurrentDictionary<String, MapModel>(); List<MapModel> maps = SecondFrostbiteMapList.Parse(response.Packet.Words.GetRange(1, response.Packet.Words.Count - 1)); foreach (MapModel map in maps) { var closureMap = map; MapModel mapInfo = this.State.MapPool.Values.FirstOrDefault(m => String.Compare(m.Name, closureMap.Name, StringComparison.OrdinalIgnoreCase) == 0 && String.Compare(m.GameMode.Name, closureMap.GameMode.Name, StringComparison.OrdinalIgnoreCase) == 0); if (mapInfo != null) { closureMap.FriendlyName = mapInfo.FriendlyName; closureMap.GameMode = mapInfo.GameMode; } modified.AddOrUpdate(String.Format("{0}/{1}", closureMap.GameMode.Name, closureMap.Name), id => closureMap, (id, model) => closureMap); } IProtocolStateDifference difference = new ProtocolStateDifference() { Override = true, Modified = { Maps = modified } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolMaplistUpdated, difference ); } }
public void ServerOnLoadingLevelDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 4) { int currentRound = 0, totalRounds = 0; if (int.TryParse(request.Packet.Words[2], out currentRound) == true && int.TryParse(request.Packet.Words[3], out totalRounds) == true) { this.State.Settings.Current.RoundIndex = currentRound; this.State.Settings.Maximum.RoundIndex = totalRounds; // Maps are the same, only a round change if (String.Compare(this.State.Settings.Current.MapNameText, request.Packet.Words[1], StringComparison.OrdinalIgnoreCase) == 0) { IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolRoundChanged, difference ); } else { MapModel selectedMap = this.State.MapPool.Select(m => m.Value).FirstOrDefault(x => String.Compare(x.Name, request.Packet.Words[1], StringComparison.OrdinalIgnoreCase) == 0); if (selectedMap != null) { this.State.Settings.Current.GameModeNameText = selectedMap.GameMode.Name; this.State.Settings.Current.FriendlyGameModeNameText = selectedMap.GameMode.FriendlyName; this.State.Settings.Current.FriendlyMapNameText = selectedMap.FriendlyName; } this.State.Settings.Current.MapNameText = request.Packet.Words[1]; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolMapChanged, difference ); } } } }
public virtual IProtocolSetupResult Setup(IProtocolSetup setup) { this.Options = setup; this.Client.Setup(ClientSetup.FromProtocolSetup(setup)); // Handle client events, most of which are proxies to events we fire. this.Client.PacketReceived += (sender, wrapper) => { this.PacketDispatcher.Dispatch(wrapper); // Alert the deferrer that we have a new packet that's been dispatched this.WaitingActions.Mark(wrapper.Packet); this.OnClientEvent(ClientEventType.ClientPacketReceived, new ClientEventData() { Packets = new List<IPacket>() { wrapper.Packet } }); }; this.Client.ConnectionStateChanged += (sender, state) => { this.OnClientEvent(ClientEventType.ClientConnectionStateChange); this.State.Settings.Current.ConnectionState = state; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent(ProtocolEventType.ProtocolSettingsUpdated, difference); if (state == ConnectionState.ConnectionReady) { this.Login(this.Options.Password); } }; this.Client.PacketSent += (sender, wrapper) => this.OnClientEvent(ClientEventType.ClientPacketSent, new ClientEventData() { Packets = new List<IPacket>() { wrapper.Packet } }); this.Client.SocketException += (sender, se) => this.OnClientEvent(ClientEventType.ClientSocketException, new ClientEventData() { Exceptions = new List<String>() { se.ToString() } }); this.Client.ConnectionFailure += (sender, exception) => this.OnClientEvent(ClientEventType.ClientConnectionFailure, new ClientEventData() { Exceptions = new List<String>() { exception.ToString() } }); return new ProtocolSetupResult(); }
public void BanListRemoveDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 1) { BanModel ban = FrostbiteBan.ParseBanRemove(request.Packet.Words.GetRange(1, request.Packet.Words.Count - 1)); IProtocolStateDifference difference = new ProtocolStateDifference() { Removed = { Bans = new ConcurrentDictionary<String, BanModel>(new Dictionary<String, BanModel>() { { String.Format("{0}/{1}", ban.Scope.Times.First().Context, ban.Scope.Players.First().Uid ?? ban.Scope.Players.First().Name ?? ban.Scope.Players.First().Ip), ban } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerUnbanned, difference, new ProtocolEventData() { Bans = new List<BanModel>() { ban } } ); } }
public virtual void PlayerOnKillDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 11) { bool headshot = false; if (bool.TryParse(request.Packet.Words[4], out headshot) == true) { var killer = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[1]); var victim = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[2]); IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { killer != null ? killer.Uid : "", killer }, { victim != null ? victim.Uid : "", victim } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerKill, difference, new ProtocolEventData() { Kills = new List<KillModel>() { new KillModel() { Scope = { Players = new List<PlayerModel>() { victim }, Items = new List<ItemModel>() { new ItemModel() { Name = request.Packet.Words[3] } }, Points = new List<Point3DModel>() { new Point3DModel(request.Packet.Words[8], request.Packet.Words[10], request.Packet.Words[9]) }, HumanHitLocations = new List<HumanHitLocation>() { headshot == true ? FrostbiteGame.Headshot : FrostbiteGame.Bodyshot } }, Now = { Players = new List<PlayerModel>() { killer }, Points = new List<Point3DModel>() { new Point3DModel(request.Packet.Words[5], request.Packet.Words[7], request.Packet.Words[6]) } } } } } ); } } }
public void ServerInfoDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (response != null) { IProtocolStateDifference difference = null; FrostbiteServerInfo info = new FrostbiteServerInfo().Parse(response.Packet.Words.GetRange(1, response.Packet.Words.Count - 1), this.ServerInfoParameters); this.UpdateSettingsMap(info.Map, info.GameMode); this.UpdateSettingsRound(info.CurrentRound, info.TotalRounds); this.State.Settings.Current.ServerNameText = info.ServerName; // this.State.Variables.ConnectionState = ConnectionState.Connected; String b = info.ConnectionState; this.State.Settings.Current.PlayerCount = info.PlayerCount; this.State.Settings.Maximum.PlayerCount = info.MaxPlayerCount; //this.State.Settings.RankedEnabled = info.Ranked; this.State.Settings.Current.AntiCheatEnabled = info.PunkBuster; this.State.Settings.Current.PasswordProtectionEnabled = info.Passworded; this.State.Settings.Current.UpTimeMilliseconds = info.ServerUptime * 1000; this.State.Settings.Current.RoundTimeMilliseconds = info.RoundTime * 1000; this.State.Settings.Current.ModNameText = info.GameMod.ToString(); if (this.State.MapPool.Count == 0) { ProtocolConfigModel config = null; if (info.GameMod == GameMods.None) { config = ProtocolConfigLoader.Load<ProtocolConfigModel>(this.Options.ConfigDirectory, this.ProtocolType); } else { config = ProtocolConfigLoader.Load<ProtocolConfigModel>(this.Options.ConfigDirectory, new ProtocolType(this.ProtocolType) { Type = String.Format("{0}_{1}", this.ProtocolType, info.GameMod) }); } if (config != null) { config.Parse(this); } difference = new ProtocolStateDifference() { Override = true, Modified = this.State }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent(ProtocolEventType.ProtocolConfigExecuted, difference); } difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolSettingsUpdated, difference, new ProtocolEventData() { Settings = new List<Settings>() { this.State.Settings } } ); } }
public virtual void PlayerOnAuthenticatedDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 3) { PlayerModel statePlayer = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[1]); if (statePlayer != null) { statePlayer.Uid = request.Packet.Words[2]; } else { statePlayer = new PlayerModel() { Name = request.Packet.Words[1], Uid = request.Packet.Words[2] }; } IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { statePlayer.Uid, statePlayer } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerJoin, difference, new ProtocolEventData() { Players = new List<PlayerModel>() { statePlayer } } ); } }
/// <summary> /// Update the current map name/gamemode, populating other settings and firing map change events as required. /// </summary> /// <param name="name">The name of the map to update with</param> /// <param name="gameModeName">The game mdoe of the map being played</param> protected void UpdateSettingsMap(String name, String gameModeName) { var modified = this.State.Settings.Current.MapNameText != name || this.State.Settings.Current.GameModeNameText != gameModeName; if (modified == true) { MapModel oldMap = this.State.MapPool.Select(m => m.Value).FirstOrDefault(map => String.Compare(map.Name, this.State.Settings.Current.MapNameText, StringComparison.OrdinalIgnoreCase) == 0 && String.Compare(map.GameMode.Name, this.State.Settings.Current.GameModeNameText, StringComparison.OrdinalIgnoreCase) == 0); this.State.Settings.Current.MapNameText = name; this.State.Settings.Current.GameModeNameText = gameModeName; MapModel currentMap = this.State.MapPool.Select(m => m.Value).FirstOrDefault(map => String.Compare(map.Name, this.State.Settings.Current.MapNameText, StringComparison.OrdinalIgnoreCase) == 0 && String.Compare(map.GameMode.Name, this.State.Settings.Current.GameModeNameText, StringComparison.OrdinalIgnoreCase) == 0); if (currentMap != null) { this.State.Settings.Current.FriendlyGameModeNameText = currentMap.GameMode.FriendlyName; this.State.Settings.Current.FriendlyMapNameText = currentMap.FriendlyName; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolMapChanged, difference, new ProtocolEventData() { Maps = new List<MapModel>() { currentMap } }, new ProtocolEventData() { Maps = new List<MapModel>() { oldMap } } ); } } }
/// <summary> /// Updates the current and total rounds, firing an events if they have changed. /// </summary> /// <param name="currentRound">The current round index being played</param> /// <param name="totalRounds">The total number of rounds to be played</param> protected void UpdateSettingsRound(int currentRound, int totalRounds) { var modified = this.State.Settings.Current.RoundIndex != currentRound; this.State.Settings.Maximum.RoundIndex = totalRounds; if (modified == true) { this.State.Settings.Current.RoundIndex = currentRound; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Settings = this.State.Settings } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolRoundChanged, difference ); } }
public void PlayerOnTeamChangeDispatchHandler(IPacketWrapper request, IPacketWrapper response) { PlayerModel player = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[1]); int teamId = 0, squadId = 0; if (player != null && int.TryParse(request.Packet.Words[2], out teamId) == true && int.TryParse(request.Packet.Words[3], out squadId) == true) { player.ModifyGroup(new GroupModel() { Type = GroupModel.Team, Uid = teamId.ToString(CultureInfo.InvariantCulture) }); player.ModifyGroup(new GroupModel() { Type = GroupModel.Squad, Uid = squadId.ToString(CultureInfo.InvariantCulture) }); IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { player.Uid, player } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerMoved, difference, new ProtocolEventData() { Players = new List<PlayerModel>() { player } } ); } }
public void PlayerOnKickedDispatchHandler(IPacketWrapper request, IPacketWrapper response) { PlayerModel player = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[1]); if (player != null) { // Note that this is removed when the player.OnLeave event is fired. //this.State.PlayerList.RemoveAll(x => x.Name == request.Packet.Words[1]); IProtocolStateDifference difference = new ProtocolStateDifference() { Removed = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { player.Uid, player } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerKicked, difference, new ProtocolEventData() { Kicks = new List<KickModel>() { new KickModel() { Now = { Players = new List<PlayerModel>() { player }, Content = new List<String>() { request.Packet.Words[2] } } } } } ); } }
public void PlayerOnSpawnDispatchHandler(IPacketWrapper request, IPacketWrapper response) { SpawnModel spawn = FrostbiteSpawn.Parse(request.Packet.Words.GetRange(1, request.Packet.Words.Count - 1)); PlayerModel player = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == spawn.Player.Name); if (player != null) { player.Role = spawn.Role; player.Inventory = spawn.Inventory; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { player.Uid, player } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerSpawn, difference, new ProtocolEventData() { Spawns = new List<SpawnModel>() { spawn } } ); } }
public override void PlayerOnJoinDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 2) { PlayerModel player = new PlayerModel() { Name = request.Packet.Words[1], Uid = request.Packet.Words[2] }; IProtocolStateDifference difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { player.Uid, player } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerJoin, difference, new ProtocolEventData() { Players = new List<PlayerModel>() { player } } ); } }
protected virtual void AdminListPlayersFinalize(List<PlayerModel> players) { var modified = new ConcurrentDictionary<String, PlayerModel>(); // 2. Add or update any new players foreach (PlayerModel player in players) { PlayerModel statePlayer; this.State.Players.TryGetValue(player.Uid, out statePlayer); player.Ping = player.Ping > 1000 ? 0 : player.Ping; if (statePlayer != null) { // Already exists, update with any new information we have. statePlayer.Kills = player.Kills; statePlayer.Score = player.Score; statePlayer.Deaths = player.Deaths; statePlayer.ClanTag = player.ClanTag; statePlayer.Ping = player.Ping; statePlayer.Uid = player.Uid; statePlayer.ModifyGroup(player.Groups.FirstOrDefault(group => group.Type == GroupModel.Team)); statePlayer.ModifyGroup(player.Groups.FirstOrDefault(group => group.Type == GroupModel.Squad)); modified.AddOrUpdate(player.Uid, id => statePlayer, (id, model) => statePlayer); } else { modified.TryAdd(player.Uid, player); } } IProtocolStateDifference difference = new ProtocolStateDifference() { Override = true, Removed = { Players = new ConcurrentDictionary<String, PlayerModel>(this.State.Players.Where(existing => players.Select(current => current.Uid).Contains(existing.Key) == false).ToDictionary(item => item.Key, item => item.Value)) }, Modified = { Players = modified } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent(ProtocolEventType.ProtocolPlayerlistUpdated, difference, new ProtocolEventData() { Players = new List<PlayerModel>(this.State.Players.Values) }); }
/// <summary> /// Handles the player.onKill event sent from the server. /// This method holds for Battlefield 3/4, but may need an override in bfbc2. /// </summary> public override void PlayerOnKillDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 5) { bool headshot = false; if (bool.TryParse(request.Packet.Words[4], out headshot) == true) { ItemModel item = this.State.Items.Select(i => i.Value).FirstOrDefault(i => i.Name == Regex.Replace(request.Packet.Words[3], @"[^\w\/_-]+", "")) ?? new ItemModel() { Name = request.Packet.Words[3] }; var killer = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[1]); var victim = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == request.Packet.Words[2]); if (killer != null && victim != null) { // Assign the item to the player, overwriting everything else attached to this killer. killer.Inventory.Now.Items.Clear(); killer.Inventory.Now.Items.Add(item); victim.Deaths++; // If this wasn't an inside job. if (killer.Uid != victim.Uid) { killer.Kills++; } var difference = new ProtocolStateDifference() { Modified = { Players = new ConcurrentDictionary<String, PlayerModel>() } }; difference.Modified.Players.AddOrUpdate(killer.Uid, id => killer, (id, model) => killer); difference.Modified.Players.AddOrUpdate(victim.Uid, id => victim, (id, model) => victim); this.ApplyProtocolStateDifference(difference); // We've updated the state, now fetch the players from the state with all of the statistics information attached. PlayerModel stateKiller = null; PlayerModel stateVictim = null; this.State.Players.TryGetValue(killer.Uid, out stateKiller); this.State.Players.TryGetValue(victim.Uid, out stateVictim); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerKill, difference, new ProtocolEventData() { Kills = new List<KillModel>() { new KillModel() { Scope = { Players = new List<PlayerModel>() { stateVictim }, Items = new List<ItemModel>() { item }, HumanHitLocations = new List<HumanHitLocation>() { headshot == true ? FrostbiteGame.Headshot : FrostbiteGame.Bodyshot } }, Now = { Players = new List<PlayerModel>() { stateKiller } } } } } ); } } } }
public void PlayerOnLeaveDispatchHandler(IPacketWrapper request, IPacketWrapper response) { if (request.Packet.Words.Count >= 2) { //request.Packet.Words.RemoveAt(1); PlayerModel player = FrostbitePlayers.Parse(request.Packet.Words.GetRange(2, request.Packet.Words.Count - 2)).FirstOrDefault(); if (player != null) { PlayerModel statePlayer = this.State.Players.Select(p => p.Value).FirstOrDefault(p => p.Name == player.Name); if (statePlayer != null) { // Already exists, update with any new information we have. // Note: We must keep the same Player object which is why we update and swap // instead of just assigning. statePlayer.Kills = player.Kills; statePlayer.Deaths = player.Deaths; statePlayer.ClanTag = player.ClanTag; statePlayer.Ping = player.Ping > 1000 ? 0 : player.Ping; statePlayer.Uid = player.Uid; statePlayer.ModifyGroup(player.Groups.FirstOrDefault(group => group.Type == GroupModel.Team)); statePlayer.ModifyGroup(player.Groups.FirstOrDefault(group => group.Type == GroupModel.Squad)); player = statePlayer; } IProtocolStateDifference difference = new ProtocolStateDifference() { Removed = { Players = new ConcurrentDictionary<String, PlayerModel>(new Dictionary<String, PlayerModel>() { { player.Uid, player } }) } }; this.ApplyProtocolStateDifference(difference); this.OnProtocolEvent( ProtocolEventType.ProtocolPlayerLeave, difference, new ProtocolEventData() { Players = new List<PlayerModel>() { player } } ); } } }