From 49ad787d7cbabb57a1c22a4d60b601a03e04f373 Mon Sep 17 00:00:00 2001 From: MrGadget <9826063+MrGadget1024@users.noreply.github.com> Date: Sat, 29 Jun 2024 15:09:50 -0400 Subject: [PATCH] fix(NetworkBehaviour): Skip OnValidate in Editor Play Mode (#3852) OnValidate only runs in Editor, but can get invoked in PlayMode if user fiddles with the inspector or by other Unity activities. --- .../NetworkRigidbodyReliable.cs | 27 +++++---- .../NetworkRigidbodyReliable2D.cs | 26 +++++---- .../NetworkRigidbodyUnreliable.cs | 27 +++++---- .../NetworkRigidbodyUnreliable2D.cs | 27 +++++---- .../NetworkTransform/NetworkTransformBase.cs | 19 ++++--- Assets/Mirror/Core/NetworkBehaviour.cs | 57 ++++++++++--------- 6 files changed, 99 insertions(+), 84 deletions(-) diff --git a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable.cs b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable.cs index ba17a7012..a88341ae3 100644 --- a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable.cs +++ b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable.cs @@ -11,6 +11,21 @@ public class NetworkRigidbodyReliable : NetworkTransformReliable Rigidbody rb; bool wasKinematic; + protected override void OnValidate() + { + // Skip if Editor is in Play mode + if (Application.isPlaying) return; + + base.OnValidate(); + + // we can't overwrite .target to be a Rigidbody. + // but we can ensure that .target has a Rigidbody, and use it. + if (target.GetComponent() == null) + { + Debug.LogWarning($"{name}'s NetworkRigidbody.target {target.name} is missing a Rigidbody", this); + } + } + // cach Rigidbody and original isKinematic setting protected override void Awake() { @@ -82,18 +97,6 @@ void FixedUpdate() } } - protected override void OnValidate() - { - base.OnValidate(); - - // we can't overwrite .target to be a Rigidbody. - // but we can ensure that .target has a Rigidbody, and use it. - if (target.GetComponent() == null) - { - Debug.LogWarning($"{name}'s NetworkRigidbody.target {target.name} is missing a Rigidbody", this); - } - } - protected override void OnTeleport(Vector3 destination) { base.OnTeleport(destination); diff --git a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable2D.cs b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable2D.cs index f17bab62e..87583322f 100644 --- a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable2D.cs +++ b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyReliable2D.cs @@ -11,6 +11,20 @@ public class NetworkRigidbodyReliable2D : NetworkTransformReliable Rigidbody2D rb; bool wasKinematic; + protected override void OnValidate() + { + if (Application.isPlaying) return; + + base.OnValidate(); + + // we can't overwrite .target to be a Rigidbody. + // but we can ensure that .target has a Rigidbody, and use it. + if (target.GetComponent() == null) + { + Debug.LogWarning($"{name}'s NetworkRigidbody2D.target {target.name} is missing a Rigidbody2D", this); + } + } + // cach Rigidbody and original isKinematic setting protected override void Awake() { @@ -82,18 +96,6 @@ void FixedUpdate() } } - protected override void OnValidate() - { - base.OnValidate(); - - // we can't overwrite .target to be a Rigidbody. - // but we can ensure that .target has a Rigidbody, and use it. - if (target.GetComponent() == null) - { - Debug.LogWarning($"{name}'s NetworkRigidbody2D.target {target.name} is missing a Rigidbody2D", this); - } - } - protected override void OnTeleport(Vector3 destination) { base.OnTeleport(destination); diff --git a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable.cs b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable.cs index 6a347669e..e2a34c03a 100644 --- a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable.cs +++ b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable.cs @@ -11,6 +11,21 @@ public class NetworkRigidbodyUnreliable : NetworkTransformUnreliable Rigidbody rb; bool wasKinematic; + protected override void OnValidate() + { + // Skip if Editor is in Play mode + if (Application.isPlaying) return; + + base.OnValidate(); + + // we can't overwrite .target to be a Rigidbody. + // but we can ensure that .target has a Rigidbody, and use it. + if (target.GetComponent() == null) + { + Debug.LogWarning($"{name}'s NetworkRigidbody.target {target.name} is missing a Rigidbody", this); + } + } + // cach Rigidbody and original isKinematic setting protected override void Awake() { @@ -82,18 +97,6 @@ void FixedUpdate() } } - protected override void OnValidate() - { - base.OnValidate(); - - // we can't overwrite .target to be a Rigidbody. - // but we can ensure that .target has a Rigidbody, and use it. - if (target.GetComponent() == null) - { - Debug.LogWarning($"{name}'s NetworkRigidbody.target {target.name} is missing a Rigidbody", this); - } - } - protected override void OnTeleport(Vector3 destination) { base.OnTeleport(destination); diff --git a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable2D.cs b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable2D.cs index 308ce0e70..387772642 100644 --- a/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable2D.cs +++ b/Assets/Mirror/Components/NetworkRigidbody/NetworkRigidbodyUnreliable2D.cs @@ -11,6 +11,21 @@ public class NetworkRigidbodyUnreliable2D : NetworkTransformUnreliable Rigidbody2D rb; bool wasKinematic; + protected override void OnValidate() + { + // Skip if Editor is in Play mode + if (Application.isPlaying) return; + + base.OnValidate(); + + // we can't overwrite .target to be a Rigidbody. + // but we can ensure that .target has a Rigidbody, and use it. + if (target.GetComponent() == null) + { + Debug.LogWarning($"{name}'s NetworkRigidbody2D.target {target.name} is missing a Rigidbody2D", this); + } + } + // cach Rigidbody and original isKinematic setting protected override void Awake() { @@ -82,18 +97,6 @@ void FixedUpdate() } } - protected override void OnValidate() - { - base.OnValidate(); - - // we can't overwrite .target to be a Rigidbody. - // but we can ensure that .target has a Rigidbody, and use it. - if (target.GetComponent() == null) - { - Debug.LogWarning($"{name}'s NetworkRigidbody2D.target {target.name} is missing a Rigidbody2D", this); - } - } - protected override void OnTeleport(Vector3 destination) { base.OnTeleport(destination); diff --git a/Assets/Mirror/Components/NetworkTransform/NetworkTransformBase.cs b/Assets/Mirror/Components/NetworkTransform/NetworkTransformBase.cs index a30f5d9c0..ab00ba22f 100644 --- a/Assets/Mirror/Components/NetworkTransform/NetworkTransformBase.cs +++ b/Assets/Mirror/Components/NetworkTransform/NetworkTransformBase.cs @@ -98,6 +98,17 @@ public abstract class NetworkTransformBase : NetworkBehaviour public bool showOverlay; public Color overlayColor = new Color(0, 0, 0, 0.5f); + protected override void OnValidate() + { + // Skip if Editor is in Play mode + if (Application.isPlaying) return; + + base.OnValidate(); + + // configure in awake + Configure(); + } + // initialization ////////////////////////////////////////////////////// // forcec configuration of some settings protected virtual void Configure() @@ -125,14 +136,6 @@ protected virtual void Awake() Configure(); } - protected override void OnValidate() - { - base.OnValidate(); - - // configure in awake - Configure(); - } - // snapshot functions ////////////////////////////////////////////////// // get local/world position protected virtual Vector3 GetPosition() => diff --git a/Assets/Mirror/Core/NetworkBehaviour.cs b/Assets/Mirror/Core/NetworkBehaviour.cs index 61d35cf43..bec39b9f3 100644 --- a/Assets/Mirror/Core/NetworkBehaviour.cs +++ b/Assets/Mirror/Core/NetworkBehaviour.cs @@ -149,6 +149,35 @@ public bool authority // hook guard prevents that. ulong syncVarHookGuard; + protected virtual void OnValidate() + { + // Skip if Editor is in Play mode + if (Application.isPlaying) return; + + // we now allow child NetworkBehaviours. + // we can not [RequireComponent(typeof(NetworkIdentity))] anymore. + // instead, we need to ensure a NetworkIdentity is somewhere in the + // parents. + // only run this in Editor. don't add more runtime overhead. + + // GetComponentInParent(includeInactive) is needed because Prefabs are not + // considered active, so this check requires to scan inactive. +#if UNITY_2021_3_OR_NEWER // 2021 has GetComponentInParent(bool includeInactive = false) + if (GetComponent() == null && + GetComponentInParent(true) == null) + { + Debug.LogError($"{GetType()} on {name} requires a NetworkIdentity. Please add a NetworkIdentity component to {name} or it's parents.", this); + } +#elif UNITY_2020_3_OR_NEWER // 2020 only has GetComponentsInParent(bool includeInactive = false), we can use this too + NetworkIdentity[] parentsIds = GetComponentsInParent(true); + int parentIdsCount = parentsIds != null ? parentsIds.Length : 0; + if (GetComponent() == null && parentIdsCount == 0) + { + Debug.LogError($"{GetType()} on {name} requires a NetworkIdentity. Please add a NetworkIdentity component to {name} or it's parents.", this); + } +#endif + } + // USED BY WEAVER to set syncvars in host mode without deadlocking protected bool GetSyncVarHookGuard(ulong dirtyBit) => (syncVarHookGuard & dirtyBit) != 0UL; @@ -302,34 +331,6 @@ protected void InitSyncObject(SyncObject syncObject) }; } - protected virtual void OnValidate() - { - // we now allow child NetworkBehaviours. - // we can not [RequireComponent(typeof(NetworkIdentity))] anymore. - // instead, we need to ensure a NetworkIdentity is somewhere in the - // parents. - // only run this in Editor. don't add more runtime overhead. - - // GetComponentInParent(includeInactive) is needed because Prefabs are not - // considered active, so this check requires to scan inactive. -#if UNITY_EDITOR -#if UNITY_2021_3_OR_NEWER // 2021 has GetComponentInParent(bool includeInactive = false) - if (GetComponent() == null && - GetComponentInParent(true) == null) - { - Debug.LogError($"{GetType()} on {name} requires a NetworkIdentity. Please add a NetworkIdentity component to {name} or it's parents.", this); - } -#elif UNITY_2020_3_OR_NEWER // 2020 only has GetComponentsInParent(bool includeInactive = false), we can use this too - NetworkIdentity[] parentsIds = GetComponentsInParent(true); - int parentIdsCount = parentsIds != null ? parentsIds.Length : 0; - if (GetComponent() == null && parentIdsCount == 0) - { - Debug.LogError($"{GetType()} on {name} requires a NetworkIdentity. Please add a NetworkIdentity component to {name} or it's parents.", this); - } -#endif -#endif - } - // pass full function name to avoid ClassA.Func <-> ClassB.Func collisions protected void SendCommandInternal(string functionFullName, int functionHashCode, NetworkWriter writer, int channelId, bool requiresAuthority = true) {