Пример #1
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns></returns>
        public bool InvokeHandler <T>(T msg) where T : IMessageBase
        {
            int msgType = MessagePacker.GetId <T>();

            byte[] data = MessagePacker.Pack(msg);
            return(InvokeHandler(msgType, new NetworkReader(data)));
        }
Пример #2
0
        public static void UnregisterHandler <T>() where T : IMessageBase
        {
            // use int to minimize collisions
            int msgType = MessagePacker.GetId <T>();

            handlers.Remove(msgType);
        }
        // note: original HLAPI HandleBytes function handled >1 message in a while loop, but this wasn't necessary
        //       anymore because NetworkServer/NetworkClient Update both use while loops to handle >1 data events per
        //       frame already.
        //       -> in other words, we always receive 1 message per Receive call, never two.
        //       -> can be tested easily with a 1000ms send delay and then logging amount received in while loops here
        //          and in NetworkServer/Client Update. HandleBytes already takes exactly one.
        /// <summary>
        /// This function allows custom network connection classes to process data from the network before it is passed to the application.
        /// </summary>
        /// <param name="buffer">The data received.</param>
        internal void TransportReceive(ArraySegment <byte> buffer, int channelId)
        {
            // unpack message
            using (PooledNetworkReader networkReader = NetworkReaderPool.GetReader(buffer))
            {
                try
                {
                    int msgType = MessagePacker.UnpackId(networkReader);

                    if (msgType == MessagePacker.GetId <NotifyPacket>())
                    {
                        // this is a notify message, send to the notify receive
                        NotifyPacket notifyPacket = networkReader.ReadNotifyPacket();
                        ReceiveNotify(notifyPacket, networkReader, channelId);
                    }
                    else
                    {
                        // try to invoke the handler for that message
                        InvokeHandler(msgType, networkReader, channelId);
                    }
                }
                catch (InvalidDataException ex)
                {
                    logger.Log(ex.ToString());
                }
                catch (Exception ex)
                {
                    logger.LogError("Closed connection: " + this + ". Invalid message " + ex);

                    Disconnect();
                }
            }
        }
Пример #4
0
        /// <summary>
        /// Replaces a handler for a particular message type.
        /// <para>See also <see cref="RegisterHandler{T}(Action{NetworkConnection, T}, bool)">RegisterHandler(T)(Action(NetworkConnection, T), bool)</see></para>
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        /// <param name="handler">Function handler which will be invoked when this message type is received.</param>
        /// <param name="requireAuthentication">True if the message requires an authenticated connection</param>
        public static void ReplaceHandler <T>(Action <NetworkConnection, T> handler, bool requireAuthentication = true)
            where T : struct, NetworkMessage
        {
            int msgType = MessagePacker.GetId <T>();

            handlers[msgType] = MessagePacker.WrapHandler(handler, requireAuthentication);
        }
Пример #5
0
        /// <summary>
        /// Unregisters a network message handler.
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        public static bool UnregisterHandler <T>() where T : NetworkMessage
        {
            // use int to minimize collisions
            int msgType = MessagePacker.GetId <T>();

            return(handlers.Remove(msgType));
        }
Пример #6
0
        /// <summary>
        /// Unregisters a network message handler.
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        public static bool UnregisterHandler <T>()
        //where T : struct, NetworkMessage // Wappen: For compatibility
        {
            // use int to minimize collisions
            int msgType = MessagePacker.GetId <T>();

            return(handlers.Remove(msgType));
        }
Пример #7
0
        /// <summary>
        /// Register a handler for a particular message type.
        /// <para>There are several system message types which you can add handlers for. You can also add your own message types.</para>
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        /// <param name="handler">Function handler which will be invoked when this message type is received.</param>
        /// <param name="requireAuthentication">True if the message requires an authenticated connection</param>
        public static void RegisterHandler <T>(Action <NetworkConnection, T> handler, bool requireAuthentication = true) where T : NetworkMessage
        {
            int msgType = MessagePacker.GetId <T>();

            if (handlers.ContainsKey(msgType))
            {
                logger.LogWarning($"NetworkClient.RegisterHandler replacing handler for {typeof(T).FullName}, id={msgType}. If replacement is intentional, use ReplaceHandler instead to avoid this warning.");
            }
            handlers[msgType] = MessagePacker.MessageHandler(handler, requireAuthentication);
        }
Пример #8
0
        /// <summary>
        /// Register a handler for a particular message type.
        /// <para>There are several system message types which you can add handlers for. You can also add your own message types.</para>
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        /// <param name="handler">Function handler which will be invoked for when this message type is received.</param>
        /// <param name="requireAuthentication">True if the message requires an authenticated connection</param>
        public void RegisterHandler <T>(Action <INetworkConnection, T> handler)
        {
            int msgType = MessagePacker.GetId <T>();

            if (logger.filterLogType == LogType.Log && messageHandlers.ContainsKey(msgType))
            {
                logger.Log("NetworkServer.RegisterHandler replacing " + msgType);
            }
            messageHandlers[msgType] = MessageHandler(handler);
        }
        public bool InvokeHandler <T>(T msg) where T : IMessageBase
        {
            NetworkWriter writer = MessagePacker.PackWriter(msg);
            NetworkReader reader = NetworkReaderPool.GetPooledReader(writer.ToArraySegment());
            bool          result = InvokeHandler(MessagePacker.GetId <T>(), reader);

            NetworkReaderPool.Recycle(reader);
            NetworkWriterPool.Recycle(writer);
            return(result);
        }
