com.unity.netcode.gameobjects@2.0.0-pre.1
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). Additional documentation and release notes are available at [Multiplayer Documentation](https://docs-multiplayer.unity3d.com). ## [2.0.0-pre.1] - 2024-06-17 ### Added - Added event `NetworkManager.OnSessionOwnerPromoted` that is invoked when a new session owner promotion occurs. (#2948) - Added `NetworkRigidBodyBase.GetLinearVelocity` and `NetworkRigidBodyBase.SetLinearVelocity` convenience/helper methods. (#2948) - Added `NetworkRigidBodyBase.GetAngularVelocity` and `NetworkRigidBodyBase.SetAngularVelocity` convenience/helper methods. (#2948) ### Fixed - Fixed issue when `NetworkTransform` half float precision is enabled and ownership changes the current base position was not being synchronized. (#2948) - Fixed issue where `OnClientConnected` not being invoked on the session owner when connecting to a new distributed authority session. (#2948) - Fixed issue where Rigidbody micro-motion (i.e. relatively small velocities) would result in non-authority instances slightly stuttering as the body would come to a rest (i.e. no motion). Now, the threshold value can increase at higher velocities and can decrease slightly below the provided threshold to account for this. (#2948) ### Changed - Changed the client's owned objects is now returned (`NetworkClient` and `NetworkSpawnManager`) as an array as opposed to a list for performance purposes. (#2948) - Changed `NetworkTransfrom.TryCommitTransformToServer` to be internal as it will be removed by the final 2.0.0 release. (#2948) - Changed `NetworkTransformEditor.OnEnable` to a virtual method to be able to customize a `NetworkTransform` derived class by creating a derived editor control from `NetworkTransformEditor`. (#2948)
This commit is contained in:
@@ -45,6 +45,9 @@ namespace Unity.Netcode.Components
|
||||
private Rigidbody m_Rigidbody;
|
||||
private Rigidbody2D m_Rigidbody2D;
|
||||
internal NetworkTransform NetworkTransform;
|
||||
private float m_TickFrequency;
|
||||
private float m_TickRate;
|
||||
|
||||
private enum InterpolationTypes
|
||||
{
|
||||
None,
|
||||
@@ -120,6 +123,129 @@ namespace Unity.Netcode.Components
|
||||
}
|
||||
}
|
||||
|
||||
internal Vector3 GetAdjustedPositionThreshold()
|
||||
{
|
||||
// Since the threshold is a measurement of unity world space units per tick, we will allow for the maximum threshold
|
||||
// to be no greater than the threshold measured in unity world space units per second
|
||||
var thresholdMax = NetworkTransform.PositionThreshold * m_TickRate;
|
||||
// Get the velocity in unity world space units per tick
|
||||
var perTickVelocity = GetLinearVelocity() * m_TickFrequency;
|
||||
// Since a rigid body can have "micro-motion" when allowed to come to rest (based on friction etc), we will allow for
|
||||
// no less than 1/10th the threshold value.
|
||||
var minThreshold = NetworkTransform.PositionThreshold * 0.1f;
|
||||
|
||||
// Finally, we adjust the threshold based on the body's current velocity
|
||||
perTickVelocity.x = Mathf.Clamp(Mathf.Abs(perTickVelocity.x), minThreshold, thresholdMax);
|
||||
perTickVelocity.y = Mathf.Clamp(Mathf.Abs(perTickVelocity.y), minThreshold, thresholdMax);
|
||||
// 2D Rigidbody only moves on x & y axis
|
||||
if (!m_IsRigidbody2D)
|
||||
{
|
||||
perTickVelocity.z = Mathf.Clamp(Mathf.Abs(perTickVelocity.z), minThreshold, thresholdMax);
|
||||
}
|
||||
|
||||
return perTickVelocity;
|
||||
}
|
||||
|
||||
internal Vector3 GetAdjustedRotationThreshold()
|
||||
{
|
||||
// Since the rotation threshold is a measurement pf degrees per tick, we get the maximum threshold
|
||||
// by calculating the threshold in degrees per second.
|
||||
var thresholdMax = NetworkTransform.RotAngleThreshold * m_TickRate;
|
||||
// Angular velocity is expressed in radians per second where as the rotation being checked is in degrees.
|
||||
// Convert the angular velocity to degrees per second and then convert that to degrees per tick.
|
||||
var rotationPerTick = (GetAngularVelocity() * Mathf.Rad2Deg) * m_TickFrequency;
|
||||
var minThreshold = NetworkTransform.RotAngleThreshold * m_TickFrequency;
|
||||
|
||||
// 2D Rigidbody only rotates around Z axis
|
||||
if (!m_IsRigidbody2D)
|
||||
{
|
||||
rotationPerTick.x = Mathf.Clamp(Mathf.Abs(rotationPerTick.x), minThreshold, thresholdMax);
|
||||
rotationPerTick.y = Mathf.Clamp(Mathf.Abs(rotationPerTick.y), minThreshold, thresholdMax);
|
||||
}
|
||||
rotationPerTick.z = Mathf.Clamp(Mathf.Abs(rotationPerTick.z), minThreshold, thresholdMax);
|
||||
|
||||
return rotationPerTick;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the linear velocity of the Rigidbody.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// For <see cref="Rigidbody2D"/>, only the x and y components of the <see cref="Vector3"/> are applied.
|
||||
/// </remarks>
|
||||
public void SetLinearVelocity(Vector3 linearVelocity)
|
||||
{
|
||||
if (m_IsRigidbody2D)
|
||||
{
|
||||
m_Rigidbody2D.velocity = linearVelocity;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_Rigidbody.linearVelocity = linearVelocity;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the linear velocity of the Rigidbody.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// For <see cref="Rigidbody2D"/>, the <see cref="Vector3"/> velocity returned is only applied to the x and y components.
|
||||
/// </remarks>
|
||||
/// <returns><see cref="Vector3"/> as the linear velocity</returns>
|
||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||
public Vector3 GetLinearVelocity()
|
||||
{
|
||||
if (m_IsRigidbody2D)
|
||||
{
|
||||
return m_Rigidbody2D.velocity;
|
||||
}
|
||||
else
|
||||
{
|
||||
return m_Rigidbody.linearVelocity;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets the angular velocity for the Rigidbody.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// For <see cref="Rigidbody2D"/>, the z component of <param name="angularVelocity"/> is only used to set the angular velocity.
|
||||
/// A quick way to pass in a 2D angular velocity component is: <see cref="Vector3.forward"/> * angularVelocity (where angularVelocity is a float)
|
||||
/// </remarks>
|
||||
/// <param name="angularVelocity">the angular velocity to apply to the body</param>
|
||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||
public void SetAngularVelocity(Vector3 angularVelocity)
|
||||
{
|
||||
if (m_IsRigidbody2D)
|
||||
{
|
||||
m_Rigidbody2D.angularVelocity = angularVelocity.z;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_Rigidbody.angularVelocity = angularVelocity;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the angular velocity for the Rigidbody.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// For <see cref="Rigidbody2D"/>, the z component of the <see cref="Vector3"/> returned is the angular velocity of the object.
|
||||
/// </remarks>
|
||||
/// <returns>angular velocity as a <see cref="Vector3"/></returns>
|
||||
[MethodImpl(MethodImplOptions.AggressiveInlining)]
|
||||
public Vector3 GetAngularVelocity()
|
||||
{
|
||||
if (m_IsRigidbody2D)
|
||||
{
|
||||
return Vector3.forward * m_Rigidbody2D.velocity;
|
||||
}
|
||||
else
|
||||
{
|
||||
return m_Rigidbody.angularVelocity;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the position of the Rigidbody
|
||||
/// </summary>
|
||||
@@ -210,6 +336,9 @@ namespace Unity.Netcode.Components
|
||||
}
|
||||
}
|
||||
|
||||
// Used for Rigidbody only (see info on normalized below)
|
||||
private Vector4 m_QuaternionCheck = Vector4.zero;
|
||||
|
||||
/// <summary>
|
||||
/// Rotatates the Rigidbody towards a specified rotation
|
||||
/// </summary>
|
||||
@@ -227,6 +356,17 @@ namespace Unity.Netcode.Components
|
||||
}
|
||||
else
|
||||
{
|
||||
// Evidently we need to check to make sure the quaternion is a perfect
|
||||
// magnitude of 1.0f when applying the rotation to a rigid body.
|
||||
m_QuaternionCheck.x = rotation.x;
|
||||
m_QuaternionCheck.y = rotation.y;
|
||||
m_QuaternionCheck.z = rotation.z;
|
||||
m_QuaternionCheck.w = rotation.w;
|
||||
// If the magnitude is greater than 1.0f (even by a very small fractional value), then normalize the quaternion
|
||||
if (m_QuaternionCheck.magnitude != 1.0f)
|
||||
{
|
||||
rotation.Normalize();
|
||||
}
|
||||
m_Rigidbody.MoveRotation(rotation);
|
||||
}
|
||||
}
|
||||
@@ -501,6 +641,8 @@ namespace Unity.Netcode.Components
|
||||
/// <inheritdoc />
|
||||
public override void OnNetworkSpawn()
|
||||
{
|
||||
m_TickFrequency = 1.0f / NetworkManager.NetworkConfig.TickRate;
|
||||
m_TickRate = NetworkManager.NetworkConfig.TickRate;
|
||||
UpdateOwnershipAuthority();
|
||||
}
|
||||
|
||||
|
||||
@@ -920,6 +920,22 @@ namespace Unity.Netcode.Components
|
||||
#endregion
|
||||
|
||||
#region PROPERTIES AND GENERAL METHODS
|
||||
|
||||
|
||||
public enum AuthorityModes
|
||||
{
|
||||
Server,
|
||||
Owner,
|
||||
}
|
||||
#if MULTIPLAYER_SERVICES_SDK_INSTALLED
|
||||
[Tooltip("Selects who has authority (sends state updates) over the transform. When the network topology is set to distributed authority, this always defaults to owner authority. If server (the default), then only server-side adjustments to the " +
|
||||
"transform will be synchronized with clients. If owner (or client), then only the owner-side adjustments to the transform will be synchronized with both the server and other clients.")]
|
||||
#else
|
||||
[Tooltip("Selects who has authority (sends state updates) over the transform. If server (the default), then only server-side adjustments to the transform will be synchronized with clients. If owner (or client), " +
|
||||
"then only the owner-side adjustments to the transform will be synchronized with both the server and other clients.")]
|
||||
#endif
|
||||
public AuthorityModes AuthorityMode;
|
||||
|
||||
/// <summary>
|
||||
/// The default position change threshold value.
|
||||
/// Any changes above this threshold will be replicated.
|
||||
@@ -1487,7 +1503,7 @@ namespace Unity.Netcode.Components
|
||||
/// </remarks>
|
||||
/// <param name="transformToCommit">the transform to be committed</param>
|
||||
/// <param name="dirtyTime">time it was marked dirty</param>
|
||||
protected void TryCommitTransformToServer(Transform transformToCommit, double dirtyTime)
|
||||
internal void TryCommitTransformToServer(Transform transformToCommit, double dirtyTime)
|
||||
{
|
||||
if (!IsSpawned)
|
||||
{
|
||||
@@ -1568,8 +1584,6 @@ namespace Unity.Netcode.Components
|
||||
// If the transform has deltas (returns dirty) or if an explicitly set state is pending
|
||||
if (m_LocalAuthoritativeNetworkState.ExplicitSet || CheckForStateChange(ref m_LocalAuthoritativeNetworkState, ref transformToCommit, synchronize))
|
||||
{
|
||||
m_LocalAuthoritativeNetworkState.LastSerializedSize = m_OldState.LastSerializedSize;
|
||||
|
||||
// If the state was explicitly set, then update the network tick to match the locally calculate tick
|
||||
if (m_LocalAuthoritativeNetworkState.ExplicitSet)
|
||||
{
|
||||
@@ -1699,9 +1713,20 @@ namespace Unity.Netcode.Components
|
||||
#if COM_UNITY_MODULES_PHYSICS
|
||||
var position = m_UseRigidbodyForMotion ? m_NetworkRigidbodyInternal.GetPosition() : InLocalSpace ? transformToUse.localPosition : transformToUse.position;
|
||||
var rotation = m_UseRigidbodyForMotion ? m_NetworkRigidbodyInternal.GetRotation() : InLocalSpace ? transformToUse.localRotation : transformToUse.rotation;
|
||||
|
||||
var positionThreshold = Vector3.one * PositionThreshold;
|
||||
var rotationThreshold = Vector3.one * RotAngleThreshold;
|
||||
|
||||
if (m_UseRigidbodyForMotion)
|
||||
{
|
||||
positionThreshold = m_NetworkRigidbodyInternal.GetAdjustedPositionThreshold();
|
||||
rotationThreshold = m_NetworkRigidbodyInternal.GetAdjustedRotationThreshold();
|
||||
}
|
||||
#else
|
||||
var position = InLocalSpace ? transformToUse.localPosition : transformToUse.position;
|
||||
var rotation = InLocalSpace ? transformToUse.localRotation : transformToUse.rotation;
|
||||
var positionThreshold = Vector3.one * PositionThreshold;
|
||||
var rotationThreshold = Vector3.one * RotAngleThreshold;
|
||||
#endif
|
||||
var rotAngles = rotation.eulerAngles;
|
||||
var scale = transformToUse.localScale;
|
||||
@@ -1828,21 +1853,21 @@ namespace Unity.Netcode.Components
|
||||
// Begin delta checks against last sent state update
|
||||
if (!UseHalfFloatPrecision)
|
||||
{
|
||||
if (SyncPositionX && (Mathf.Abs(networkState.PositionX - position.x) >= PositionThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncPositionX && (Mathf.Abs(networkState.PositionX - position.x) >= positionThreshold.x || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.PositionX = position.x;
|
||||
networkState.HasPositionX = true;
|
||||
isPositionDirty = true;
|
||||
}
|
||||
|
||||
if (SyncPositionY && (Mathf.Abs(networkState.PositionY - position.y) >= PositionThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncPositionY && (Mathf.Abs(networkState.PositionY - position.y) >= positionThreshold.y || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.PositionY = position.y;
|
||||
networkState.HasPositionY = true;
|
||||
isPositionDirty = true;
|
||||
}
|
||||
|
||||
if (SyncPositionZ && (Mathf.Abs(networkState.PositionZ - position.z) >= PositionThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncPositionZ && (Mathf.Abs(networkState.PositionZ - position.z) >= positionThreshold.z || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.PositionZ = position.z;
|
||||
networkState.HasPositionZ = true;
|
||||
@@ -1863,7 +1888,7 @@ namespace Unity.Netcode.Components
|
||||
{
|
||||
for (int i = 0; i < 3; i++)
|
||||
{
|
||||
if (Math.Abs(position[i] - m_HalfPositionState.PreviousPosition[i]) >= PositionThreshold)
|
||||
if (Math.Abs(position[i] - m_HalfPositionState.PreviousPosition[i]) >= positionThreshold[i])
|
||||
{
|
||||
isPositionDirty = i == 0 ? SyncPositionX : i == 1 ? SyncPositionY : SyncPositionZ;
|
||||
if (!isPositionDirty)
|
||||
@@ -1958,21 +1983,21 @@ namespace Unity.Netcode.Components
|
||||
|
||||
if (!UseQuaternionSynchronization)
|
||||
{
|
||||
if (SyncRotAngleX && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleX, rotAngles.x)) >= RotAngleThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncRotAngleX && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleX, rotAngles.x)) >= rotationThreshold.x || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.RotAngleX = rotAngles.x;
|
||||
networkState.HasRotAngleX = true;
|
||||
isRotationDirty = true;
|
||||
}
|
||||
|
||||
if (SyncRotAngleY && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleY, rotAngles.y)) >= RotAngleThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncRotAngleY && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleY, rotAngles.y)) >= rotationThreshold.y || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.RotAngleY = rotAngles.y;
|
||||
networkState.HasRotAngleY = true;
|
||||
isRotationDirty = true;
|
||||
}
|
||||
|
||||
if (SyncRotAngleZ && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleZ, rotAngles.z)) >= RotAngleThreshold || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
if (SyncRotAngleZ && (Mathf.Abs(Mathf.DeltaAngle(networkState.RotAngleZ, rotAngles.z)) >= rotationThreshold.z || networkState.IsTeleportingNextFrame || isAxisSync))
|
||||
{
|
||||
networkState.RotAngleZ = rotAngles.z;
|
||||
networkState.HasRotAngleZ = true;
|
||||
@@ -1989,7 +2014,7 @@ namespace Unity.Netcode.Components
|
||||
var previousRotation = networkState.Rotation.eulerAngles;
|
||||
for (int i = 0; i < 3; i++)
|
||||
{
|
||||
if (Mathf.Abs(Mathf.DeltaAngle(previousRotation[i], rotAngles[i])) >= RotAngleThreshold)
|
||||
if (Mathf.Abs(Mathf.DeltaAngle(previousRotation[i], rotAngles[i])) >= rotationThreshold[i])
|
||||
{
|
||||
isRotationDirty = true;
|
||||
break;
|
||||
@@ -2984,7 +3009,13 @@ namespace Unity.Netcode.Components
|
||||
return;
|
||||
}
|
||||
m_CachedNetworkObject = NetworkObject;
|
||||
if (m_CachedNetworkManager && m_CachedNetworkManager.DistributedAuthorityMode)
|
||||
{
|
||||
AuthorityMode = AuthorityModes.Owner;
|
||||
}
|
||||
CanCommitToTransform = IsServerAuthoritative() ? IsServer : IsOwner;
|
||||
|
||||
|
||||
var currentPosition = GetSpaceRelativePosition();
|
||||
var currentRotation = GetSpaceRelativeRotation();
|
||||
|
||||
@@ -3011,22 +3042,24 @@ namespace Unity.Netcode.Components
|
||||
#else
|
||||
var forUpdate = true;
|
||||
#endif
|
||||
m_LocalAuthoritativeNetworkState.SynchronizeBaseHalfFloat = false;
|
||||
|
||||
if (CanCommitToTransform)
|
||||
{
|
||||
|
||||
// Make sure authority doesn't get added to updates (no need to do this on the authority side)
|
||||
m_CachedNetworkManager.NetworkTransformRegistration(this, forUpdate, false);
|
||||
if (UseHalfFloatPrecision)
|
||||
{
|
||||
m_HalfPositionState = new NetworkDeltaPosition(currentPosition, m_CachedNetworkManager.ServerTime.Tick, math.bool3(SyncPositionX, SyncPositionY, SyncPositionZ));
|
||||
m_LocalAuthoritativeNetworkState.SynchronizeBaseHalfFloat = isOwnershipChange;
|
||||
SetState(teleportDisabled: false);
|
||||
}
|
||||
|
||||
m_CurrentPosition = currentPosition;
|
||||
m_TargetPosition = currentPosition;
|
||||
|
||||
RegisterForTickUpdate(this);
|
||||
|
||||
m_LocalAuthoritativeNetworkState.SynchronizeBaseHalfFloat = false;
|
||||
if (UseHalfFloatPrecision && isOwnershipChange && !IsServerAuthoritative() && Interpolate)
|
||||
{
|
||||
m_HalfFloatTargetTickOwnership = m_CachedNetworkManager.ServerTime.Tick;
|
||||
@@ -3038,16 +3071,13 @@ namespace Unity.Netcode.Components
|
||||
m_CachedNetworkManager.NetworkTransformRegistration(this, forUpdate, true);
|
||||
// Remove this instance from the tick update
|
||||
DeregisterForTickUpdate(this);
|
||||
|
||||
ResetInterpolatedStateToCurrentAuthoritativeState();
|
||||
m_LocalAuthoritativeNetworkState.SynchronizeBaseHalfFloat = false;
|
||||
m_CurrentPosition = currentPosition;
|
||||
m_TargetPosition = currentPosition;
|
||||
m_CurrentScale = transform.localScale;
|
||||
m_TargetScale = transform.localScale;
|
||||
m_CurrentRotation = currentRotation;
|
||||
m_TargetRotation = currentRotation.eulerAngles;
|
||||
|
||||
}
|
||||
OnInitialize(ref m_LocalAuthoritativeNetworkState);
|
||||
}
|
||||
@@ -3296,7 +3326,7 @@ namespace Unity.Netcode.Components
|
||||
{
|
||||
var serverTime = m_CachedNetworkManager.ServerTime;
|
||||
var cachedServerTime = serverTime.Time;
|
||||
var offset = (float)serverTime.TickOffset;
|
||||
//var offset = (float)serverTime.TickOffset;
|
||||
#if COM_UNITY_MODULES_PHYSICS
|
||||
var cachedDeltaTime = m_UseRigidbodyForMotion ? m_CachedNetworkManager.RealTimeProvider.FixedDeltaTime : m_CachedNetworkManager.RealTimeProvider.DeltaTime;
|
||||
#else
|
||||
@@ -3314,7 +3344,7 @@ namespace Unity.Netcode.Components
|
||||
//offset = m_NetworkTransformTickRegistration.Offset;
|
||||
//}
|
||||
|
||||
var cachedRenderTime = serverTime.TimeTicksAgo(ticksAgo, offset).Time;
|
||||
var cachedRenderTime = serverTime.TimeTicksAgo(ticksAgo).Time;
|
||||
|
||||
// Now only update the interpolators for the portions of the transform being synchronized
|
||||
if (SynchronizePosition)
|
||||
@@ -3388,28 +3418,32 @@ namespace Unity.Netcode.Components
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Override this method and return false to switch to owner authoritative mode
|
||||
/// Determines whether the <see cref="NetworkTransform"/> is <see cref="AuthorityModes.Server"/> or <see cref="AuthorityModes.Owner"/> based on the <see cref="AuthorityMode"/> property.
|
||||
/// You can override this method to control this logic.
|
||||
/// </summary>
|
||||
/// <returns>(<see cref="true"/> or <see cref="false"/>) where when false it runs as owner-client authoritative</returns>
|
||||
/// <returns><see cref="true"/> or <see cref="false"/></returns>
|
||||
protected virtual bool OnIsServerAuthoritative()
|
||||
{
|
||||
if (m_CachedNetworkManager)
|
||||
{
|
||||
return !m_CachedNetworkManager.DistributedAuthorityMode;
|
||||
}
|
||||
return true;
|
||||
return AuthorityMode == AuthorityModes.Server;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Method to determine if this <see cref="NetworkTransform"/> instance is owner or server authoritative.
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// Used by <see cref="NetworkRigidbody"/> to determines if this is server or owner authoritative.
|
||||
/// When using a <see cref="NetworkTopologyTypes.DistributedAuthority"/> <see cref="NetworkConfig.NetworkTopology"/>, this will always be viewed as a <see cref="AuthorityModes.Owner"/> authoritative motion model.
|
||||
/// </remarks>
|
||||
/// <returns><see cref="true"/> or <see cref="false"/></returns>
|
||||
public bool IsServerAuthoritative()
|
||||
{
|
||||
return OnIsServerAuthoritative();
|
||||
if (m_CachedNetworkManager && m_CachedNetworkManager.DistributedAuthorityMode)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return OnIsServerAuthoritative();
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
@@ -3451,9 +3485,10 @@ namespace Unity.Netcode.Components
|
||||
private NetworkTransformMessage m_OutboundMessage = new NetworkTransformMessage();
|
||||
|
||||
|
||||
internal void SerializeMessage(FastBufferWriter writer, int targetVersion)
|
||||
internal int SerializeMessage(FastBufferWriter writer, int targetVersion)
|
||||
{
|
||||
var networkObject = NetworkObject;
|
||||
var position = writer.Position;
|
||||
BytePacker.WriteValueBitPacked(writer, NetworkObjectId);
|
||||
BytePacker.WriteValueBitPacked(writer, (int)NetworkBehaviourId);
|
||||
writer.WriteNetworkSerializable(m_LocalAuthoritativeNetworkState);
|
||||
@@ -3470,6 +3505,7 @@ namespace Unity.Netcode.Components
|
||||
BytePacker.WriteValuePacked(writer, targetId);
|
||||
}
|
||||
}
|
||||
return writer.Position - position;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -3482,7 +3518,7 @@ namespace Unity.Netcode.Components
|
||||
return;
|
||||
}
|
||||
|
||||
bool isServerAuthoritative = OnIsServerAuthoritative();
|
||||
bool isServerAuthoritative = IsServerAuthoritative();
|
||||
if (isServerAuthoritative && !IsServer)
|
||||
{
|
||||
Debug.LogError($"Server authoritative {nameof(NetworkTransform)} can only be updated by the server!");
|
||||
@@ -3526,6 +3562,7 @@ namespace Unity.Netcode.Components
|
||||
// Clients (owner authoritative) send messages to the server-host
|
||||
NetworkManager.MessageManager.SendMessage(ref m_OutboundMessage, networkDelivery, NetworkManager.ServerClientId);
|
||||
}
|
||||
m_LocalAuthoritativeNetworkState.LastSerializedSize = m_OutboundMessage.BytesWritten;
|
||||
}
|
||||
#endregion
|
||||
|
||||
|
||||
Reference in New Issue
Block a user