- Home /
[UNet/HLAPI] Specify recipients of data sending / actions
Hello everyone,
I am changing a "network architecture" of my project from the old networking system to the new one using UNet / HLAPI. I am totally new to the new system.
By the way, I believe the new system is less flexible from the first one. You don't have much control as before ... Anyway ...
Context
I understood that the system is a server authoritative system, thus, all the data must be sent to the server before being sent to all the clients. And the fact that all the clients receive the data is exactly what I don't want. A similar problem I have is that spawning objects create the objects on all the clients.
Problem
I would like to prevent this last behaviour since my clients really don't care about the other clients, and I would like to save some bandwidth (it's very critical for the system I am making).
With the old system, I was using networkView groups from my clients as follow :
void Awake()
{
// All network messages and RPC calls go through this group number
networkView.group = 1;
// Disable transmission of messages and RPC calls on the network group number 1.
if( Network.isServer )
{
Network.SetSendingEnabled( 1, false );
}
}
But with the new system, I don't know if it's still possible.
But now, my first problem is to prevent the spawning of players on each clients. I could what I already made but if there is the new system, I guess it's possible with it too !
Alternative
If there is no way, I could just send an order to the clients to instantiate their players, and instantiate each players on the server too, but how can I make them communicate ? (Using NetworkViewId like before ?)
I already tried to destroy the instantiated object if it's not a local player, but : it glitches + useless data sending + error raised by Unity.
void Start ()
{
if ( !isLocalPlayer )
Destroy( gameObject );
}
$$anonymous$$issingReferenceException: The object of type 'NetworkIdentity' has been destroyed but you are still trying to access it.
EDIT : Overriding the NetworkBehaviour.OnStartLocalPlayer function solve this problem.
It seems that a server can send a message to only client using
NetworkServer.SendToClient<$$anonymous$$SG>(int,short,$$anonymous$$SG)
Doc : http://docs.unity3d.com/ScriptReference/Networking.NetworkServer.SendToClient.html
I will have to make some research to understand how can I use it for my problem ...
The documentation about UNet definitively lacks of examples.
Answer by meat5000 · Jul 29, 2015 at 01:33 PM
I think this page is what you need
http://docs.unity3d.com/Manual/UNetVisibility.html
You should use ILSpy to bust open
C:\Program Files\Unity\Editor\Data\UnityExtensions\Unity\Networking\UnityEngine.Networking.dll
It is very very useful to see exactly how these methods are written.
Edit: This could be of interest
// UnityEngine.Networking.NetworkServer
internal static void HideForConnection(NetworkIdentity uv, NetworkConnection conn)
{
conn.Send(13, new ObjectDestroyMessage
{
netId = uv.netId
});
}
Which you could access via reflection, perhaps?
public static void HideAnObject (NetworkIdentity myUV, NetworkConnection myConn)
{
Type netServType = Type.GetType ("UnityEngine.Networking.NetworkServer,UnityEngine");
MethodInfo MyHideForConnection = netServType.GetMethod ("HideForConnection", BindingFlags.NonPublic | BindingFlags.Static);
object[] myArgs = new object[] {myUV, myConn};
MyHideForConnection.Invoke (null, myArgs);
}
Here's some code that compiles but I've no idea if it'd work; never used Reflection.
Aaaand, that's how you kill a fly with a bazooka ! x) I only need to instantiate empty points in each of my clients as input controllers to control server application. And I don't feel creating physic colliders, managing NetworkProximityChecker just to return false every time !
UNet is very, very game oriented, too much maybe...
Thanks for your answer @meat5000 , I think, I will have to keep it the old way !
You should not spend so much time on my problem @meat5000 !
I must admit I have never used reflection though I understand a little bit its purpose. But I don't really understand what HideForConnection does ...
According to the doc, it sends a message ? But who is the recipient ? Where does the value '13' comes from ? ObjectDestroy$$anonymous$$essage
is not documented (seems to be $$anonymous$$sgType.ObjectDestroy)
This is an internal $$anonymous$$ethod from Networking.dll
It appears that you specify a connection and a Network Identity and it hides the object.
Its worth the time spent as this is useful to a lot of people.