There are no words for how good it feels to get something working after such a long time. My hourly dev effort has definitely not worked out the way I wanted since I hit this problem, but I now have a solution to a couple of problems.
The first was to replicate an Unityās old RPC system in Unet. RPCs still exist in a sense, but they function differently in the HLAPI, and have weird restrictions which means they arenāt suitable for what I want to do. In this case, send a piece of information, say, a simple string, likeĀ āI really donāt like Unetā.
The way to do this is actually with Unetās network messages which you can read about here:Ā http://docs.unity3d.com/Manual/UNetMessages.html
And if that doesnāt seem to make a whole lot of sense, hereās a fairly simple breakdown that got me started:Ā http://forum.unity3d.com/threads/command-between-2-different-scripts.334902/#post-2168275
The forum post (Thanks Carpe Denius!) gave me the basic approach and understanding, and going back to the official documentation helped me flesh out what I needed to do.Ā
Using the MessageBase class itās possible to create a message with a range of data inside, but for now Iām just sending the aforementioned simple string.
On the client, in the one script I have
class StringMessage : MessageBase
{
Ā Ā public string deathCoords;
}
public class Networking : MonoBehaviour
{
Ā Ā NetworkClient myClient;
Ā Ā StringMessage msg;
// Use this for initialization
void Start ()
Ā Ā {
Ā Ā Ā Ā ConnectToServer();
Ā Ā }
// Update is called once per frame
void Update ()
Ā Ā {
Ā Ā if(Input.GetKeyDown(KeyCode.P))
Ā Ā Ā Ā {
Ā Ā Ā Ā Ā Ā Debug.Log("Pressed P");
Ā Ā Ā Ā Ā Ā msg = new StringMessage();
Ā Ā Ā Ā Ā Ā msg.deathCoords = "0,0";
Ā Ā Ā Ā Ā Ā myClient.Send(666, msg);
//some other functions doing some stuff...
}
So you can see Iām going to send coordinates of where the player has died (simulated by pressing P), and for now those are hard coded to a string saying 0,0. Iāll retrieve the actual player coords later, I just needed to get the message sent first; baby steps.
public class MyNetworkManager : MonoBehaviour
{
Ā Ā public StringMessage receivedMsg;
Ā Ā public bool isAtStartup = true;
Ā Ā void Start()
Ā Ā {
Ā Ā Ā Ā SetupServer();
Ā Ā }
Ā Ā void OnGUI()
Ā Ā {
Ā Ā Ā Ā //some display stuff
Ā Ā }
Ā Ā // Create a server and listen on a port
Ā Ā public void SetupServer()
Ā Ā {
Ā Ā Ā Ā NetworkServer.Listen(4445);
Ā Ā Ā Ā NetworkServer.RegisterHandler(666, DeathLog);
Ā Ā Ā Ā isAtStartup = false;
Ā Ā }
Ā Ā void DeathLog(NetworkMessage msg)
Ā Ā {
Ā Ā Ā Ā receivedMsg = msg.ReadMessage<StringMessage>();
Ā Ā Ā Ā Debug.Log("received Message " + receivedMsg.value);
Ā Ā Ā Ā guiUpdate += "player died at coords " + receivedMsg.value + "\n";
Ā Ā }
}
And here Iām logging the location. one of the things I was also doing wrong here in the DeathLog function was not setting a local stringmessage variable, and trying to do this
Debug.Log("received Message " + msg.ReadMessage<StringMessage>() .value);Ā
guiUpdate += "player died at coords " + msg.ReadMessage<StringMessage>() .value + "\n";
This gives an error because you canāt deserialise the message more than once, which happens when ReadMessage is called. So by deserialising into receivedMsg itās usable as many times as required. I spent a few hours trying to work out why the log would print out fine and then every other readmessage afterwards would fail.
I found that solution here:Ā http://forum.unity3d.com/threads/need-help-with-custom-messages.339010/
So now I am sending and receiving messages. The next step is to fix my server GUI, because despite me updating it, the display does not change. Iām hoping thatās less painful than these last few weeks.