* feat: NetworkRigidbody and sample scene

* feat: NetworkRigidbody2D component to support 2d physics

* test: add network rigidbody tests
This commit is contained in:
Luke Stampfli 2021-09-17 08:52:51 +01:00 коммит произвёл GitHub
Родитель 2091e2aea9
Коммит 4fe7a30c4e
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
33 изменённых файлов: 3682 добавлений и 40 удалений

Просмотреть файл

@ -0,0 +1,72 @@
using UnityEngine;
namespace Unity.Netcode.Components
{
/// <summary>
/// NetworkRigidbody allows for the use of <see cref="Rigidbody"/> on network objects. By controlling the kinematic
/// mode of the rigidbody and disabling it on all peers but the authoritative one.
/// </summary>
[RequireComponent(typeof(Rigidbody))]
[RequireComponent(typeof(NetworkTransform))]
public class NetworkRigidbody : NetworkBehaviour
{
private Rigidbody m_Rigidbody;
private bool m_OriginalKinematic;
// Used to cache the authority state of this rigidbody during the last frame
private bool m_IsAuthority;
/// <summary>
/// Gets a bool value indicating whether this <see cref="NetworkRigidbody"/> on this peer currently holds authority.
/// </summary>
internal bool HasAuthority => NetworkManager.IsServer; // TODO update this once we support owner authoritative NetworkTransform.
private void Awake()
{
m_Rigidbody = GetComponent<Rigidbody>();
}
// Currently commented out because it is not needed as authority currently can't change at runtime.
// private void FixedUpdate()
// {
// if (NetworkManager.IsListening)
// {
// if (HasAuthority != m_IsAuthority)
// {
// m_IsAuthority = HasAuthority;
// UpdateRigidbodyKinematicMode();
// }
// }
// }
// Puts the rigidbody in a kinematic non-interpolated mode on everyone but the server.
private void UpdateRigidbodyKinematicMode()
{
if (m_IsAuthority == false)
{
m_OriginalKinematic = m_Rigidbody.isKinematic;
m_Rigidbody.isKinematic = true;
}
else
{
// Resets the rigidbody back to it's non replication only state. Happens on shutdown and when authority is lost
m_Rigidbody.isKinematic = m_OriginalKinematic;
}
}
/// <inheritdoc />
public override void OnNetworkSpawn()
{
m_IsAuthority = HasAuthority;
m_OriginalKinematic = m_Rigidbody.isKinematic;
UpdateRigidbodyKinematicMode();
}
/// <inheritdoc />
public override void OnNetworkDespawn()
{
UpdateRigidbodyKinematicMode();
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f6c0be61502bb534f922ebb746851216
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,73 @@
using UnityEngine;
namespace Unity.Netcode.Components
{
/// <summary>
/// NetworkRigidbody allows for the use of <see cref="Rigidbody2D"/> on network objects. By controlling the kinematic
/// mode of the rigidbody and disabling it on all peers but the authoritative one.
/// </summary>
[RequireComponent(typeof(Rigidbody2D))]
[RequireComponent(typeof(NetworkTransform))]
public class NetworkRigidbody2D : NetworkBehaviour
{
private Rigidbody2D m_Rigidbody;
private bool m_OriginalKinematic;
// Used to cache the authority state of this rigidbody during the last frame
private bool m_IsAuthority;
/// <summary>
/// Gets a bool value indicating whether this <see cref="NetworkRigidbody2D"/> on this peer currently holds authority.
/// </summary>
internal bool HasAuthority => NetworkManager.IsServer; // TODO update this once we support owner authoritative NetworkTransform.
private void Awake()
{
m_Rigidbody = GetComponent<Rigidbody2D>();
}
// Currently commented out because it is not needed as authority currently can't change at runtime.
// private void FixedUpdate()
// {
// if (NetworkManager.IsListening)
// {
// if (HasAuthority != m_IsAuthority)
// {
// m_IsAuthority = HasAuthority;
// UpdateRigidbodyKinematicMode();
// }
// }
// }
// Puts the rigidbody in a kinematic non-interpolated mode on everyone but the server.
private void UpdateRigidbodyKinematicMode()
{
if (m_IsAuthority == false)
{
m_OriginalKinematic = m_Rigidbody.isKinematic;
m_Rigidbody.isKinematic = true;
}
else
{
// Resets the rigidbody back to it's non replication only state. Happens on shutdown and when authority is lost
m_Rigidbody.isKinematic = m_OriginalKinematic;
}
}
/// <inheritdoc />
public override void OnNetworkSpawn()
{
m_IsAuthority = HasAuthority;
m_OriginalKinematic = m_Rigidbody.isKinematic;
UpdateRigidbodyKinematicMode();
}
/// <inheritdoc />
public override void OnNetworkDespawn()
{
m_IsAuthority = false;
UpdateRigidbodyKinematicMode();
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 80d7c879794dfda4687da0e400131852
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 58745956b2a1e8346a48c5179cb247eb
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,77 @@
using System.Collections;
using NUnit.Framework;
using Unity.Netcode.Components;
using UnityEngine;
using UnityEngine.TestTools;
namespace Unity.Netcode.RuntimeTests.Physics
{
public class NetworkRigidbody2DDynamicTest : NetworkRigidbodyTestBase
{
public override bool Kinematic => false;
}
public class NetworkRigidbody2DKinematicTest : NetworkRigidbodyTestBase
{
public override bool Kinematic => true;
}
public abstract class NetworkRigidbody2DTestBase : BaseMultiInstanceTest
{
protected override int NbClients => 1;
public abstract bool Kinematic { get; }
[UnitySetUp]
public override IEnumerator Setup()
{
yield return StartSomeClientsAndServerWithPlayers(true, NbClients, playerPrefab =>
{
playerPrefab.AddComponent<NetworkTransform>();
playerPrefab.AddComponent<Rigidbody2D>();
playerPrefab.AddComponent<NetworkRigidbody>();
playerPrefab.GetComponent<Rigidbody2D>().isKinematic = Kinematic;
});
}
/// <summary>
/// Tests that a server can destroy a NetworkObject and that it gets despawned correctly.
/// </summary>
/// <returns></returns>
[UnityTest]
public IEnumerator TestRigidbodyKinematicEnableDisable()
{
// This is the *SERVER VERSION* of the *CLIENT PLAYER*
var serverClientPlayerResult = new MultiInstanceHelpers.CoroutineResultWrapper<NetworkObject>();
yield return MultiInstanceHelpers.Run(MultiInstanceHelpers.GetNetworkObjectByRepresentation((x => x.IsPlayerObject && x.OwnerClientId == m_ClientNetworkManagers[0].LocalClientId), m_ServerNetworkManager, serverClientPlayerResult));
var serverPlayer = serverClientPlayerResult.Result.gameObject;
// This is the *CLIENT VERSION* of the *CLIENT PLAYER*
var clientClientPlayerResult = new MultiInstanceHelpers.CoroutineResultWrapper<NetworkObject>();
yield return MultiInstanceHelpers.Run(MultiInstanceHelpers.GetNetworkObjectByRepresentation((x => x.IsPlayerObject && x.OwnerClientId == m_ClientNetworkManagers[0].LocalClientId), m_ClientNetworkManagers[0], clientClientPlayerResult));
var clientPlayer = clientClientPlayerResult.Result.gameObject;
Assert.IsNotNull(serverPlayer);
Assert.IsNotNull(clientPlayer);
int waitFor = Time.frameCount + 2;
yield return new WaitUntil(() => Time.frameCount >= waitFor);
// server rigidbody has authority and should have a kinematic mode of false
Assert.True(serverPlayer.GetComponent<Rigidbody2D>().isKinematic == Kinematic);
// client rigidbody has no authority and should have a kinematic mode of true
Assert.True(clientPlayer.GetComponent<Rigidbody2D>().isKinematic);
// despawn the server player
serverPlayer.GetComponent<NetworkObject>().Despawn(false);
yield return null;
Assert.IsTrue(serverPlayer.GetComponent<Rigidbody2D>().isKinematic == Kinematic);
yield return null;
Assert.IsTrue(clientPlayer == null); // safety check that object is actually despawned.
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: f33b2f298cbb7b248b2a76ba48ee1d53
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,77 @@
using System.Collections;
using NUnit.Framework;
using Unity.Netcode.Components;
using UnityEngine;
using UnityEngine.TestTools;
namespace Unity.Netcode.RuntimeTests.Physics
{
public class NetworkRigidbodyDynamicTest : NetworkRigidbodyTestBase
{
public override bool Kinematic => false;
}
public class NetworkRigidbodyKinematicTest : NetworkRigidbodyTestBase
{
public override bool Kinematic => true;
}
public abstract class NetworkRigidbodyTestBase : BaseMultiInstanceTest
{
protected override int NbClients => 1;
public abstract bool Kinematic { get; }
[UnitySetUp]
public override IEnumerator Setup()
{
yield return StartSomeClientsAndServerWithPlayers(true, NbClients, playerPrefab =>
{
playerPrefab.AddComponent<NetworkTransform>();
playerPrefab.AddComponent<Rigidbody>();
playerPrefab.AddComponent<NetworkRigidbody>();
playerPrefab.GetComponent<Rigidbody>().isKinematic = Kinematic;
});
}
/// <summary>
/// Tests that a server can destroy a NetworkObject and that it gets despawned correctly.
/// </summary>
/// <returns></returns>
[UnityTest]
public IEnumerator TestRigidbodyKinematicEnableDisable()
{
// This is the *SERVER VERSION* of the *CLIENT PLAYER*
var serverClientPlayerResult = new MultiInstanceHelpers.CoroutineResultWrapper<NetworkObject>();
yield return MultiInstanceHelpers.Run(MultiInstanceHelpers.GetNetworkObjectByRepresentation((x => x.IsPlayerObject && x.OwnerClientId == m_ClientNetworkManagers[0].LocalClientId), m_ServerNetworkManager, serverClientPlayerResult));
var serverPlayer = serverClientPlayerResult.Result.gameObject;
// This is the *CLIENT VERSION* of the *CLIENT PLAYER*
var clientClientPlayerResult = new MultiInstanceHelpers.CoroutineResultWrapper<NetworkObject>();
yield return MultiInstanceHelpers.Run(MultiInstanceHelpers.GetNetworkObjectByRepresentation((x => x.IsPlayerObject && x.OwnerClientId == m_ClientNetworkManagers[0].LocalClientId), m_ClientNetworkManagers[0], clientClientPlayerResult));
var clientPlayer = clientClientPlayerResult.Result.gameObject;
Assert.IsNotNull(serverPlayer);
Assert.IsNotNull(clientPlayer);
int waitFor = Time.frameCount + 2;
yield return new WaitUntil(() => Time.frameCount >= waitFor);
// server rigidbody has authority and should have a kinematic mode of false
Assert.True(serverPlayer.GetComponent<Rigidbody>().isKinematic == Kinematic);
// client rigidbody has no authority and should have a kinematic mode of true
Assert.True(clientPlayer.GetComponent<Rigidbody>().isKinematic);
// despawn the server player
serverPlayer.GetComponent<NetworkObject>().Despawn(false);
yield return null;
Assert.IsTrue(serverPlayer.GetComponent<Rigidbody>().isKinematic == Kinematic);
yield return null;
Assert.IsTrue(clientPlayer == null); // safety check that object is actually despawned.
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 344ba3f81f24b6d40afb926333fd118d
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,185 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!1 &8301517917652696228
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 8301517917652696222}
- component: {fileID: 8301517917652696225}
- component: {fileID: 8301517917652696224}
- component: {fileID: 8301517917652696227}
- component: {fileID: 8301517917652696226}
- component: {fileID: 8301517917652696229}
- component: {fileID: 8301517917652696223}
- component: {fileID: 8705555767646236361}
- component: {fileID: 4776132987328577834}
m_Layer: 0
m_Name: PhysicsNetworkedSphere
m_TagString: Untagged
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!4 &8301517917652696222
Transform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 0, y: 0.5, z: 0}
m_LocalScale: {x: 1, y: 1, z: 1}
m_Children: []
m_Father: {fileID: 0}
m_RootOrder: 0
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!33 &8301517917652696225
MeshFilter:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Mesh: {fileID: 10207, guid: 0000000000000000e000000000000000, type: 0}
--- !u!23 &8301517917652696224
MeshRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Enabled: 1
m_CastShadows: 1
m_ReceiveShadows: 1
m_DynamicOccludee: 1
m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RayTraceProcedural: 0
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:
- {fileID: 10303, guid: 0000000000000000f000000000000000, type: 0}
m_StaticBatchInfo:
firstSubMesh: 0
subMeshCount: 0
m_StaticBatchRoot: {fileID: 0}
m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0
m_StitchLightmapSeams: 1
m_SelectedEditorRenderState: 3
m_MinimumChartSize: 4
m_AutoUVMaxDistance: 0.5
m_AutoUVMaxAngle: 89
m_LightmapParameters: {fileID: 0}
m_SortingLayerID: 0
m_SortingLayer: 0
m_SortingOrder: 0
m_AdditionalVertexStreams: {fileID: 0}
--- !u!135 &8301517917652696227
SphereCollider:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Material: {fileID: 0}
m_IsTrigger: 0
m_Enabled: 1
serializedVersion: 2
m_Radius: 0.5
m_Center: {x: 0, y: 0, z: 0}
--- !u!54 &8301517917652696226
Rigidbody:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
serializedVersion: 2
m_Mass: 1
m_Drag: 0
m_AngularDrag: 0.05
m_UseGravity: 1
m_IsKinematic: 0
m_Interpolate: 0
m_Constraints: 0
m_CollisionDetection: 0
--- !u!114 &8301517917652696229
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: d5a57f767e5e46a458fc5d3c628d0cbb, type: 3}
m_Name:
m_EditorClassIdentifier:
GlobalObjectIdHash: 951099334
AlwaysReplicateAsRoot: 0
DontDestroyWithOwner: 0
AutoObjectParentSync: 1
--- !u!114 &8301517917652696223
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: e96cb6065543e43c4a752faaa1468eb1, type: 3}
m_Name:
m_EditorClassIdentifier:
SyncPositionX: 1
SyncPositionY: 1
SyncPositionZ: 1
SyncRotAngleX: 1
SyncRotAngleY: 1
SyncRotAngleZ: 1
SyncScaleX: 1
SyncScaleY: 1
SyncScaleZ: 1
PositionThreshold: 0
RotAngleThreshold: 0
ScaleThreshold: 0
InLocalSpace: 0
Interpolate: 1
FixedSendsPerSecond: 30
--- !u!114 &8705555767646236361
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: b310964cc951d7d4a8b6a83cb280fee7, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &4776132987328577834
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8301517917652696228}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: f6c0be61502bb534f922ebb746851216, type: 3}
m_Name:
m_EditorClassIdentifier:

Просмотреть файл

@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 03e5087a1763528448af628c813543fa
PrefabImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,200 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!1 &4079352819444256614
GameObject:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
serializedVersion: 6
m_Component:
- component: {fileID: 4079352819444256611}
- component: {fileID: 4079352819444256610}
- component: {fileID: 4079352819444256613}
- component: {fileID: 4079352819444256612}
- component: {fileID: -3775814466963834669}
- component: {fileID: 1750810845806302260}
- component: {fileID: -6757728931092222887}
- component: {fileID: 4053684789567975459}
- component: {fileID: 3885376173097824340}
- component: {fileID: 1991357795387791033}
m_Layer: 8
m_Name: PhysicsPlayer
m_TagString: Player
m_Icon: {fileID: 0}
m_NavMeshLayer: 0
m_StaticEditorFlags: 0
m_IsActive: 1
--- !u!4 &4079352819444256611
Transform:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_LocalRotation: {x: 0, y: 0, z: 0, w: 1}
m_LocalPosition: {x: 5, y: 0.5, z: 5}
m_LocalScale: {x: 1, y: 1, z: 1}
m_Children: []
m_Father: {fileID: 0}
m_RootOrder: 0
m_LocalEulerAnglesHint: {x: 0, y: 0, z: 0}
--- !u!33 &4079352819444256610
MeshFilter:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Mesh: {fileID: 10202, guid: 0000000000000000e000000000000000, type: 0}
--- !u!23 &4079352819444256613
MeshRenderer:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_CastShadows: 1
m_ReceiveShadows: 1
m_DynamicOccludee: 1
m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
m_RayTracingMode: 2
m_RayTraceProcedural: 0
m_RenderingLayerMask: 1
m_RendererPriority: 0
m_Materials:
- {fileID: 2100000, guid: a7b755ad8e4fe4bdb8f5518c951abc70, type: 2}
m_StaticBatchInfo:
firstSubMesh: 0
subMeshCount: 0
m_StaticBatchRoot: {fileID: 0}
m_ProbeAnchor: {fileID: 0}
m_LightProbeVolumeOverride: {fileID: 0}
m_ScaleInLightmap: 1
m_ReceiveGI: 1
m_PreserveUVs: 0
m_IgnoreNormalsForChartDetection: 0
m_ImportantGI: 0
m_StitchLightmapSeams: 1
m_SelectedEditorRenderState: 3
m_MinimumChartSize: 4
m_AutoUVMaxDistance: 0.5
m_AutoUVMaxAngle: 89
m_LightmapParameters: {fileID: 0}
m_SortingLayerID: 0
m_SortingLayer: 0
m_SortingOrder: 0
m_AdditionalVertexStreams: {fileID: 0}
--- !u!65 &4079352819444256612
BoxCollider:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Material: {fileID: 0}
m_IsTrigger: 0
m_Enabled: 1
serializedVersion: 2
m_Size: {x: 1, y: 1, z: 1}
m_Center: {x: 0, y: 0, z: 0}
--- !u!114 &-3775814466963834669
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: d5a57f767e5e46a458fc5d3c628d0cbb, type: 3}
m_Name:
m_EditorClassIdentifier:
GlobalObjectIdHash: 951099334
AlwaysReplicateAsRoot: 0
DontDestroyWithOwner: 0
AutoObjectParentSync: 1
--- !u!54 &1750810845806302260
Rigidbody:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
serializedVersion: 2
m_Mass: 100
m_Drag: 7
m_AngularDrag: 0.05
m_UseGravity: 1
m_IsKinematic: 0
m_Interpolate: 1
m_Constraints: 112
m_CollisionDetection: 1
--- !u!114 &-6757728931092222887
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: e96cb6065543e43c4a752faaa1468eb1, type: 3}
m_Name:
m_EditorClassIdentifier:
SyncPositionX: 1
SyncPositionY: 1
SyncPositionZ: 1
SyncRotAngleX: 1
SyncRotAngleY: 1
SyncRotAngleZ: 1
SyncScaleX: 1
SyncScaleY: 1
SyncScaleZ: 1
PositionThreshold: 0
RotAngleThreshold: 0
ScaleThreshold: 0
InLocalSpace: 0
Interpolate: 1
FixedSendsPerSecond: 5
--- !u!114 &4053684789567975459
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 24a9235f10bc6456183432fdb3015157, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &3885376173097824340
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 82b41b172a31546ffba450f1418f4e69, type: 3}
m_Name:
m_EditorClassIdentifier:
m_Speed: 5
m_RotSpeed: 2.5
--- !u!114 &1991357795387791033
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: f6c0be61502bb534f922ebb746851216, type: 3}
m_Name:
m_EditorClassIdentifier:

Просмотреть файл

@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 286f65b05cb270345948340b8908b7e2
PrefabImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -18,6 +18,7 @@ GameObject:
- component: {fileID: 4053684789567975459}
- component: {fileID: 6442518961346739709}
- component: {fileID: 2756533617708860847}
- component: {fileID: 5257990644900685376}
m_Layer: 8
m_Name: Player
m_TagString: Player
@ -51,9 +52,20 @@ MonoBehaviour:
m_Script: {fileID: 11500000, guid: e96cb6065543e43c4a752faaa1468eb1, type: 3}
m_Name:
m_EditorClassIdentifier:
Authority: 1
Channel: 0
SyncPositionX: 1
SyncPositionY: 1
SyncPositionZ: 1
SyncRotAngleX: 1
SyncRotAngleY: 1
SyncRotAngleZ: 1
SyncScaleX: 1
SyncScaleY: 1
SyncScaleZ: 1
PositionThreshold: 0
RotAngleThreshold: 0
ScaleThreshold: 0
InLocalSpace: 0
Interpolate: 1
FixedSendsPerSecond: 15
--- !u!114 &-3775814466963834669
MonoBehaviour:
@ -90,7 +102,6 @@ MeshRenderer:
m_CastShadows: 1
m_ReceiveShadows: 1
m_DynamicOccludee: 1
m_StaticShadowCaster: 0
m_MotionVectors: 1
m_LightProbeUsage: 1
m_ReflectionProbeUsage: 1
@ -187,3 +198,15 @@ MonoBehaviour:
m_Name:
m_EditorClassIdentifier:
MoveSpeed: 10
--- !u!114 &5257990644900685376
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 4079352819444256614}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: f6c0be61502bb534f922ebb746851216, type: 3}
m_Name:
m_EditorClassIdentifier:

