FishNet icon indicating copy to clipboard operation
FishNet copied to clipboard

Unexpected behaviour caused by spawning an object in OnStartServer

Open maxkratt opened this issue 2 years ago • 6 comments

There is an unexpected/strange behavior that happens when trying to move an object and spawn another object in OnStartServer.

This is with "client authority" set in the Network Transform. Note: the object being moved is not the object being spawned.

If the call to spawn the object comes before the call to move, then the move does not happen effectively.

  • The object will not move on its owner's client.
  • The object will move on the server, and then instantly snap back.
  • The object will move on other clients, and not snap back.

If however the call to spawn the object comes after the call to move, then the move does happen effectively.

  • The object will move on the server and all clients.

Tested on FishNet versions 2.3.14 Pro and 2.4.5hf0 Pro. The problem does not happen for host clients.

Example of working code:

public override void OnStartServer()
{
    base.OnStartServer();

    GameObject go = Instantiate(prefab);

    // Setting this object's position, NOT the position of the spawned object.
    transform.SetPositionAndRotation(new Vector3(4, 4, 0), Quaternion.identity);

    InstanceFinder.ServerManager.Spawn(go);
}

Example of code not working:

public override void OnStartServer()
{
    base.OnStartServer();

    GameObject go = Instantiate(prefab);
    InstanceFinder.ServerManager.Spawn(go);

    // Setting this object's position, NOT the position of the spawned object.
    transform.SetPositionAndRotation(new Vector3(4, 4, 0), Quaternion.identity);
}

Here is a unitypackage with an example. The working version of the code is commented out. SpawnObjectTest.zip

maxkratt avatar Sep 23 '22 15:09 maxkratt

Having now considered that moving an object on the server that has client authority is a pretty bad idea, I am ready to close this issue. However I'll wait for a response first in case this information could be helpful in tracking down a bug.

maxkratt avatar Sep 24 '22 22:09 maxkratt

You said its client auth but in your example you're not assigning an owner. If there is no owner the server should have say. If you are assigning an owner then the server won't have say at that point.

FirstGearGames avatar Sep 24 '22 22:09 FirstGearGames

So in the example I use the default player spawner component that comes with FishNet, this does set an owner unless I'm mistaken.

maxkratt avatar Sep 25 '22 05:09 maxkratt

It sounds like it's working as intended then.

You are moving the object before network spawning in one example, which updates the position on the server properly you stated. This makes sense because there is no owner at the time.

In your second example you're doing it after server spawning, where an owner has been set. Because you are using a NT with client authoritative and there is an owner, server no longer has say of the position, that owner does. Therefor the position you set on the server is properly being ignored.

FirstGearGames avatar Sep 26 '22 17:09 FirstGearGames

I think there is a misunderstanding, but I'll ask this. When OnServerStart is called on an object that has an owner set in its spawn call, doesn't the object already have an owner? The following is where I think the misunderstanding is. The object being spawned in the script is not the object being moved. The object being spawned is irrelevant, all that's important in the example is the fact that spawning an object affects the outcome of the rest of the code in the script.

maxkratt avatar Sep 26 '22 19:09 maxkratt

I think there is a misunderstanding, but I'll ask this. When OnServerStart is called on an object that has an owner set in its spawn call, doesn't the object already have an owner? The following is where I think the misunderstanding is. The object being spawned in the script is not the object being moved. The object being spawned is irrelevant, all that's important in the example is the fact that spawning an object affects the outcome of the rest of the code in the script.

You're right I missed that. This behavior is unusual.

FirstGearGames avatar Sep 26 '22 23:09 FirstGearGames

Confirmed unusual behavior. Marking as bug until I can investigate further.

FirstGearGames avatar Dec 04 '22 22:12 FirstGearGames

On the playerObj it would seem OnSpawnServer is being called before the position is changed. It's possible spawning another object is forcing the OnSpawnServer to invoke before OnStartServer finishes.

I've not dug deep enough but I suspect by spawning another object observers are being rebuilt immediately rather than after OnStartServer, which is why OnSpawnServer is being sent before the method completes.

I've yet to confirm this theory but it makes sense. I'm not sure how easy a fix for this will be but I'm keeping this bug on my radar.

FirstGearGames avatar Jan 29 '23 16:01 FirstGearGames

I'm putting this as wont fix. Maybe will come back to it later but seems like a minor issue and may require a bit of work I'm not ready to put in yet.

FirstGearGames avatar Feb 06 '23 23:02 FirstGearGames