Пример #10
0
        /// <summary>
        /// Register a handler for a particular message type.
        /// <para>There are several system message types which you can add handlers for. You can also add your own message types.</para>
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        /// <param name="handler">Function handler which will be invoked for when this message type is received.</param>
        /// <param name="requireAuthentication">True if the message requires an authenticated connection</param>
        public void RegisterHandler <T>(Action <INetworkConnection, T> handler)
            where T : IMessageBase, new()
        {
            int msgType = MessagePacker.GetId <T>();

            if (LogFilter.Debug && messageHandlers.ContainsKey(msgType))
            {
                Debug.Log("NetworkServer.RegisterHandler replacing " + msgType);
            }
            messageHandlers[msgType] = MessageHandler(handler);
        }
Пример #11
0
        /// <summary>
        /// Register a handler for a particular message type.
        /// <para>There are several system message types which you can add handlers for. You can also add your own message types.</para>
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        /// <param name="handler">Function handler which will be invoked for when this message type is received.</param>
        /// <param name="requireAuthentication">True if the message requires an authenticated connection</param>
        public void RegisterHandler <C, T>(Action <C, T> handler, bool requireAuthentication = true)
            where T : IMessageBase, new()
            where C : NetworkConnection
        {
            int msgType = MessagePacker.GetId <T>();

            if (LogFilter.Debug && messageHandlers.ContainsKey(msgType))
            {
                Debug.Log("NetworkServer.RegisterHandler replacing " + msgType);
            }
            messageHandlers[msgType] = MessageHandler(handler, requireAuthentication);
        }
Пример #12
0
        public static void RegisterHandler <T>(Action <NetworkConnection, T> handler) where T : IMessageBase, new()
        {
            int msgType = MessagePacker.GetId <T>();

            if (handlers.ContainsKey(msgType))
            {
                if (LogFilter.Debug)
                {
                    Debug.Log("NetworkClient.RegisterHandler replacing " + handler + " - " + msgType);
                }
            }
            handlers[msgType] = MessagePacker.MessageHandler <T>(handler);
        }
Пример #13
0
        /// <summary>
        /// Register a handler for a particular message type.
        /// <para>There are several system message types which you can add handlers for. You can also add your own message types.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="handler"></param>
        /// <param name="requireAuthentication">true if the message requires an authenticated connection</param>
        public static void RegisterHandler <T>(Action <NetworkConnection, T> handler, bool requireAuthentication = true) where T : IMessageBase, new()
        {
            int msgType = MessagePacker.GetId <T>();

            if (handlers.ContainsKey(msgType))
            {
                if (logger.LogEnabled())
                {
                    logger.Log("NetworkClient.RegisterHandler replacing " + handler + " - " + msgType);
                }
            }
            handlers[msgType] = MessagePacker.MessageHandler(handler, requireAuthentication);
        }
Пример #14
0
 public static void RegisterHandler<T>(Action<NetworkConnection, T> handler) where T: IMessageBase, new()
 {
     int msgType = MessagePacker.GetId<T>();
     if (handlers.ContainsKey(msgType))
     {
         if (LogFilter.Debug) Debug.Log("NetworkServer.RegisterHandler replacing " + msgType);
     }
     handlers[msgType] = networkMessage =>
     {
         T message = networkMessage.ReadMessage<T>();
         handler(networkMessage.conn, message);
     };
 }
Пример #15
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns></returns>
        public bool InvokeHandler <T>(T msg) where T : IMessageBase
        {
            // get writer from pool
            NetworkWriter writer = NetworkWriterPool.GetWriter();

            // pack and invoke
            int msgType = MessagePacker.GetId <T>();

            MessagePacker.Pack(msg, writer);
            bool result = InvokeHandler(msgType, new NetworkReader(writer.ToArraySegment()));

            // recycle writer and return
            NetworkWriterPool.Recycle(writer);
            return(result);
        }
Пример #16
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns>Returns true if the handler was successfully invoked</returns>
        public bool InvokeHandler <T>(T msg, int channelId) where T : NetworkMessage
        {
            using (PooledNetworkWriter writer = NetworkWriterPool.GetWriter())
            {
                // if it is a value type,  just use typeof(T) to avoid boxing
                // this works because value types cannot be derived
                // if it is a reference type (for example NetworkMessage),
                // ask the message for the real type
                int msgType = MessagePacker.GetId(default(T) != null ? typeof(T) : msg.GetType());

                MessagePacker.Pack(msg, writer);
                ArraySegment <byte> segment = writer.ToArraySegment();
                using (PooledNetworkReader networkReader = NetworkReaderPool.GetReader(segment))
                    return(InvokeHandler(msgType, networkReader, channelId));
            }
        }