Просмотреть файл

@ -19,6 +19,7 @@ GameObject:
- component: {fileID: 3809075828520557319}
- component: {fileID: 7138389085065872747}
- component: {fileID: 5715768330125915997}
- component: {fileID: 2744080254494315543}
m_Layer: 0
m_Name: PlayerCube
m_TagString: Target
@ -271,18 +272,6 @@ MonoBehaviour:
m_Name:
m_EditorClassIdentifier:
Range: 10
--- !u!114 &-4978466230159947418
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8685790303553767886}
m_Enabled: 0
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 9548116c10df1486ea12b7329b77c5cf, type: 3}
m_Name:
m_EditorClassIdentifier:
--- !u!114 &5715768330125915997
MonoBehaviour:
m_ObjectHideFlags: 0
@ -295,7 +284,30 @@ MonoBehaviour:
m_Script: {fileID: 11500000, guid: e96cb6065543e43c4a752faaa1468eb1, type: 3}
m_Name:
m_EditorClassIdentifier:
Authority: 1
SyncPositionX: 1
SyncPositionY: 1
SyncPositionZ: 1
SyncRotAngleX: 1
SyncRotAngleY: 1
SyncRotAngleZ: 1
SyncScaleX: 1
SyncScaleY: 1
SyncScaleZ: 1
PositionThreshold: 0
RotAngleThreshold: 0
ScaleThreshold: 0
InLocalSpace: 0
Interpolate: 1
FixedSendsPerSecond: 30
m_PositionInterpolatorFactory: {fileID: 0}
--- !u!114 &2744080254494315543
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 8685790303553767886}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: f6c0be61502bb534f922ebb746851216, type: 3}
m_Name:
m_EditorClassIdentifier:

