public static void EnterLobby(RemotePlayer player) { lock (_enterLock) { bool added = false; List <RemotePlayer> players; lock (Players) { players = Players.Values.ToList(); if (!Players.ContainsKey(player.ID)) { added = true; Players.Add(player.ID, player); } } if (added) { player.PlayerState = PlayerState.IN_LOBBY; var packet = new S2C_LobbyPlayerJoined(player.GetDisplay()); foreach (var p in players) { p.Connection.Send(packet); } SendInitialLobbyData(player); } } }
public static void LeaveLobby(RemotePlayer player) { lock (_enterLock) { bool removed = false; lock (Players) { removed = Players.Remove(player.ID); //if (!removed) // return; } if (removed) { player.ClearAllInvites(); } var packet = new S2C_LobbyPlayerLeft(player.GetDisplay()); var players = GetPlayerList(); foreach (var p in players) { p.Connection.Send(packet); } } }
public static void Bind() { Net.Init(); NetworkComms.AppendGlobalConnectionEstablishHandler((connection) => { // todo: Automatically disconnect after 60 seconds without a handshake }); NetworkComms.AppendGlobalConnectionCloseHandler((connection) => { DisconnectPlayer(connection.GetID()); }); Net.On <C2S_Handshake>((header, connection, obj) => { var response = new S2C_HandshakeResponse(obj.Version == VERSION, IsNicknameValid(obj.Nickname), "OK", null); if (IsValidPlayer(connection.GetID())) { //handshake for second time.. let's disconnect DisconnectPlayer(connection.GetID()); } if (!response.OK) { response.Message = $"Error:\n Version: {response.VersionOK}\n Nickname: {response.NicknameOK}"; if (!response.NicknameOK) { response.Message += "\n Nickname length must be within 3-16 characters and MUST be unique."; } } else { // OK! var player = new RemotePlayer() { Connection = connection, Nickname = obj.Nickname, PlayerState = PlayerState.HANDSHAKE_OK }; response.LocalPlayer = player.GetDisplay(); AddPlayer(player); } connection.Send(response); }); Net.On <C2S_JoinLobby>((header, connection, obj) => { RemotePlayer player; if (IsValidPlayer(connection.GetID(), out player)) { LobbyServer.EnterLobby(player); } }); Net.On <C2S_SendPlayerInvite>((header, connection, obj) => { RemotePlayer source, destination; if (IsValidPlayer(connection.GetID(), out source, PlayerState.IN_LOBBY) && IsValidPlayer(obj.Destination, out destination, PlayerState.IN_LOBBY)) { source.SendInvite(destination); } }); Net.On <C2S_RevokeSentPlayerInvite>((header, connection, obj) => { RemotePlayer source, destination; if (IsValidPlayer(connection.GetID(), out source, PlayerState.IN_LOBBY) && IsValidPlayer(obj.Destination, out destination, PlayerState.IN_LOBBY)) { source.RevokeSentInvite(destination); } }); Net.On <C2S_AcceptIncomingPlayerInvite>((header, connection, obj) => { RemotePlayer source, destination; if (IsValidPlayer(obj.Source, out source, PlayerState.IN_LOBBY) && IsValidPlayer(connection.GetID(), out destination, PlayerState.IN_LOBBY)) { if (source.HasSentInviteTo(destination)) { //We have a pair :) LobbyServer.LeaveLobby(source); LobbyServer.LeaveLobby(destination); GameServer.InitNewGame(source, destination); } } }); Net.On <C2S_GameReady>((header, connection, obj) => { RemotePlayer player; if (IsValidPlayer(connection.GetID(), out player, PlayerState.IN_GAME)) { var p = player.Game.GetPlayer(player); player.Game.OnPlayerReady(p); } }); Net.On <C2S_FireAt>((header, connection, obj) => { RemotePlayer player; if (IsValidPlayer(connection.GetID(), out player, PlayerState.IN_GAME)) { var p = player.Game.GetPlayer(player); p.FireAtEnemy(obj.X, obj.Y); } }); }