Пример #17
0
        public static void RegisterHandler <T>(Action <NetworkConnection, T> handler) where T : IMessageBase, new()
        {
            int msgType = MessagePacker.GetId <T>();

            if (handlers.ContainsKey(msgType))
            {
                if (LogFilter.Debug)
                {
                    Debug.Log("NetworkClient.RegisterHandler replacing " + handler.ToString() + " - " + msgType);
                }
            }
            handlers[msgType] = (networkMessage) =>
            {
                handler(networkMessage.conn, networkMessage.ReadMessage <T>());
            };
        }
Пример #18
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns></returns>
        public bool InvokeHandler <T>(T msg, int channelId) where T : IMessageBase
        {
            // get writer from pool
            NetworkWriter writer = NetworkWriterPool.GetWriter();

            // pack and invoke
            int msgType = MessagePacker.GetId(typeof(T).IsValueType ? typeof(T) : msg.GetType());

            MessagePacker.Pack(msg, writer);
            ArraySegment <byte> segment = writer.ToArraySegment();
            NetworkReader       reader  = NetworkReaderPool.GetReader(segment);
            bool result = InvokeHandler(msgType, reader, channelId);

            NetworkReaderPool.Recycle(reader);

            // recycle writer and return
            NetworkWriterPool.Recycle(writer);
            return(result);
        }
Пример #19
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns></returns>
        public bool InvokeHandler <T>(T msg, int channelId) where T : IMessageBase
        {
            // get writer from pool
            NetworkWriter writer = NetworkWriterPool.GetWriter();

            // if it is a value type,  just use typeof(T) to avoid boxing
            // this works because value types cannot be derived
            // if it is a reference type (for example IMessageBase),
            // ask the message for the real type
            int msgType = MessagePacker.GetId(typeof(T).IsValueType ? typeof(T) : msg.GetType());

            MessagePacker.Pack(msg, writer);
            ArraySegment <byte> segment = writer.ToArraySegment();
            bool result = InvokeHandler(msgType, new NetworkReader(segment), channelId);

            // recycle writer and return
            NetworkWriterPool.Recycle(writer);
            return(result);
        }
Пример #20
0
        /// <summary>
        /// This function invokes the registered handler function for a message.
        /// <para>Network connections used by the NetworkClient and NetworkServer use this function for handling network messages.</para>
        /// </summary>
        /// <typeparam name="T">The message type to unregister.</typeparam>
        /// <param name="msg">The message object to process.</param>
        /// <returns></returns>
        public bool InvokeHandler <T>(T msg, int channelId) where T : IMessageBase
        {
            // get writer from pool
            using (PooledNetworkWriter writer = NetworkWriterPool.GetWriter())
            {
                // if it is a value type,  just use typeof(T) to avoid boxing
                // this works because value types cannot be derived
                // if it is a reference type (for example IMessageBase),
                // ask the message for the real type
                int msgType = MessagePacker.GetId(typeof(T).IsValueType ? typeof(T) : msg.GetType());

                Debug.Log("[NetworkConnection].InvokeHandler -- msg: " + msg.ToString());

                MessagePacker.Pack(msg, writer);
                ArraySegment <byte> segment = writer.ToArraySegment();
                using (PooledNetworkReader networkReader = NetworkReaderPool.GetReader(segment))
                    return(InvokeHandler(msgType, networkReader, channelId));
            }
        }
Пример #21
0
        /* TODO use or remove
        static void GenerateDataError(NetworkConnection conn, byte error)
        {
            NetworkError dataError = (NetworkError)error;
            Debug.LogError("Mirror Server Data Error: " + dataError);
            GenerateError(conn, error);
        }

        static void GenerateDisconnectError(NetworkConnection conn, byte error)
        {
            NetworkError disconnectError = (NetworkError)error;
            Debug.LogError("Mirror Server Disconnect Error: " + disconnectError + " conn:[" + conn + "]:" + conn.connectionId);
            GenerateError(conn, error);
        }
        */

        static void GenerateError(NetworkConnection conn, byte error)
        {
            int msgId = MessagePacker.GetId<ErrorMessage>();
            if (handlers.ContainsKey(msgId))
            {
                ErrorMessage msg = new ErrorMessage
                {
                    value = error
                };

                // write the message to a local buffer
                NetworkWriter writer = new NetworkWriter();
                msg.Serialize(writer);

                // pass a reader (attached to local buffer) to handler
                NetworkReader reader = new NetworkReader(writer.ToArray());
                conn.InvokeHandler(msgId, reader);
            }
        }
        /// <summary>
        /// Unregisters a handler for a particular message type.
        /// </summary>
        /// <typeparam name="T">Message type</typeparam>
        public void UnregisterHandler <T>()
        {
            int msgType = MessagePacker.GetId <T>();

            messageHandlers.Remove(msgType);
        }
Пример #23
0
        public static void UnregisterHandler <T>() where T : IMessageBase
        {
            int msgType = MessagePacker.GetId <T>();

            handlers.Remove(msgType);
        }