Просмотреть файл

@ -0,0 +1,19 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!114 &11400000
MonoBehaviour:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_GameObject: {fileID: 0}
m_Enabled: 1
m_EditorHideFlags: 0
m_Script: {fileID: 11500000, guid: 39a16938ffb5cd846a9f6df7a686a9c4, type: 3}
m_Name: PhysicsSample
m_EditorClassIdentifier:
SceneToReference: {fileID: 102900000, guid: 2c76877ad66aa22458c62a0d74514a91, type: 3}
m_IncludedScenes: []
m_DisplayName: Physics Sample
m_ReferencedScenes:
- PhysicsSample

Просмотреть файл

@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 7289196bc52552d458b24c94498df352
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 11400000
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 0c7f77749025f7741b112edaf3004376
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

Разница между файлами не показана из-за своего большого размера Загрузить разницу

Просмотреть файл

@ -0,0 +1,7 @@
fileFormatVersion: 2
guid: 2c76877ad66aa22458c62a0d74514a91
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,63 @@
%YAML 1.1
%TAG !u! tag:unity3d.com,2011:
--- !u!850595691 &4890085278179872738
LightingSettings:
m_ObjectHideFlags: 0
m_CorrespondingSourceObject: {fileID: 0}
m_PrefabInstance: {fileID: 0}
m_PrefabAsset: {fileID: 0}
m_Name: PhysiscSampleLightingSettings
serializedVersion: 3
m_GIWorkflowMode: 0
m_EnableBakedLightmaps: 1
m_EnableRealtimeLightmaps: 0
m_RealtimeEnvironmentLighting: 1
m_BounceScale: 1
m_AlbedoBoost: 1
m_IndirectOutputScale: 1
m_UsingShadowmask: 1
m_BakeBackend: 1
m_LightmapMaxSize: 1024
m_BakeResolution: 40
m_Padding: 2
m_TextureCompression: 1
m_AO: 0
m_AOMaxDistance: 1
m_CompAOExponent: 1
m_CompAOExponentDirect: 0
m_ExtractAO: 0
m_MixedBakeMode: 2
m_LightmapsBakeMode: 1
m_FilterMode: 1
m_LightmapParameters: {fileID: 15204, guid: 0000000000000000f000000000000000, type: 0}
m_ExportTrainingData: 0
m_TrainingDataDestination: TrainingData
m_RealtimeResolution: 2
m_ForceWhiteAlbedo: 0
m_ForceUpdates: 0
m_FinalGather: 0
m_FinalGatherRayCount: 256
m_FinalGatherFiltering: 1
m_PVRCulling: 1
m_PVRSampling: 1
m_PVRDirectSampleCount: 32
m_PVRSampleCount: 512
m_PVREnvironmentSampleCount: 256
m_PVREnvironmentReferencePointCount: 2048
m_LightProbeSampleCountMultiplier: 4
m_PVRBounces: 2
m_PVRMinBounces: 1
m_PVREnvironmentMIS: 1
m_PVRFilteringMode: 1
m_PVRDenoiserTypeDirect: 1
m_PVRDenoiserTypeIndirect: 1
m_PVRDenoiserTypeAO: 1
m_PVRFilterTypeDirect: 0
m_PVRFilterTypeIndirect: 0
m_PVRFilterTypeAO: 0
m_PVRFilteringGaussRadiusDirect: 1
m_PVRFilteringGaussRadiusIndirect: 5
m_PVRFilteringGaussRadiusAO: 2
m_PVRFilteringAtrousPositionSigmaDirect: 0.5
m_PVRFilteringAtrousPositionSigmaIndirect: 2
m_PVRFilteringAtrousPositionSigmaAO: 1

