Iâm going to necro this thread worse than it already has been, because I ran into a similar situation and stumbled across it.
In my situation:
I have a C# server, not unity.
In a shared assembly (shared between Unity and the server), it has NetMessage defined, a base class. This is shared so both the client and server know about certain shared network messages.
One of its derived classes is LoginRequest. LoginRequest has two properties, the login id and the password.
When the client wants to login to the server, it creates and sends a new LoginRequest(login, password) to the server.
Now, the server receives the network data, and has to create a loginrequest message for login handling by the server.
private static NetMessage ReadMessage(NetPeer peer, NetDataReader reader)
{
short rawMessageType = reader.GetShort();
MessageType messageType = (MessageType)rawMessageType;
NetMessage message;
switch (messageType)
{
case MessageType.None:
message = new NullMessage();
break;
case MessageType.LoginRequest:
message = new LoginRequest();
break;
default:
message = new NullMessage();
CLog.Log($"Unknown message type {rawMessageType} received from {peer.EndPoint}");
break;
}
message.Read(reader);
return message;
}
so it creates the concrete message type, and calls .Read() to actually read in the byte data from the network stream or whatever, and populate an actual login message. But this function returns it as a NetMessage, NOT a LoginRequest.
Why? I want to handle the Read function for all, in one place, instead of having to handle the serialization in each case statement.
When it returns it, I need to actually handle the login request.
This is where I think one of the above posters is touching on.
So I have a NetMessage now, that is actually a base type of some derived type. So now I want to actually do the login work.
switch (message.Type)
{
case MessageType.None:
break;
case MessageType.LoginRequest:
HandleLoginRequest(peer, (LoginRequest) message);
break;
So now I have to cast it BACK to a LoginRequest, because this is on the server. I do NOT want to have the actual login handling code in the LoginRequest, because that is available to the client. I want to call a method on the server, and actually pass it a LoginRequest, so it can access the login id and password.
I donât see how I could have a generic way to handle DoWork() on the NetMessages, unless I want to have both messages defined, one for the client and one for the server. Thatâs the only way I could see to handle that. The client one is basically a data class, the server one actually has the login handling code.
SoâŚa viable way of handling it, personally I donât care for the duplication and so far I feel just downcasting is fine in this case. These messages only transport data, they donât handle processing the results.