How to Send Network Messages¶
If you're seeking an intro to developing a basic multiuser virtual world, also look at Multiuser basics and Network mutex
Introduction¶
There are 2 ways to send network messages.- Through channels (recommended).
- Through the NetworkClient.
For either approach you need to have your plugin also implement the IParkObject.
This will give access to the VastPark Player’s engines which contains the NetworkClient.
1) Channels¶
Grabbing channels
We recommend using channels as the messages are only sent through that media. Therefore to receive a message one must have the same name and the same configurations to be sent through to the things that are listening to that channel.
In the client plugin (plugins that the VastPark Player runs), it is best to request for a channel when the NetworkClient is connected, which is done by looking out for the ConnectionEstablished event trigger.
1 public void Load()
2 {
3 _ParkEngine.NetworkClient.ConnectionEstablished += new EventHandler<VastPark.Data.EventArg.CustomNetworkMessageArgs>(NetworkClient_ConnectionEstablished);
4 }
Once connection established is triggered, you can request the channel for your plugin.
1 void NetworkClient_ConnectionEstablished(object sender, VastPark.Data.EventArg.CustomNetworkMessageArgs e)
2 {
3 string channelName = "My Plugin Channel";
4 bool reliable = true;
5 bool ordered = true;
6 _ParkEngine.NetworkClient.GetChannel(channelName, reliable, ordered, new TypedAsyncCallback<INetworkChannel>(My_Channel));
7 }
As soon as the channel is provided, it will trigger the call back that you have provided, there you can start looking out for messages that you have received through the MessageReceived event.
1 private void My_Channel(INetworkChannel channel)
2 {
3 _Channel = channel;
4 _Channel.MessageReceived += new Event<string, NetworkMessage>(Channel_MessageReceived);
5 }
Differentiate different message types by the ID property of the message:
1 void Channel_MessageReceived(object sender, VastPark.Data.EventArg.TypedEventArgs<string, NetworkMessage> e)
2 {
3 switch (e.Value2.ID)
4 {
5 case 1:
6 {
7 //TODO perform you tasks here
8 break;
9 }
10 case 2:
11 {
12 //TODO something else here
13 break;
14 }
15 //etc
16 }
17 }
That’s the basics to grabbing a channel.
Sending Messages
To send a message you need to use the NetworkMessage object from the VastPark.Data project.
There you will need to specify an ID to identify the message you have, and send any information that you may need.
Then choose whom to send it to the message to using your channels. Choose between Broadcast, SendMessage or SendToHost.
1 public void Use_MyChannel()
2 {
3 NetworkMessage message = new NetworkMessage();
4 message.ID = 1;
5
6 string hello = "Hello World";
7
8 message.WriteInt(hello.Length);
9 message.WriteString(hello);
10
11 _Channel.BroadcastMessage(message); //Send message to server plugin and everyone else
12
13 string senderId = _ParkEngine.NetworkClient.ConnectedClients[0].ClientId;
14
15 _Channel.SendMessage(senderId, message); //Send the message to the person with id "senderId"
16 _Channel.SendMessageToHost(message); //Sends to the server only
17 }
You must place the information you want inside the network message in the order that you are planning to extract that information. Think of a NetworkMessage as being similar to a sequentially accessed stream.
Receiving Messages
If you have set up the message received event like this, then messages will passed in.
Try not to do too much work during events handling as it will slow down the framework. If a lot of processing time is needed consider using a queue and another thread to process that queue.
1 _Channel.MessageReceived += new Event<string, NetworkMessage>(Channel_MessageReceived);
2
3 void Channel_MessageReceived(object sender, VastPark.Data.EventArg.TypedEventArgs<string, NetworkMessage> e)
4 {
5 switch (e.Value2.ID)
6 {
7 case 1:
8 {
9 //TODO perform you tasks here
10 NetworkMessage received = e.Value2;
11
12 int stringLength = received.ReadInt();
13 string hello = received.ReadString(stringLength);
14
15 // We receive the client alias here but need to know the client Id.
16 // Lookup the senderId
17 if (e.Value1 != null)
18 {
19 string senderId = (from c in _ParkEngine.NetworkClient.ConnectedClients
20 where c.Alias == e.Value1
21 select c.ClientId).Single();
22 }
23
24 break;
25 }
26 }
27 }
2) NetworkClient¶
NetworkClient send/broadcast methods are marked as obsolete and should be avoided as data sent via these methods will become part of the framework's default channels, reserved for IMML state changes. Sending large messages using these methods can cause unwanted delays in state synchronisation.
Receiving Messages
To listen to the default framework messaging channel, in the load method of your plugin you can hook it as follows:
1 public void Load()
2 {
3 _ParkEngine.NetworkClient.CustomNetworkMessageReceived += new EventHandler<VastPark.Data.EventArg.CustomNetworkMessageArgs>(NetworkClient_CustomNetworkMessageReceived);
4 }
The messages will be sent in the CustomNetworkMessageArgs inside the Message property.
1 void NetworkClient_CustomNetworkMessageReceived(object sender, VastPark.Data.EventArg.CustomNetworkMessageArgs e)
2 {
3 switch (e.Message.ID)
4 {
5 case 1:
6 {
7 //TODO perform you tasks here
8
9 break;
10 }
11 }
12 }
Sending Messages
To send a message you need to use the NetworkMessage object from the VastPark.Data project.
There you will need to specify your ID to identify the message you have, and send any information that you may need.
Then choose whom to send it to the message to using your channels. Choose between Broadcast, SendMessage or SendToHost.
1 public void SendMessage()
2 {
3 NetworkMessage message = new NetworkMessage();
4 message.ID = 1;
5
6 string hello = "Hello World";
7
8 message.WriteInt(hello.Length);
9 message.WriteString(hello);
10
11 _ParkEngine.NetworkClient.SendMessageToHost(message); //Sends to the server and triggers the message to the server plugin
12 _ParkEngine.NetworkClient.BroadcastMessage(message); //Send message to server plugin and everyone else
13
14 string senderId = _ParkEngine.NetworkClient.ConnectedClients[0].ClientId;
15
16 _ParkEngine.NetworkClient.SendMessage(senderId, message); //Send the message to the person who has got it
17 }
You must place the information you want inside the network message in the order that you are planning to extract that information.