void OnEnable() { // create list of edges: var mf = GetComponent <MeshFilter>(); { var mesh = mf.sharedMesh; _vertices = new NativeArray <Vector3>(mesh.vertices, Allocator.Persistent); var triangles = new NativeArray <int>(mesh.triangles, Allocator.TempJob); var job = new ToEdgesJob { Triangles = triangles.AsReadOnly(), Results = new NativeList <int2>(initialCapacity: triangles.Length * 3, Allocator.Persistent) }; job.Run(); _edges = job.Results.ToArray(Allocator.Persistent); job.Results.Dispose(); triangles.Dispose(); } // create segment buffer: Segments.Core.CreateBatch(out _segments, _materialOverride); // initialize buffer size: _segments.buffer.Length = _edges.Length; }
private void InitAudioVisualizer() { totalTriangles = (int)sampleMesh.GetIndexCount(0) / 3; audioProfile.bandSize = totalTriangles; audioProcessor = new AudioProcessor(ref audioSource, ref audioProfile); MeshUtil.DeepCopyMesh(ref sampleMesh, out modifiedSampleMesh); audioVFX.SetMesh(VFXPropertyId.mesh_sampleMesh, modifiedSampleMesh); audioVFX.SetInt(VFXPropertyId.int_triangleCount, totalTriangles); modifiedSampleMesh.MarkDynamic(); meshFilter.mesh = modifiedSampleMesh; // transferring mesh data to native arrays to be processed parallely Mesh.MeshDataArray sampleMeshData = Mesh.AcquireReadOnlyMeshData(sampleMesh); normals = MeshUtil.NativeGetNormals(sampleMeshData[0], Allocator.Persistent); normals.AsReadOnly(); triangles = MeshUtil.NativeGetIndices(sampleMeshData[0], Allocator.Persistent); triangles.AsReadOnly(); vertices = MeshUtil.NativeGetVertices(sampleMeshData[0], Allocator.Persistent); // audio processing attributes samples = new NativeArray <float>(audioProfile.sampleSize, Allocator.Persistent); bandDistribution = new NativeArray <int>(audioProfile.bandSize + 1, Allocator.Persistent); bandDistribution.CopyFrom(audioProcessor.bandDistribution); bandDistribution.AsReadOnly(); prevBands = new NativeArray <float>(totalTriangles, Allocator.Persistent); prevBands.CopyFrom(prevBands); bandVelocities = new NativeArray <float>(totalTriangles, Allocator.Persistent); bandVelocities.CopyFrom(bandVelocities); sampleMeshData.Dispose(); if (seed != 0) { // if randomized is turned on int[] seqArray = MathUtil.GenerateSeqArray(totalTriangles); MathUtil.ShuffleArray <int>(ref seqArray, seed); // triangle indices NativeArray <int> trianglesCopy = new NativeArray <int>(triangles, Allocator.Temp); for (int s = 0; s < seqArray.Length; s++) { triangles[s * 3] = trianglesCopy[seqArray[s] * 3]; triangles[s * 3 + 1] = trianglesCopy[seqArray[s] * 3 + 1]; triangles[s * 3 + 2] = trianglesCopy[seqArray[s] * 3 + 2]; } trianglesCopy.Dispose(); } }
//[BurstCompile] //[RequireComponentTag(typeof(MoveForward))] //struct MoveForwardRotation : IJobForEach<Translation, Rotation, MoveSpeed> //{ // public float dt; // public void Execute(ref Translation pos, [ReadOnly] ref Rotation rot, [ReadOnly] ref MoveSpeed speed) // { // pos.Value = pos.Value + (dt * speed.Value * math.forward(rot.Value)); // } //} protected override void OnUpdate() { NativeArray <Translation> _boidsPosition = boidPositionQuery.ToComponentDataArray <Translation>(Allocator.TempJob); var boidsPosition = _boidsPosition.AsReadOnly(); var _boidsDirection = boidDirectionQuery.ToComponentDataArray <Direction>(Allocator.TempJob); var boidsDirection = _boidsDirection.AsReadOnly(); var dt = Time.DeltaTime; var separationDistance = 4f; var coherenceDistance = 25f; var aignmentDistance = 12f; var jobHandle = Entities.WithAll <BoidTag>().WithBurst().ForEach((ref Direction direction, in Translation pos) => { float3 coherence = 0, separation = 0, aignment = 0; int coherenceCounter = 0, separationCounter = 0, aligmentCounter = 0; for (int i = 0; i < boidsPosition.Length; i++) { var other = boidsPosition[i]; var toOtherDirection = math.normalize(other.Value - pos.Value); var distance = math.length(pos.Value - other.Value); if (distance <= math.EPSILON) { continue; } if (distance < separationDistance) { separation -= toOtherDirection; separationCounter += 1; } else if (distance < coherenceDistance) { coherence += toOtherDirection; coherenceCounter += 1; } if (distance < aignmentDistance && math.dot(toOtherDirection, direction.Value) > 0.7) { aignment += boidsDirection[i].Value; aligmentCounter += 1; } } coherence = (coherence) / math.max(1, coherenceCounter); separation = (separation) / math.max(1, separationCounter); aignment = (aignment) / math.max(1, aligmentCounter); direction.Value = math.normalize(11 * direction.Value + 1.2f * (separation) + 0.5f * (coherence) + 0.9f * (aignment)); //pos.Value = pos.Value + (dt * 1 * direction.Value); }).ScheduleParallel(this.Dependency); //return moveForwardRotationJob.Schedule(this, inputDeps); var boidsHandle = _boidsPosition.Dispose(jobHandle); var secondHandle = _boidsDirection.Dispose(jobHandle); this.Dependency = JobHandle.CombineDependencies(boidsHandle, secondHandle); }
public IEnumerator SendAndReceiveMessageWithExecuteTasks() { var test = new MonoBehaviourTest <SignalingPeers>(); var label = "test"; RTCDataChannel channel1 = test.component.CreateDataChannel(0, label); Assert.That(channel1, Is.Not.Null); yield return(test); var op1 = new WaitUntilWithTimeout(() => test.component.GetDataChannelList(1).Count > 0, 5000); yield return(op1); RTCDataChannel channel2 = test.component.GetDataChannelList(1)[0]; Assert.That(channel2, Is.Not.Null); Assert.That(channel1.ReadyState, Is.EqualTo(RTCDataChannelState.Open)); Assert.That(channel2.ReadyState, Is.EqualTo(RTCDataChannelState.Open)); Assert.That(channel1.Label, Is.EqualTo(channel2.Label)); Assert.That(channel1.Id, Is.EqualTo(channel2.Id)); // send string const int millisecondTimeout = 5000; const string message1 = "hello"; string message2 = null; channel2.OnMessage = bytes => { message2 = System.Text.Encoding.UTF8.GetString(bytes); }; channel1.Send(message1); ExecutePendingTasksWithTimeout(ref message2, millisecondTimeout); Assert.That(message1, Is.EqualTo(message2)); // send byte array byte[] message3 = { 1, 2, 3 }; byte[] message4 = null; channel2.OnMessage = bytes => { message4 = bytes; }; channel1.Send(message3); ExecutePendingTasksWithTimeout(ref message4, millisecondTimeout); Assert.That(message3, Is.EqualTo(message4)); // Native Collections Tests Vector3[] structData = { Vector3.one, Vector3.zero, Vector3.up, Vector3.down }; using (var nativeArray = new NativeArray <Vector3>(structData, Allocator.Temp)) { var nativeArrayTestMessageReceiver = default(byte[]); channel2.OnMessage = bytes => { nativeArrayTestMessageReceiver = bytes; }; // Native Array var message5 = nativeArray; Assert.That(message5.IsCreated, Is.True); nativeArrayTestMessageReceiver = null; channel1.Send(message5); ExecutePendingTasksWithTimeout(ref nativeArrayTestMessageReceiver, millisecondTimeout); Assert.That(NativeArrayMemCmp(message5, nativeArrayTestMessageReceiver), Is.True, "Elements of the received message are not the same as the original message."); // Native Slice var message6 = nativeArray.Slice(); nativeArrayTestMessageReceiver = null; channel1.Send(message6); ExecutePendingTasksWithTimeout(ref nativeArrayTestMessageReceiver, millisecondTimeout); Assert.That(NativeArrayMemCmp(message6, nativeArrayTestMessageReceiver), Is.True, "Elements of the received message are not the same as the original message."); #if UNITY_2021_1_OR_NEWER // NativeArray.ReadOnly var message7 = nativeArray.AsReadOnly(); nativeArrayTestMessageReceiver = null; channel1.Send(message7); ExecutePendingTasksWithTimeout(ref nativeArrayTestMessageReceiver, millisecondTimeout); Assert.That(NativeArrayMemCmp(message7, nativeArrayTestMessageReceiver), Is.True, "Elements of the received message are not the same as the original message."); #endif // UNITY_2021_1_OR_NEWER } test.component.Dispose(); Object.DestroyImmediate(test.gameObject); }
public IEnumerator SendAndReceiveMessage() { var test = new MonoBehaviourTest <SignalingPeers>(); var label = "test"; RTCDataChannel channel1 = test.component.CreateDataChannel(0, label); Assert.That(channel1, Is.Not.Null); yield return(test); var op1 = new WaitUntilWithTimeout(() => test.component.GetDataChannelList(1).Count > 0, 5000); yield return(op1); RTCDataChannel channel2 = test.component.GetDataChannelList(1)[0]; Assert.That(channel2, Is.Not.Null); Assert.That(channel1.ReadyState, Is.EqualTo(RTCDataChannelState.Open)); Assert.That(channel2.ReadyState, Is.EqualTo(RTCDataChannelState.Open)); Assert.That(channel1.Label, Is.EqualTo(channel2.Label)); Assert.That(channel1.Id, Is.EqualTo(channel2.Id)); // send string const string message1 = "hello"; string message2 = null; channel2.OnMessage = bytes => { message2 = System.Text.Encoding.UTF8.GetString(bytes); }; channel1.Send(message1); var op10 = new WaitUntilWithTimeout(() => !string.IsNullOrEmpty(message2), 5000); yield return(op10); Assert.That(op10.IsCompleted, Is.True); Assert.That(message1, Is.EqualTo(message2)); // send byte array byte[] message3 = { 1, 2, 3 }; byte[] message4 = null; channel2.OnMessage = bytes => { message4 = bytes; }; channel1.Send(message3); var op11 = new WaitUntilWithTimeout(() => message4 != null, 5000); yield return(op11); Assert.That(op11.IsCompleted, Is.True); Assert.That(message3, Is.EqualTo(message4)); // Native Array // Native Arrays that are declared in tests that use IEnumerator seem to have some oddities about them // they tend to dispose themselves on yields so we recreate the array as needed. byte[] comparisonBuffer = { 1, 2, 3 }; var nativeArrayTestMessageReceiver = default(byte[]); using (var message5 = new NativeArray <byte>(comparisonBuffer, Allocator.Temp)) { Assert.That(message5.IsCreated, Is.True); // Only needs to be set once as it will be reused. channel2.OnMessage = bytes => { nativeArrayTestMessageReceiver = bytes; }; channel1.Send(message5); } var op12 = new WaitUntilWithTimeout(() => nativeArrayTestMessageReceiver != null, 5000); yield return(op12); Assert.That(op12.IsCompleted, Is.True); Assert.That(comparisonBuffer, Is.EqualTo(nativeArrayTestMessageReceiver)); // Native Slice using (var nativeArray = new NativeArray <byte>(comparisonBuffer, Allocator.Temp)) { Assert.That(nativeArray.IsCreated, Is.True); var message6 = nativeArray.Slice(); nativeArrayTestMessageReceiver = null; channel1.Send(message6); } var op13 = new WaitUntilWithTimeout(() => nativeArrayTestMessageReceiver != null, 5000); yield return(op13); Assert.That(op13.IsCompleted, Is.True); Assert.That(comparisonBuffer, Is.EqualTo(nativeArrayTestMessageReceiver)); #if UNITY_2021_1_OR_NEWER // NativeArray.ReadOnly using (var nativeArray = new NativeArray <byte>(comparisonBuffer, Allocator.Temp)) { Assert.That(nativeArray.IsCreated, Is.True); var message7 = nativeArray.AsReadOnly(); nativeArrayTestMessageReceiver = null; channel1.Send(message7); } var op14 = new WaitUntilWithTimeout(() => nativeArrayTestMessageReceiver != null, 5000); yield return(op14); Assert.That(op14.IsCompleted, Is.True); Assert.That(comparisonBuffer, Is.EqualTo(nativeArrayTestMessageReceiver)); #endif // UNITY_2020_1_OR_NEWER test.component.Dispose(); Object.DestroyImmediate(test.gameObject); }
public static NativeArray <InterpolationSetup> .ReadOnly GetSetups() { return(_interpolationSetups.AsReadOnly()); }
public static void UpdateProperties(ChiselModel model, ChiselColliderObjects[] colliders) { if (colliders == null) { return; } var colliderSettings = model.ColliderSettings; for (int i = 0; i < colliders.Length; i++) { var meshCollider = colliders[i].meshCollider; if (!meshCollider) { continue; } // If the cookingOptions are not the default values it would force a full slow rebake later, // even if we already did a Bake in a job //if (meshCollider.cookingOptions != colliderSettings.cookingOptions) // meshCollider.cookingOptions = colliderSettings.cookingOptions; if (meshCollider.convex != colliderSettings.convex) { meshCollider.convex = colliderSettings.convex; } if (meshCollider.isTrigger != colliderSettings.isTrigger) { meshCollider.isTrigger = colliderSettings.isTrigger; } var sharedMesh = colliders[i].sharedMesh; var expectedEnabled = sharedMesh.vertexCount > 0; if (meshCollider.enabled != expectedEnabled) { meshCollider.enabled = expectedEnabled; } } // TODO: find all the instanceIDs before we start doing CSG, then we can do the Bake's in the same job that sets the meshes // hopefully that will make it easier for Unity to not screw up the scheduling var bakingSettings = new NativeArray <BakeData>(colliders.Length, Allocator.TempJob); for (int i = 0; i < colliders.Length; i++) { var meshCollider = colliders[i].meshCollider; if (!meshCollider) { bakingSettings[i] = new BakeData { instanceID = 0 }; continue; } var sharedMesh = colliders[i].sharedMesh; bakingSettings[i] = new BakeData { convex = colliderSettings.convex, instanceID = sharedMesh.GetInstanceID() }; } var bakeColliderJob = new BakeColliderJob { bakingSettings = bakingSettings.AsReadOnly() }; // WHY ARE ALL OF THESE JOBS SEQUENTIAL ON THE SAME WORKER THREAD? var jobHandle = bakeColliderJob.Schedule(colliders.Length, 1); jobHandle.Complete(); bakingSettings.Dispose(jobHandle); // TODO: is there a way to defer forcing the collider to update? for (int i = 0; i < colliders.Length; i++) { var meshCollider = colliders[i].meshCollider; if (!meshCollider) { continue; } meshCollider.sharedMesh = colliders[i].sharedMesh; } }