/**
         * @brief Instantiates a new prefab in a deterministic way.
         *
         * @param prefab GameObject's prefab to instantiate.
         * @param position Position to place the new GameObject.
         * @param rotation Rotation to set in the new GameObject.
         **/
        public static GameObject SyncedInstantiate(GameObject prefab, TSVector position, TSQuaternion rotation)
        {
            GameObject go = GameObject.Instantiate(prefab, position.ToVector(), rotation.ToQuaternion()) as GameObject;

            InitializeGameObject(go, position, rotation);
            return(go);
        }
        private static void InitializeGameObject(GameObject go, TSVector position, TSQuaternion rotation)
        {
            ICollider[] tsColliders = go.GetComponentsInChildren <ICollider>();
            if (tsColliders != null)
            {
                for (int index = 0, length = tsColliders.Length; index < length; index++)
                {
                    PhysicsManager.instance.AddBody(tsColliders[index]);
                }
            }

            TSTransform rootTSTransform = go.GetComponent <TSTransform>();

            if (rootTSTransform != null)
            {
                rootTSTransform.Initialize();

                rootTSTransform.position = position;
                rootTSTransform.rotation = rotation;
            }

            TSTransform[] tsTransforms = go.GetComponentsInChildren <TSTransform>();
            if (tsTransforms != null)
            {
                for (int index = 0, length = tsTransforms.Length; index < length; index++)
                {
                    TSTransform tsTransform = tsTransforms[index];

                    if (tsTransform != rootTSTransform)
                    {
                        tsTransform.Initialize();
                    }
                }
            }

            TSTransform2D rootTSTransform2D = go.GetComponent <TSTransform2D>();

            if (rootTSTransform2D != null)
            {
                rootTSTransform2D.Initialize();

                rootTSTransform2D.position = new TSVector2(position.x, position.y);
                rootTSTransform2D.rotation = rotation.ToQuaternion().eulerAngles.z;
            }

            TSTransform2D[] tsTransforms2D = go.GetComponentsInChildren <TSTransform2D>();
            if (tsTransforms2D != null)
            {
                for (int index = 0, length = tsTransforms2D.Length; index < length; index++)
                {
                    TSTransform2D tsTransform2D = tsTransforms2D[index];

                    if (tsTransform2D != rootTSTransform2D)
                    {
                        tsTransform2D.Initialize();
                    }
                }
            }
        }
        private static void InitializeGameObject(GameObject go, TSVector position, TSQuaternion rotation)
        {
            MonoBehaviour[] monoBehaviours = go.GetComponentsInChildren <MonoBehaviour>();
            for (int index = 0, length = monoBehaviours.Length; index < length; index++)
            {
                MonoBehaviour bh = monoBehaviours[index];

                if (bh is IFrameSyncBehaviour)
                {
                    instance.queuedBehaviours.Add(instance.NewManagedBehavior((IFrameSyncBehaviour)bh));
                }
            }


            ICollider[] tsColliders = go.GetComponentsInChildren <ICollider>();
            if (tsColliders != null)
            {
                for (int index = 0, length = tsColliders.Length; index < length; index++)
                {
                    PhysicsManager.instance.AddBody(tsColliders[index]);
                }
            }

            FPTransform rootFPTransform = go.GetComponent <FPTransform>();

            if (rootFPTransform != null)
            {
                rootFPTransform.Initialize();

                rootFPTransform.position = position;
                rootFPTransform.rotation = rotation;
            }

            FPTransform[] FPTransforms = go.GetComponentsInChildren <FPTransform>();
            if (FPTransforms != null)
            {
                for (int index = 0, length = FPTransforms.Length; index < length; index++)
                {
                    FPTransform FPTransform = FPTransforms[index];

                    if (FPTransform != rootFPTransform)
                    {
                        FPTransform.Initialize();
                    }
                }
            }

            FPTransform2D rootFPTransform2D = go.GetComponent <FPTransform2D>();

            if (rootFPTransform2D != null)
            {
                rootFPTransform2D.Initialize();

                rootFPTransform2D.position = new TSVector2(position.x, position.y);
                rootFPTransform2D.rotation = rotation.ToQuaternion().eulerAngles.z;
            }

            FPTransform2D[] FPTransforms2D = go.GetComponentsInChildren <FPTransform2D>();
            if (FPTransforms2D != null)
            {
                for (int index = 0, length = FPTransforms2D.Length; index < length; index++)
                {
                    FPTransform2D FPTransform2D = FPTransforms2D[index];

                    if (FPTransform2D != rootFPTransform2D)
                    {
                        FPTransform2D.Initialize();
                    }
                }
            }
        }