/// <summary> /// Processes all events /// </summary> public override void ProcessEvents() { while (localPeerConnectionAttemptMessages.TryDequeue(out LocalPeerConnectionAttemptMessage local_peer_connection_attempt_message)) { IPeer peer = local_peer_connection_attempt_message.Peer; OnPeerConnectionAttempted?.Invoke(peer); if (IsConnectionAllowed(peer)) { peers.Add(peer.GUID.ToString(), peer); OnPeerConnected?.Invoke(peer); } else { local_peer_connection_attempt_message.Peer.Disconnect(EDisconnectionReason.Banned); } } while (localPeerDisconnectionMessages.TryDequeue(out LocalPeerDisconnectionMessage local_peer_disconnection_message)) { IPeer peer = local_peer_disconnection_message.Peer; string key = peer.GUID.ToString(); if (peers.ContainsKey(key)) { OnPeerDisconnected?.Invoke(peer); peers.Remove(key); } foreach (KeyValuePair <string, ILocalPeer> peer_peer in peerPeerLookup) { if (peer.GUID == peer_peer.Value.GUID) { peerPeerLookup.Remove(peer_peer.Key); break; } } } while (localPeerReceiveMessages.TryDequeue(out LocalPeerReceiveMessage local_peer_receive_message)) { OnPeerMessageReceived?.Invoke(local_peer_receive_message.Peer, Compression.Decompress(local_peer_receive_message.Message, local_peer_receive_message.Index, local_peer_receive_message.Length)); } }
/// <summary> /// Constructor /// </summary> /// <param name="Host">Host</param> /// <param name="port">Port</param> /// <param name="timeoutTime">Timeout time in seconds</param> /// <param name="onHandlePeerConnectionAttempt">Handles peer connection attempts</param> public ENetConnector(Host host, ushort port, uint timeoutTime, HandlePeerConnectionAttemptDelegate onHandlePeerConnectionAttempt) : base(onHandlePeerConnectionAttempt) { Host = host ?? throw new ArgumentNullException(nameof(host)); Port = port; TimeoutTime = timeoutTime; connectorThread = new Thread(() => { HashSet <uint> available_peer_ids = new HashSet <uint>(); while (isConnectorThreadRunning) { bool has_network_event = true; if (Host.CheckEvents(out Event network_event) <= 0) { if (Host.Service((int)TimeoutTime, out network_event) <= 0) { has_network_event = false; } } if (has_network_event) { switch (network_event.Type) { case EventType.Connect: available_peer_ids.Add(network_event.Peer.ID); peerConnectionAttemptMessages.Enqueue(new ENetPeerConnectionAttemptMessage(network_event.Peer)); break; case EventType.Disconnect: available_peer_ids.Remove(network_event.Peer.ID); peerDisconnectionMessages.Enqueue(new ENetPeerDisconnectionMessage(network_event.Peer)); break; case EventType.Receive: Packet packet = network_event.Packet; if (buffer.Length < packet.Length) { buffer = new byte[packet.Length / buffer.Length * (((packet.Length % buffer.Length) == 0) ? 1 : 2) * buffer.Length]; } Marshal.Copy(packet.Data, buffer, 0, packet.Length); peerReceiveMessages.Enqueue(new ENetPeerReceiveMessage(network_event.Peer, network_event.ChannelID, Compression.Decompress(buffer, 0U, (uint)packet.Length))); break; case EventType.Timeout: available_peer_ids.Remove(network_event.Peer.ID); peerTimeOutMessages.Enqueue(new ENetPeerTimeOutMessage(network_event.Peer)); break; } } while (peerSendMessages.TryDequeue(out ENetPeerSendMessage send_message)) { if (available_peer_ids.Contains(send_message.Peer.ID)) { Packet packet = default; packet.Create(send_message.Message, (int)send_message.Index, (int)send_message.Length, PacketFlags.Reliable); send_message.Peer.Send(0, ref packet); disposePackets.Add(packet); } } if (disposePackets.Count > 0) { Host.Flush(); foreach (Packet packet in disposePackets) { packet.Dispose(); } disposePackets.Clear(); } } available_peer_ids.Clear(); }); connectorThread.Start(); }