Search Unity

Resolved Network Rigidbody Kinematic sets to unwanted value

Discussion in 'Netcode for GameObjects' started by ACWestmountain, Jan 13, 2023.

  1. ACWestmountain

    ACWestmountain

    Joined:
    Nov 7, 2022
    Posts:
    7
    Hello!
    I'm working on a VR project where two clients are meant to be able to grab and move around an object. To use the Handgrab function of Oculus the objects need a rigidbody with kinematics set to true. We have no interest in collisions for this usecase.

    I'm using ClientNetworkTransform in order to sync the transform of the objects. And as asked by the editor I added a Network Rigidbody on the object. However when activating these objects in the game they instantly fly away as if 'is Kinematic' was set to false.

    I found this line in the Network Rigidbody code:
    // If you have authority then you are not kinematic
    m_Rigidbody.isKinematic = !m_isAuthority;

    Is there any way to override this? As mentioned we have no interest in the objects being non kinematic.

    Thankful for any help or insight, cheers!
     
    sampenguin likes this.
  2. CodeSmile

    CodeSmile

    Joined:
    Apr 10, 2014
    Posts:
    5,889
    In that case it should suffice to not use NetworkRigidbody and rely only on the ClientNetworkTransform to synch the position + rotation. Have you tried that?
     
  3. ACWestmountain

    ACWestmountain

    Joined:
    Nov 7, 2022
    Posts:
    7
    Thank you for the reply! I did try that however the user cannot move the object in that case. The Grab doesn't seem to register anymore, or maybe it does but the server doesn't allow movement. hmm
     
  4. sampenguin

    sampenguin

    Joined:
    Feb 1, 2011
    Posts:
    64
    I just encountered this same problem, seems like a pretty big incorrect assumption to change this flag based on authority (which I assume == ownership?) I'm not using physics sim at all so I always want everything kinematic... however using ClientNetworkTransform makes all my obects start floating and spinning away :\

    Update: Removing the NetworkRigidBody solves my issue... but the editor shows a warning that I should be using it. That warning should be a little more clear about when you need a NRB and implications.
     
  5. ACWestmountain

    ACWestmountain

    Joined:
    Nov 7, 2022
    Posts:
    7
    Indeed I had to use Client network transform and avoid adding the Network Rigidbody component. In this case we also had two other issues, one was ownership. I made it so that when the user grabs the object they ask for ownership and get given ownership by the server. But that still didn't allow us to move the object.
    I did a lot of debugging and saw a few warnings that Network Behaviour didn't act as intended because objects where inactive. When toggling between different objects I set the other as inactive. Netcode didn't like that and seem to have refused to change ownership and handle any transform changes because of it.
    I rewrote my code as to disable mesh renderer and collider instead of setting the entire gameobject as inactive. And ta-da, it works!
     
  6. silviu-georgian77

    silviu-georgian77

    Joined:
    Jan 17, 2016
    Posts:
    12
    Encountered the same problem.

    In my case, I need the
    RigidBody
    to be kinematic on the sever. Each time the
    NetworkManager
    starts, is sets
    isKinematic
    to
    false
    .

    In my case, the solution is to force
    isKinematic = true
    on an update loop.

    Please fix this.
     
  7. FlamingoeZ

    FlamingoeZ

    Joined:
    Sep 20, 2021
    Posts:
    2
    I did a bit of digging through the code and Unity docs. The isKinematic thing is 100% intentional so that the system can run more optimally and not waste data. That being said, unless you go out of your way to make a custom script, your clients will not be able to control their rigidbodies.. *Correct me if I'm wrong.

    I had to make a custom script: (Which I saw on the docs earlier and didn't bat an eye)

    Literally, a copy and paste, because by default "Server is authoritative" or something idk I'm new to this stuff, but this part isn't user-friendly. Hope it helps someone.


    https://docs-multiplayer.unity3d.com/netcode/current/components/networktransform/
    Code (CSharp):
    1. using Unity.Netcode.Components;
    2. using UnityEngine;
    3.  
    4. namespace Unity.Multiplayer.Samples.Utilities.ClientAuthority
    5. {
    6.     /// <summary>
    7.     /// Used for syncing a transform with client side changes. This includes host. Pure server as owner isn't supported by this. Please use NetworkTransform
    8.     /// for transforms that'll always be owned by the server.
    9.     /// </summary>
    10.     [DisallowMultipleComponent]
    11.     public class ClientNetworkTransform : NetworkTransform
    12.     {
    13.         /// <summary>
    14.         /// Used to determine who can write to this transform. Owner client only.
    15.         /// This imposes state to the server. This is putting trust on your clients. Make sure no security-sensitive features use this transform.
    16.         /// </summary>
    17.         protected override bool OnIsServerAuthoritative()
    18.         {
    19.             return false;
    20.         }
    21.     }
    22. }
    THEN IF YOU HAVEN'T DONE SO ALREADY
    When spawning your object, SPAWN IT WITH OWNERSHIP...
    Code (CSharp):
    1. [SerializeField] NetworkObject prefab;
    2. [ServerRpc(RequireOwnership = false)]
    3. public void SpawnBallServerRpc(ServerRpcParams id =default)
    4. {
    5. NetworkObject obj = Instantiate(prefab);
    6. obj.SpawnWithOwnership(id.Receive.SenderClientId, true);
    7. }
     
  8. Papouth

    Papouth

    Joined:
    Mar 28, 2020
    Posts:
    8
    To solve this issue, I just set :
    myPrefab.GetComponent<Rigidbody>().isKinematic = false

    Just after I instantiate my prefab.
    Then is stay interactable and in non kinematic mode.

    You can also do the reverse thing if you want it to stay in kinematic mode.