/// <summary> /// Listens to all data received from the network interface /// </summary> public override void ListenIncoming() { // we loop on all LocalPlayers to gather network data foreach (LiveIdentifiedPlayer identifiedPlayer in LocalPlayers) { var gamer = (LocalNetworkGamer)identifiedPlayer.LiveGamer; while (gamer.IsDataAvailable) { NetworkGamer sender; gamer.ReceiveData(_packetReader, out sender); byte message = _packetReader.ReadByte(); // If the message is to execute commands on server, we execute them and ask all clients to execute them with the server computed value if (message == Constants.ExecuteCommandOnServerDataExchanged) { if (!gamer.IsHost) { throw new CoreException("Gamer isn't host"); } ushort commandId = _packetReader.ReadUInt16(); Command command = Commands[commandId]; if (command.NetworkValueType == typeof(bool)) { command.NetworkValue = _packetReader.ReadBoolean(); } else if (command.NetworkValueType == typeof(byte)) { command.NetworkValue = _packetReader.ReadByte(); } else if (command.NetworkValueType == typeof(byte[])) { int tempNumberOfBytes = _packetReader.ReadInt32(); command.NetworkValue = _packetReader.ReadBytes(tempNumberOfBytes); } else if (command.NetworkValueType == typeof(char)) { command.NetworkValue = _packetReader.ReadChar(); } else if (command.NetworkValueType == typeof(char[])) { int tempNumberOfChars = _packetReader.ReadInt32(); command.NetworkValue = _packetReader.ReadChars(tempNumberOfChars); } else if (command.NetworkValueType == typeof(Color)) { command.NetworkValue = _packetReader.ReadColor(); } else if (command.NetworkValueType == typeof(double)) { command.NetworkValue = _packetReader.ReadDouble(); } else if (command.NetworkValueType == typeof(float)) { command.NetworkValue = _packetReader.ReadSingle(); } else if (command.NetworkValueType == typeof(int)) { command.NetworkValue = _packetReader.ReadInt32(); } else if (command.NetworkValueType == typeof(long)) { command.NetworkValue = _packetReader.ReadInt64(); } else if (command.NetworkValueType == typeof(Matrix)) { command.NetworkValue = _packetReader.ReadMatrix(); } else if (command.NetworkValueType == typeof(Quaternion)) { command.NetworkValue = _packetReader.ReadQuaternion(); } else if (command.NetworkValueType == typeof(sbyte)) { command.NetworkValue = _packetReader.ReadSByte(); } else if (command.NetworkValueType == typeof(short)) { command.NetworkValue = _packetReader.ReadInt16(); } else if (command.NetworkValueType == typeof(string)) { command.NetworkValue = _packetReader.ReadString(); } else if (command.NetworkValueType == typeof(uint)) { command.NetworkValue = _packetReader.ReadUInt32(); } else if (command.NetworkValueType == typeof(ulong)) { command.NetworkValue = _packetReader.ReadInt64(); } else if (command.NetworkValueType == typeof(ushort)) { command.NetworkValue = _packetReader.ReadUInt16(); } else if (command.NetworkValueType == typeof(Vector2)) { command.NetworkValue = _packetReader.ReadVector2(); } else if (command.NetworkValueType == typeof(Vector3)) { command.NetworkValue = _packetReader.ReadVector3(); } else if (command.NetworkValueType == typeof(Vector4)) { command.NetworkValue = _packetReader.ReadVector4(); } if (command.NetworkValue == null) { throw new CoreException("No value transfered"); } if (command.Condition == null || (command.Condition.Invoke())) { command.NetworkValue = command.ServerExecution(command, command.NetworkValue); } if (command.ApplyServerResult != null) { ExecuteServerCommandOnClients(command); } else { command.WaitingForServerReply = false; } } // Some Commands may not return values and ask the server to compute it for all clients else if (message == Constants.ExecuteCommandOnServerNoDataExchanged) { if (!gamer.IsHost) { throw new CoreException("Gamer isn't host"); } ushort commandId = _packetReader.ReadUInt16(); Command command = Commands[commandId]; if (command.Condition == null || (command.Condition.Invoke())) { command.NetworkValue = command.ServerExecution(command, null); } if (command.ApplyServerResult != null) { ExecuteServerCommandOnClients(command); } else { command.WaitingForServerReply = false; } } else if (message == Constants.SynchronizeCommandOnClient) { if (CommandsToSynchronize.Count > 0) { Command command = CommandsToSynchronize.Dequeue(); ushort commandId = _packetReader.ReadUInt16(); if (Commands.ContainsKey(commandId)) { Commands[commandId] = command; } else { command.Id = commandId; Commands.Add(command.Id, command); } } } else if (message == Constants.SynchronizeSceneEntitiesOnClient) { if (SceneEntitiesToSynchronize.Count > 0) { SceneEntity entity = (SceneEntity)SceneEntitiesToSynchronize.Dequeue(); var entityUniqueId = _packetReader.ReadInt32(); if (RegisteredEntities.ContainsKey(entityUniqueId)) { RegisteredEntities[entityUniqueId] = entity; } else { entity.UniqueId = entityUniqueId; RegisteredEntities.Add(entity.UniqueId, entity); } } } else if (message == Constants.SynchronizationDoneOnClient) { if (!gamer.IsHost) { throw new CoreException("Gamer isn't host"); } var synchronizedPlayers = new List <IdentifiedPlayer>(); if (sender.IsLocal) { foreach (var player in PlayersToSynchronize) { if (player.IsLocal) { synchronizedPlayers.Add(player); } } } else { var senderMachine = sender.Machine; foreach (var player in PlayersToSynchronize) { if (!player.IsLocal) { if (((NetworkGamer)((LiveIdentifiedPlayer)player).LiveGamer).Machine.Equals(senderMachine)) { synchronizedPlayers.Add(player); } } } } if (synchronizedPlayers.Count > 0) { foreach (var synchronizedPlayer in synchronizedPlayers) { PlayersToSynchronize.Remove(synchronizedPlayer); } if (PlayersToSynchronize.Count == 0) { _sessionState = SessionState.Playing; OnStarted(); } } } else { ushort commandId = _packetReader.ReadUInt16(); Command command = Commands[commandId]; command.WaitingForServerReply = false; object networkValue = null; if (message == Constants.ExecuteServerCommandOnClientsDataExchanged) { if (command.NetworkValueType == typeof(bool)) { networkValue = _packetReader.ReadBoolean(); } else if (command.NetworkValueType == typeof(byte)) { networkValue = _packetReader.ReadByte(); } else if (command.NetworkValueType == typeof(byte[])) { int tempNumberOfBytes = _packetReader.ReadInt32(); networkValue = _packetReader.ReadBytes(tempNumberOfBytes); } else if (command.NetworkValueType == typeof(char)) { networkValue = _packetReader.ReadChar(); } else if (command.NetworkValueType == typeof(char[])) { int tempNumberOfChars = _packetReader.ReadInt32(); networkValue = _packetReader.ReadChars(tempNumberOfChars); } else if (command.NetworkValueType == typeof(Color)) { networkValue = _packetReader.ReadColor(); } else if (command.NetworkValueType == typeof(double)) { networkValue = _packetReader.ReadDouble(); } else if (command.NetworkValueType == typeof(float)) { networkValue = _packetReader.ReadSingle(); } else if (command.NetworkValueType == typeof(int)) { networkValue = _packetReader.ReadInt32(); } else if (command.NetworkValueType == typeof(long)) { networkValue = _packetReader.ReadInt64(); } else if (command.NetworkValueType == typeof(Matrix)) { networkValue = _packetReader.ReadMatrix(); } else if (command.NetworkValueType == typeof(Quaternion)) { networkValue = _packetReader.ReadQuaternion(); } else if (command.NetworkValueType == typeof(sbyte)) { networkValue = _packetReader.ReadSByte(); } else if (command.NetworkValueType == typeof(short)) { networkValue = _packetReader.ReadInt16(); } else if (command.NetworkValueType == typeof(string)) { networkValue = _packetReader.ReadString(); } else if (command.NetworkValueType == typeof(uint)) { networkValue = _packetReader.ReadUInt32(); } else if (command.NetworkValueType == typeof(ulong)) { networkValue = _packetReader.ReadInt64(); } else if (command.NetworkValueType == typeof(ushort)) { networkValue = _packetReader.ReadUInt16(); } else if (command.NetworkValueType == typeof(Vector2)) { networkValue = _packetReader.ReadVector2(); } else if (command.NetworkValueType == typeof(Vector3)) { networkValue = _packetReader.ReadVector3(); } else if (command.NetworkValueType == typeof(Vector4)) { networkValue = _packetReader.ReadVector4(); } } command.ApplyServerResult(command, networkValue); } } } }
private void ProcessServerMessages() { while ((_incomingMessage = LidgrenSessionManager.Server.ReadMessage()) != null) { switch (_incomingMessage.MessageType) { case NetIncomingMessageType.StatusChanged: { var status = (NetConnectionStatus)_incomingMessage.ReadByte(); switch (status) { case NetConnectionStatus.Disconnected: { IPEndPoint lostConnectionIpEndPoint = _incomingMessage.SenderEndPoint; var playersToRemove = new List <IdentifiedPlayer>(1); foreach (var remotePlayerIpEndPoint in _remotePlayerIpEndPoints) { if (remotePlayerIpEndPoint.Value.Equals(lostConnectionIpEndPoint)) { playersToRemove.Add(remotePlayerIpEndPoint.Key); } } foreach (IdentifiedPlayer identifiedPlayer in playersToRemove) { _remotePlayers.Remove(identifiedPlayer); _remotePlayerIpEndPoints.Remove(identifiedPlayer); _allPlayers.Remove(identifiedPlayer); } SendDisconnectedPlayersToClients(playersToRemove); break; } case NetConnectionStatus.Connected: case NetConnectionStatus.Disconnecting: case NetConnectionStatus.InitiatedConnect: case NetConnectionStatus.None: case NetConnectionStatus.RespondedAwaitingApproval: case NetConnectionStatus.RespondedConnect: default: { Console.WriteLine("Server Status changed to " + status); break; } } break; } case NetIncomingMessageType.DebugMessage: case NetIncomingMessageType.ErrorMessage: case NetIncomingMessageType.VerboseDebugMessage: case NetIncomingMessageType.WarningMessage: { Console.WriteLine(_incomingMessage.ReadString()); break; } case NetIncomingMessageType.Data: { var msgType = (LidgrenMessages)_incomingMessage.ReadByte(); switch (msgType) { case LidgrenMessages.SendLocalPlayersToServer: { List <LidgrenIdentifiedPlayer> clientPlayers = AddNewPlayersOnServer(); if (AllPlayers.Count > 0) { SendPlayersListToJustConnectedClient(); } if (LidgrenSessionManager.Server.ConnectionsCount > 1) { SendNewPlayersToClients(clientPlayers); } SendSessionStateChangedToClients(); break; } case LidgrenMessages.SendSynchronizationDoneToServer: { var synchronizedPlayers = new List <IdentifiedPlayer>(); if (NetUtility.IsLocal(_incomingMessage.SenderEndPoint)) { foreach (IdentifiedPlayer player in PlayersToSynchronize) { if (player.IsLocal) { synchronizedPlayers.Add(player); } } } else { IPEndPoint remoteEndPoint = _incomingMessage.SenderEndPoint; foreach (IdentifiedPlayer player in PlayersToSynchronize) { if (!player.IsLocal) { if (_remotePlayerIpEndPoints[player].Equals(remoteEndPoint)) { synchronizedPlayers.Add(player); } } } } if (synchronizedPlayers.Count > 0) { foreach (IdentifiedPlayer synchronizedPlayer in synchronizedPlayers) { PlayersToSynchronize.Remove(synchronizedPlayer); } if (PlayersToSynchronize.Count == 0) { _serverSessionState = SessionState.Playing; SendSessionStateChangedToClients(); } } break; } case LidgrenMessages.ExecuteCommandOnServerDataExchanged: { ushort commandId = _incomingMessage.ReadUInt16(); Command command = Commands[commandId]; if (command.NetworkValueType == typeof(bool)) { command.NetworkValue = _incomingMessage.ReadBoolean(); } else if (command.NetworkValueType == typeof(byte)) { command.NetworkValue = _incomingMessage.ReadByte(); } else if (command.NetworkValueType == typeof(byte[])) { int tempNumberOfBytes = _incomingMessage.ReadInt32(); command.NetworkValue = _incomingMessage.ReadBytes(tempNumberOfBytes); } else if (command.NetworkValueType == typeof(char)) { command.NetworkValue = Convert.ToChar(_incomingMessage.ReadByte()); } else if (command.NetworkValueType == typeof(char[])) { int tempNumberOfChars = _incomingMessage.ReadInt32(); for (int i = 0; i < tempNumberOfChars; i++) { command.NetworkValue = _incomingMessage.ReadBytes(tempNumberOfChars * 8); } } else if (command.NetworkValueType == typeof(Color)) { command.NetworkValue = new Color(_incomingMessage.ReadVector4()); } else if (command.NetworkValueType == typeof(double)) { command.NetworkValue = _incomingMessage.ReadDouble(); } else if (command.NetworkValueType == typeof(float)) { command.NetworkValue = _incomingMessage.ReadSingle(); } else if (command.NetworkValueType == typeof(int)) { command.NetworkValue = _incomingMessage.ReadInt32(); } else if (command.NetworkValueType == typeof(long)) { command.NetworkValue = _incomingMessage.ReadInt64(); } else if (command.NetworkValueType == typeof(Matrix)) { command.NetworkValue = _incomingMessage.ReadMatrix(); } else if (command.NetworkValueType == typeof(Quaternion)) { command.NetworkValue = _incomingMessage.ReadRotation(24); } else if (command.NetworkValueType == typeof(sbyte)) { command.NetworkValue = _incomingMessage.ReadSByte(); } else if (command.NetworkValueType == typeof(short)) { command.NetworkValue = _incomingMessage.ReadInt16(); } else if (command.NetworkValueType == typeof(string)) { command.NetworkValue = _incomingMessage.ReadString(); } else if (command.NetworkValueType == typeof(uint)) { command.NetworkValue = _incomingMessage.ReadUInt32(); } else if (command.NetworkValueType == typeof(ulong)) { command.NetworkValue = _incomingMessage.ReadInt64(); } else if (command.NetworkValueType == typeof(ushort)) { command.NetworkValue = _incomingMessage.ReadUInt16(); } else if (command.NetworkValueType == typeof(Vector2)) { command.NetworkValue = _incomingMessage.ReadVector2(); } else if (command.NetworkValueType == typeof(Vector3)) { command.NetworkValue = _incomingMessage.ReadVector3(); } else if (command.NetworkValueType == typeof(Vector4)) { command.NetworkValue = _incomingMessage.ReadVector4(); } if (command.NetworkValue == null) { throw new CoreException("No value transfered"); } if (command.Condition == null || (command.Condition.Invoke())) { command.NetworkValue = command.ServerExecution(command, command.NetworkValue); } if (command.ApplyServerResult != null) { ExecuteServerCommandOnClients(command); } else { command.WaitingForServerReply = false; } break; } case LidgrenMessages.ExecuteCommandOnServerNoDataExchanged: { ushort commandId = _incomingMessage.ReadUInt16(); Command command = Commands[commandId]; if (command.Condition == null || (command.Condition.Invoke())) { command.NetworkValue = command.ServerExecution(command, null); } if (command.ApplyServerResult != null) { ExecuteServerCommandOnClients(command); } else { command.WaitingForServerReply = false; } break; } default: break; } break; } case NetIncomingMessageType.DiscoveryRequest: { _outgoingMessage = LidgrenSessionManager.Server.CreateMessage(); _outgoingMessage.Write((byte)SessionType); _outgoingMessage.WriteVariableInt32(AllPlayers.Count); _outgoingMessage.WriteVariableInt32(_privateReservedSlots); _outgoingMessage.WriteVariableInt32(_maxGamers - AllPlayers.Count - _privateReservedSlots); _outgoingMessage.WriteVariableInt32(_sessionProperties.Count); for (int i = 0; i < _sessionProperties.Count; i++) { _outgoingMessage.Write(BitConverter.GetBytes(_sessionProperties[i].Value)); } LidgrenSessionManager.Server.SendDiscoveryResponse(_outgoingMessage, _incomingMessage.SenderEndPoint); break; } case NetIncomingMessageType.ConnectionApproval: case NetIncomingMessageType.ConnectionLatencyUpdated: case NetIncomingMessageType.DiscoveryResponse: case NetIncomingMessageType.Error: case NetIncomingMessageType.NatIntroductionSuccess: case NetIncomingMessageType.Receipt: case NetIncomingMessageType.UnconnectedData: default: { Console.WriteLine("Server received " + _incomingMessage.MessageType); break; } } } }