Просмотреть файл

@ -0,0 +1,8 @@
fileFormatVersion: 2
guid: 7b34956cf0a136c4f8438c8ec088925e
NativeFormatImporter:
externalObjects: {}
mainObjectFileID: 4890085278179872738
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -2500,6 +2500,7 @@ MonoBehaviour:
- {fileID: 11400000, guid: 660535b6e155b5b4bbede52313fcb32e, type: 2}
- {fileID: 11400000, guid: d2e34ed37c087154dbd7f89fd463801b, type: 2}
- {fileID: 11400000, guid: 138603ab28f532140b48a57bea0e54b0, type: 2}
- {fileID: 11400000, guid: 7289196bc52552d458b24c94498df352, type: 2}
m_SceneMenusDropDownList: {fileID: 1362704539}
m_OptionsList:
m_Options:

Просмотреть файл

@ -0,0 +1,25 @@
using UnityEngine;
[RequireComponent(typeof(LineRenderer))]
public class DrawRay : MonoBehaviour
{
private LineRenderer m_LineRenderer;
private void Awake()
{
m_LineRenderer = GetComponent<LineRenderer>();
m_LineRenderer.SetPosition(0, transform.position);
}
private void FixedUpdate()
{
if (Physics.Raycast(new Ray(transform.position, transform.forward * 10), out RaycastHit hit, 10, Physics.DefaultRaycastLayers))
{
m_LineRenderer.SetPosition(1, hit.point);
}
else
{
m_LineRenderer.SetPosition(1, transform.position + transform.forward * 10);
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 0c2b2d2a037a80c4e914906666f7e9be
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,33 @@
using System.Collections;
using UnityEngine;
public class OnCollisionColor : MonoBehaviour
{
private int m_CollisionCount;
public void OnCollisionEnter(Collision other)
{
m_CollisionCount++;
HandleCollisionCountChanged();
StartCoroutine(StayColored());
}
private void HandleCollisionCountChanged()
{
if (m_CollisionCount > 0)
{
GetComponent<Renderer>().material.color = Color.red;
}
else
{
GetComponent<Renderer>().material.color = Color.white;
}
}
private IEnumerator StayColored()
{
yield return new WaitForSeconds(0.2f);
m_CollisionCount--;
HandleCollisionCountChanged();
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: b310964cc951d7d4a8b6a83cb280fee7
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -8,28 +8,17 @@ public class PlayerMovement : NetworkBehaviour
private float m_Speed = 20.0f;
[SerializeField]
private float m_RotSpeed = 5.0f;
private Rigidbody m_Rigidbody;
public static Dictionary<ulong, PlayerMovement> Players = new Dictionary<ulong, PlayerMovement>();
private void Start()
{
m_Rigidbody = GetComponent<Rigidbody>();
if (IsLocalPlayer)
{
var temp = transform.position;
temp.y = 0.5f;
transform.position = temp;
}
if (m_Rigidbody)
{
// Only the owner should ever move an object
// If we don't set the non-local-player object as kinematic,
// the local physics would apply and result in unwanted position
// updates being sent up
m_Rigidbody.isKinematic = !IsLocalPlayer;
}
}
public override void OnNetworkSpawn()

Просмотреть файл

@ -0,0 +1,38 @@
using System.Collections;
using Unity.Netcode;
using UnityEngine;
public class Spawner : MonoBehaviour
{
public GameObject Prefab;
public float Frequency;
private void OnServerStarted()
{
StartCoroutine(SpawnRoutine());
}
private IEnumerator SpawnRoutine()
{
while (true)
{
yield return new WaitForSeconds(Frequency);
var go = Instantiate(Prefab, transform.position, Quaternion.identity);
var networkObject = go.GetComponent<NetworkObject>();
networkObject.Spawn();
}
}
private void Start()
{
NetworkManager.Singleton.OnServerStarted += OnServerStarted;
}
private void OnDestroy()
{
if (NetworkManager.Singleton != null)
{
NetworkManager.Singleton.OnServerStarted -= OnServerStarted;
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 73d0710f702ebbf4b9e70d41c06e7678
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -0,0 +1,28 @@
using UnityEngine;
public class TriggerColorChanger : MonoBehaviour
{
private Material m_Material;
private int m_ActiveTriggerCount;
private void Start()
{
m_Material = GetComponent<Renderer>().material;
}
private void OnTriggerEnter(Collider other)
{
m_Material.color = Color.green;
m_ActiveTriggerCount++;
}
private void OnTriggerExit(Collider other)
{
m_ActiveTriggerCount--;
if (m_ActiveTriggerCount == 0)
{
m_Material.color = Color.white;
}
}
}

Просмотреть файл

@ -0,0 +1,11 @@
fileFormatVersion: 2
guid: 08cb6173d0006264f829ee44732d3d08
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

Просмотреть файл

@ -12,24 +12,12 @@ namespace TestProject.ManualTests
private RandomMovement m_RandomMovement;
private Rigidbody m_Rigidbody;
// Start is called before the first frame update
private void Start()
{
m_RandomMovement = GetComponent<RandomMovement>();
}
public override void OnNetworkSpawn()
{
m_Rigidbody = GetComponent<Rigidbody>();
if (m_Rigidbody != null)
{
m_Rigidbody.isKinematic = !NetworkObject.NetworkManager.IsServer;
}
}
private void Update()
{
if (NetworkObject != null)