public void TestCreateDestroyContainerWithDevice() { Flex.InitDesc desc = new Flex.InitDesc { deviceIndex = -1, enableExtensions = false, #if FLEX_CUDA computeType = Flex.ComputeType.CUDA, #else computeType = Flex.ComputeType.D3D11, #endif renderContext = default(IntPtr), renderDevice = default(IntPtr) }; Flex.Library lib = Flex.Init(Flex.FLEX_VERSION, ErrorCallback, ref desc); Flex.SolverDesc slvDsc = default(Flex.SolverDesc); Flex.SetSolverDescDefaults(ref slvDsc); slvDsc.maxParticles = 1000; Flex.Solver solver = Flex.CreateSolver(lib, ref slvDsc); FlexExt.Container container = FlexExt.CreateContainer(lib, solver, 10000); FlexExt.DestroyContainer(container); Flex.DestroySolver(solver); Flex.Shutdown(lib); }
void BuildFromMesh() { if (m_boundaryMesh) { Vector3[] vertices = m_boundaryMesh.vertices; if (vertices != null && vertices.Length > 0) { for (int i = 0; i < vertices.Length; ++i) { Vector3 v = vertices[i]; vertices[i] = new Vector3(v.x * m_meshLocalScale.x, v.y * m_meshLocalScale.y, v.z * m_meshLocalScale.z); } int[] indices = m_boundaryMesh.triangles; if (indices != null && indices.Length > 0) { FlexExt.Asset.Handle assetHandle = FlexExt.CreateRigidFromMesh(ref vertices[0], vertices.Length, ref indices[0], indices.Length, m_particleSpacing, m_meshExpansion); if (assetHandle) { FlexExt.Asset asset = assetHandle.asset; FlexExt.Asset particlesOnly = new FlexExt.Asset(); particlesOnly.numParticles = asset.numParticles; particlesOnly.maxParticles = asset.numParticles; particlesOnly.particles = asset.particles; StoreAsset(particlesOnly); FlexExt.DestroyAsset(assetHandle); } } } } }
public void TestCreateDestroyInstance() { Flex.Library lib = Flex.Init(Flex.FLEX_VERSION, ErrorCallback); Flex.SolverDesc slvDsc = default(Flex.SolverDesc); Flex.SetSolverDescDefaults(ref slvDsc); slvDsc.maxParticles = 1000; Flex.Solver solver = Flex.CreateSolver(lib, ref slvDsc); FlexExt.Container container = FlexExt.CreateContainer(lib, solver, 1000); FlexExt.Asset.Handle asset = CreateTestClothAsset(); FlexExt.ParticleData data = FlexExt.MapParticleData(container); Matrix4x4 transform = Matrix4x4.identity; FlexExt.Instance.Handle instance = FlexExt.CreateInstance(container, ref data, asset, ref transform, 1.0f, 1.0f, 1.0f, Flex.MakePhase(1, Flex.Phase.Default), 1.0f); Assert.AreEqual(asset.asset.numParticles, instance.instance.numParticles); FlexExt.DestroyInstance(container, instance); FlexExt.UnmapParticleData(container); FlexExt.DestroyAsset(asset); FlexExt.DestroyContainer(container); Flex.DestroySolver(solver); Flex.Shutdown(lib); }
public void TestTearClothMesh() { Vector4[] particles = { new Vector4(1, 1, 0), new Vector4(0, 1, 0), new Vector4(-1, 1, 0), new Vector4(1, 0, 0), new Vector4(0, 0, 0), new Vector4(-1, 0, 0), new Vector4(1, -1, 0), new Vector4(0, -1, 0), new Vector4(-1, -1, 0) }; int[] indices = { 0, 1, 4, 0, 4, 3, 1, 2, 5, 1, 5, 4, 3, 4, 7, 3, 7, 6, 4, 5, 8, 4, 8, 7 }; float stretchStiffness = 1.0f; float bendStiffness = 1.0f; float pressure = 0.0f; FlexExt.Asset.Handle handle = FlexExt.CreateTearingClothFromMesh(ref particles[0], particles.Length, particles.Length * 2, ref indices[0], indices.Length / 3, stretchStiffness, bendStiffness, pressure); float maxStrain = 0.0f; int maxSplits = 10; FlexExt.TearingParticleClone[] particlesCopies = new FlexExt.TearingParticleClone[10]; int numParticlesCopies = 0; int maxCopies = 10; FlexExt.TearingMeshEdit[] triangleEdits = new FlexExt.TearingMeshEdit[10]; int numTriangleEdits = 0; int maxEdits = 10; FlexExt.TearClothMesh(handle, maxStrain, maxSplits, ref particlesCopies[0], ref numParticlesCopies, maxCopies, ref triangleEdits[0], ref numTriangleEdits, maxEdits); // todo: make the mesh tear FlexExt.DestroyTearingCloth(handle); }
public FlexExt.Instance.Handle CreateInstance(FlexExt.Asset.Handle _assetHandle, Matrix4x4 _location, Vector3 _velocity, int _phase, float _massScale) { FlexExt.ParticleData particleData = FlexExt.MapParticleData(m_containerHandle); FlexExt.Instance.Handle instanceHandle = FlexExt.CreateInstance(m_containerHandle, ref particleData, _assetHandle, ref _location, _velocity.x, _velocity.y, _velocity.z, _phase, 1.0f / _massScale); UpdateBuffer(particleData); FlexExt.UnmapParticleData(m_containerHandle); return(instanceHandle); }
public void TestCreateWeldedMeshIndices() { Vector3[] tetra = { new Vector3(1, 1, 1), new Vector3(-1, -1, 1), new Vector3(-1, 1, -1), new Vector3(1, -1, -1) }; Vector3[] vertices = { tetra[0], tetra[1], tetra[2], tetra[0], tetra[3], tetra[1], tetra[0], tetra[2], tetra[3], tetra[1], tetra[3], tetra[2] }; int[] uniqueVerts = new int[vertices.Length]; int[] originalToUniqueMap = new int[vertices.Length]; float threshold = 0.001f; int numUniqueVerts = FlexExt.CreateWeldedMeshIndices(ref vertices[0], vertices.Length, ref uniqueVerts[0], ref originalToUniqueMap[0], threshold); Assert.AreEqual(tetra.Length, numUniqueVerts); }
void BuildFromMesh() { if (m_boundaryMesh) { Vector3[] vertices = m_boundaryMesh.vertices; if (vertices != null && vertices.Length > 0) { for (int i = 0; i < vertices.Length; ++i) { Vector3 v = vertices[i]; vertices[i] = new Vector3(v.x * m_meshLocalScale.x, v.y * m_meshLocalScale.y, v.z * m_meshLocalScale.z); } int[] indices = m_boundaryMesh.triangles; if (indices != null && indices.Length > 0) { FlexExt.Asset.Handle assetHandle = FlexExt.CreateSoftFromMesh(ref vertices[0], vertices.Length, ref indices[0], indices.Length, m_particleSpacing, m_volumeSampling, m_surfaceSampling, m_clusterSpacing, m_clusterRadius, m_clusterStiffness, m_linkRadius, m_linkStiffness); if (assetHandle) { StoreAsset(assetHandle.asset); FlexExt.DestroyAsset(assetHandle); foreach (var i in fixedParticles) { if (i < particles.Length) { particles[i].w = 0.0f; } } m_referenceShape = -1; if (fixedParticles.Length == 0) { float minDist2 = float.MaxValue; Vector3 center = m_boundaryMesh.bounds.center; //Debug.Log(" center of asset bounds: " + center); for (int i = 0; i < shapeCenters.Length; ++i) { float dist2 = (shapeCenters[i] - center).sqrMagnitude; if (dist2 < minDist2) { minDist2 = dist2; m_referenceShape = i; } } } } } } } }
public void TestCreateDestroyContainer() { Flex.Library lib = Flex.Init(Flex.FLEX_VERSION, ErrorCallback); Flex.SolverDesc slvDsc = default(Flex.SolverDesc); Flex.SetSolverDescDefaults(ref slvDsc); slvDsc.maxParticles = 1000; Flex.Solver solver = Flex.CreateSolver(lib, ref slvDsc); FlexExt.Container container = FlexExt.CreateContainer(lib, solver, 10000); FlexExt.DestroyContainer(container); Flex.DestroySolver(solver); Flex.Shutdown(lib); }
static FlexExt.Asset.Handle CreateTestClothAsset() { Vector4[] particles = { new Vector4(1, 1, 0), new Vector4(0, 1, 0), new Vector4(-1, 1, 0), new Vector4(1, 0, 0), new Vector4(0, 0, 0), new Vector4(-1, 0, 0), new Vector4(1, -1, 0), new Vector4(0, -1, 0), new Vector4(-1, -1, 0) }; int[] indices = { 0, 1, 4, 0, 4, 3, 1, 2, 5, 1, 5, 4, 3, 4, 7, 3, 7, 6, 4, 5, 8, 4, 8, 7 }; float stretchStiffness = 1.0f; float bendStiffness = 1.0f; float tetherStiffness = 1.0f; float tetherGive = 1.0f; float pressure = 0.0f; return(FlexExt.CreateClothFromMesh(ref particles[0], particles.Length, ref indices[0], indices.Length / 3, stretchStiffness, bendStiffness, tetherStiffness, tetherGive, pressure)); }
public void TestCreateRigidFromMesh() { Vector3[] vertices = { new Vector3(1, 1, 1), new Vector3(-1, -1, 1), new Vector3(-1, 1, -1), new Vector3(1, -1, -1) }; int[] indices = { 0, 1, 2, 0, 3, 1, 0, 2, 3, 1, 3, 2 }; float radius = 0.1f; float expand = 0.0f; FlexExt.Asset.Handle handle = FlexExt.CreateRigidFromMesh(ref vertices[0], vertices.Length, ref indices[0], indices.Length, radius, expand); FlexExt.Asset asset = handle.asset; Assert.AreEqual(2680, asset.numParticles); Assert.AreEqual(1, asset.numShapes); FlexExt.DestroyAsset(handle); }
public void TestCreateSoftMeshSkinning() { Vector3[] vertices = { new Vector3(1, 1, 1), new Vector3(-1, -1, 1), new Vector3(-1, 1, -1), new Vector3(1, -1, -1) }; Vector3[] bones = { new Vector3(0, 0, 1), new Vector3(0, 0, 0), new Vector3(0, 0, -1) }; float falloff = 1.0f; float maxDistance = 2.5f; float[] skinningWeights = new float[vertices.Length * 4]; int[] skinningIndices = new int[vertices.Length * 4]; FlexExt.CreateSoftMeshSkinning(ref vertices[0], vertices.Length, ref bones[0], bones.Length, falloff, maxDistance, ref skinningWeights[0], ref skinningIndices[0]); Assert.AreEqual(0, skinningIndices[0]); Assert.AreEqual(1, skinningIndices[1]); Assert.AreEqual(2, skinningIndices[2]); Assert.AreEqual(-1, skinningIndices[3]); Assert.AreEqual(1.0f, skinningWeights[0] + skinningWeights[1] + skinningWeights[2] + skinningWeights[3]); }
public void TestCreateTearingClothFromMesh() { Vector4[] particles = { new Vector4(1, 1, 0, 1), new Vector4(0, 1, 0, 1), new Vector4(-1, 1, 0, 1), new Vector4(1, 0, 0, 1), new Vector4(0, 0, 0, 1), new Vector4(-1, 0, 0, 1), new Vector4(1, -1, 0, 1), new Vector4(0, -1, 0, 1), new Vector4(-1, -1, 0, 1) }; int[] indices = { 0, 1, 4, 0, 4, 3, 1, 2, 5, 1, 5, 4, 3, 4, 7, 3, 7, 6, 4, 5, 8, 4, 8, 7 }; float stretchStiffness = 1.0f; float bendStiffness = 1.0f; float pressure = 0.0f; FlexExt.Asset.Handle handle = FlexExt.CreateTearingClothFromMesh(ref particles[0], particles.Length, particles.Length * 2, ref indices[0], indices.Length / 3, stretchStiffness, bendStiffness, pressure); FlexExt.Asset asset = handle.asset; Assert.AreEqual(particles.Length, asset.numParticles); Assert.AreEqual(indices.Length / 3, asset.numTriangles); FlexExt.DestroyTearingCloth(handle); }
void BuildSkinningInfo() { if (m_actor && m_actor.asset && m_renderer && m_renderer.sharedMesh) { Vector3[] vertices = m_renderer.sharedMesh.vertices; Transform actorTransform = m_actor.transform; Transform rendererTransform = m_renderer.transform; Vector3[] shapeCenters = (Vector3[])m_actor.asset.shapeCenters.Clone(); for (int i = 0; i < shapeCenters.Length; ++i) { shapeCenters[i] = rendererTransform.InverseTransformPoint(actorTransform.TransformPoint(shapeCenters[i])); } Quaternion shapeRotation = Quaternion.Inverse(rendererTransform.rotation) * actorTransform.rotation; m_bindposes = new Matrix4x4[shapeCenters.Length]; for (int i = 0; i < shapeCenters.Length; ++i) { m_bindposes[i] = Matrix4x4.TRS(shapeCenters[i], shapeRotation, Vector3.one).inverse; } float[] skinningWeights = new float[vertices.Length * 4]; int[] skinningIndices = new int[vertices.Length * 4]; FlexExt.CreateSoftMeshSkinning(ref vertices[0], vertices.Length, ref shapeCenters[0], shapeCenters.Length, m_skinningFalloff, m_skinningMaxDistance, ref skinningWeights[0], ref skinningIndices[0]); m_boneWeights = new BoneWeight[vertices.Length]; for (int i = 0; i < vertices.Length; ++i) { BoneWeight w = new BoneWeight(); w.boneIndex0 = skinningIndices[i * 4 + 0]; w.boneIndex1 = skinningIndices[i * 4 + 1]; w.boneIndex2 = skinningIndices[i * 4 + 2]; w.boneIndex3 = skinningIndices[i * 4 + 3]; w.weight0 = skinningWeights[i * 4 + 0]; w.weight1 = skinningWeights[i * 4 + 1]; w.weight2 = skinningWeights[i * 4 + 2]; w.weight3 = skinningWeights[i * 4 + 3]; m_boneWeights[i] = w; } } }
public void TestLockUnlockShapeData() { Flex.Library lib = Flex.Init(Flex.FLEX_VERSION, ErrorCallback); Flex.SolverDesc slvDsc = default(Flex.SolverDesc); Flex.SetSolverDescDefaults(ref slvDsc); slvDsc.maxParticles = 1000; Flex.Solver solver = Flex.CreateSolver(lib, ref slvDsc); FlexExt.Container container = FlexExt.CreateContainer(lib, solver, 1000); FlexExt.ShapeData data = FlexExt.MapShapeData(container); Assert.AreNotEqual(IntPtr.Zero, data.positions); FlexExt.UnmapShapeData(container); FlexExt.DestroyContainer(container); Flex.DestroySolver(solver); Flex.Shutdown(lib); }
void BuildFromMesh() { if (m_referenceMesh) { Vector3[] vertices = m_referenceMesh.vertices; int[] triangles = m_referenceMesh.triangles; if (vertices != null && vertices.Length > 0 && triangles != null && triangles.Length > 0) { Tesselation(ref vertices, ref triangles, m_meshTesselation); int[] uniqueVerts = new int[vertices.Length]; int[] originalToUniqueMap = new int[vertices.Length]; int particleCount = FlexExt.CreateWeldedMeshIndices(ref vertices[0], vertices.Length, ref uniqueVerts[0], ref originalToUniqueMap[0], m_weldingThreshold); Vector4[] particles = new Vector4[particleCount]; for (int i = 0; i < particleCount; ++i) { Vector3 v = vertices[uniqueVerts[i]]; particles[i] = new Vector4(v.x * m_meshLocalScale.x, v.y * m_meshLocalScale.y, v.z * m_meshLocalScale.z, 1.0f); } foreach (var i in fixedParticles) { if (i < particleCount) { particles[i].w = 0.0f; } } int indexCount = triangles.Length; int[] indices = new int[indexCount]; for (int i = 0; i < indexCount; ++i) { indices[i] = originalToUniqueMap[triangles[i]]; } FlexExt.Asset.Handle assetHandle = FlexExt.CreateClothFromMesh(ref particles[0], particles.Length, ref indices[0], indices.Length / 3, m_stretchStiffness, m_bendStiffness, m_tetherStiffness, m_tetherGive, m_pressure); if (assetHandle) { StoreAsset(assetHandle.asset); FlexExt.DestroyAsset(assetHandle); } } } }
public void TestCreateSoftFromMesh() { Vector3[] vertices = { new Vector3(1, 1, 1), new Vector3(-1, -1, 1), new Vector3(-1, 1, -1), new Vector3(1, -1, -1) }; int[] indices = { 0, 1, 2, 0, 3, 1, 0, 2, 3, 1, 3, 2 }; float particleSpacing = 0.1f; float volumeSampling = 0.1f; float surfaceSampling = 0.1f; float clusterSpacing = 0.1f; float clusterRadius = 0.3f; float clusterStiffness = 0.5f; float linkRadius = 0.2f; float linkStiffness = 0.5f; FlexExt.Asset.Handle handle = FlexExt.CreateSoftFromMesh(ref vertices[0], vertices.Length, ref indices[0], indices.Length, particleSpacing, volumeSampling, surfaceSampling, clusterSpacing, clusterRadius, clusterStiffness, linkRadius, linkStiffness); FlexExt.Asset asset = handle.asset; Assert.AreEqual(668, asset.numParticles); Assert.AreEqual(502, asset.numShapes); Assert.AreEqual(3856, asset.numSprings); FlexExt.DestroyAsset(handle); }
public void TestAllocateFreeParticles() { Flex.Library lib = Flex.Init(Flex.FLEX_VERSION, ErrorCallback); Flex.SolverDesc slvDsc = default(Flex.SolverDesc); Flex.SetSolverDescDefaults(ref slvDsc); slvDsc.maxParticles = 1000; Flex.Solver solver = Flex.CreateSolver(lib, ref slvDsc); FlexExt.Container container = FlexExt.CreateContainer(lib, solver, 1000); int n = 1000; int[] indices = new int[n]; int m = FlexExt.AllocParticles(container, n, ref indices[0]); Assert.AreEqual(n, m); FlexExt.FreeParticles(container, n, ref indices[0]); FlexExt.DestroyContainer(container); Flex.DestroySolver(solver); Flex.Shutdown(lib); }
public ShapeData(Collider collider) { bool dynamic = false; if (collider is SphereCollider) { SphereCollider sphereCollider = collider as SphereCollider; Vector3 scale = collider.transform.localScale; geometry.sphere.radius = sphereCollider.radius * Mathf.Max(scale.x, scale.y, scale.z); flags = Flex.MakeShapeFlags(Flex.CollisionShapeType.Sphere, dynamic); shapeMin = Vector3.one * -geometry.sphere.radius; shapeMax = Vector3.one * geometry.sphere.radius; shapeCenter = sphereCollider.center; shapeCenter.x *= scale.x; shapeCenter.y *= scale.y; shapeCenter.z *= scale.z; } else if (collider is CapsuleCollider) { CapsuleCollider capsuleCollider = collider as CapsuleCollider; Vector3 scale = collider.transform.localScale; if (capsuleCollider.direction == 1) { scale = new Vector3(scale.y, scale.z, scale.x); } if (capsuleCollider.direction == 2) { scale = new Vector3(scale.z, scale.x, scale.y); } geometry.capsule.radius = capsuleCollider.radius * Mathf.Max(scale.y, scale.z); geometry.capsule.halfHeight = capsuleCollider.height * scale.x * 0.5f - geometry.capsule.radius; flags = Flex.MakeShapeFlags(Flex.CollisionShapeType.Capsule, dynamic); shapeMin = new Vector3(-geometry.capsule.halfHeight - geometry.capsule.radius, -geometry.capsule.radius, -geometry.capsule.radius); shapeMax = new Vector3(geometry.capsule.halfHeight + geometry.capsule.radius, geometry.capsule.radius, geometry.capsule.radius); shapeCenter = capsuleCollider.center; shapeCenter.x *= scale.x; shapeCenter.y *= scale.y; shapeCenter.z *= scale.z; if (capsuleCollider.direction == 1) { shapePreRotation = Quaternion.Euler(0.0f, 0.0f, 90.0f); } if (capsuleCollider.direction == 2) { shapePreRotation = Quaternion.Euler(0.0f, 90.0f, 0.0f); } } else if (collider is BoxCollider) { BoxCollider boxCollider = collider as BoxCollider; Vector3 scale = collider.transform.localScale; Vector3 halfSize = new Vector3(boxCollider.size.x * scale.x * 0.5f, boxCollider.size.y * scale.y * 0.5f, boxCollider.size.z * scale.z * 0.5f); geometry.box.halfExtents = halfSize; flags = Flex.MakeShapeFlags(Flex.CollisionShapeType.Box, dynamic); shapeMin = -halfSize; shapeMax = halfSize; shapeCenter = boxCollider.center; shapeCenter.x *= scale.x; shapeCenter.y *= scale.y; shapeCenter.z *= scale.z; } else if (collider is MeshCollider) { MeshCollider meshCollider = collider as MeshCollider; Mesh mesh = meshCollider.sharedMesh; if (mesh) { Vector3 scale = collider.transform.localScale; Vector3 boundsMin = new Vector3(mesh.bounds.min.x * scale.x, mesh.bounds.min.y * scale.y, mesh.bounds.min.z * scale.z); Vector3 boundsMax = new Vector3(mesh.bounds.max.x * scale.x, mesh.bounds.max.y * scale.y, mesh.bounds.max.z * scale.z); Vector3[] vertices = mesh.vertices; int[] triangles = mesh.triangles; if (vertices.Length > 0 && triangles.Length > 0) { bool useConvex = meshCollider.convex; if (useConvex) { Vector4[] planes = new Vector4[triangles.Length / 3]; Vector3[] bounds = new Vector3[2]; int planeCount = FlexUtils.ConvexPlanes(ref vertices[0], ref scale, ref triangles[0], triangles.Length / 3, ref planes[0], ref bounds[0]); // Convex meshes in Flex can't have more than 64 faces if (planeCount <= 64) { m_flexConvex = Flex.CreateConvexMesh(FlexContainer.library); Flex.Buffer planeBuffer = Flex.AllocBuffer(FlexContainer.library, planeCount, sizeof(float) * 4, Flex.BufferType.Host); FlexUtils.FastCopy(planes, Flex.Map(planeBuffer)); Flex.Unmap(planeBuffer); Flex.UpdateConvexMesh(FlexContainer.library, m_flexConvex, planeBuffer, planeCount, ref bounds[0], ref bounds[1]); geometry.convexMesh.scale = Vector3.one; geometry.convexMesh.mesh = m_flexConvex; Flex.FreeBuffer(planeBuffer); flags = Flex.MakeShapeFlags(Flex.CollisionShapeType.ConvexMesh, dynamic); shapeMin = bounds[0]; shapeMax = bounds[1]; } else { useConvex = false; } } if (!useConvex) { int[] uniqueInds = new int[vertices.Length]; int[] originalToUniqueMap = new int[vertices.Length]; int uniqueVertCount = FlexExt.CreateWeldedMeshIndices(ref vertices[0], vertices.Length, ref uniqueInds[0], ref originalToUniqueMap[0], 0.0001f); // @@@ Vector4[] uniqueVerts = new Vector4[uniqueVertCount]; for (int i = 0; i < uniqueVertCount; ++i) { uniqueVerts[i] = new Vector3(vertices[uniqueInds[i]].x * scale.x, vertices[uniqueInds[i]].y * scale.y, vertices[uniqueInds[i]].z * scale.z); } Flex.Buffer vertexBuffer = Flex.AllocBuffer(FlexContainer.library, uniqueVerts.Length, sizeof(float) * 4, Flex.BufferType.Host); FlexUtils.FastCopy(uniqueVerts, Flex.Map(vertexBuffer)); Flex.Unmap(vertexBuffer); int[] indices = new int[triangles.Length]; for (int i = 0; i < triangles.Length; ++i) { indices[i] = originalToUniqueMap[triangles[i]]; } Flex.Buffer indexBuffer = Flex.AllocBuffer(FlexContainer.library, indices.Length, sizeof(int), Flex.BufferType.Host); FlexUtils.FastCopy(indices, Flex.Map(indexBuffer)); Flex.Unmap(indexBuffer); m_flexMesh = Flex.CreateTriangleMesh(FlexContainer.library); Flex.UpdateTriangleMesh(FlexContainer.library, m_flexMesh, vertexBuffer, indexBuffer, uniqueVertCount, indices.Length / 3, ref boundsMin, ref boundsMax); geometry.triMesh.scale = Vector3.one; geometry.triMesh.mesh = m_flexMesh; Flex.FreeBuffer(vertexBuffer); Flex.FreeBuffer(indexBuffer); flags = Flex.MakeShapeFlags(Flex.CollisionShapeType.TriangleMesh, dynamic); Flex.GetTriangleMeshBounds(FlexContainer.library, m_flexMesh, ref shapeMin, ref shapeMax); } } } } shapePrevPosition = collider.transform.position + collider.transform.rotation * shapeCenter; shapePrevRotation = collider.transform.rotation * shapePreRotation; }
void BuildFromMesh() { if (m_referenceMesh) { Vector3[] vertices = m_referenceMesh.vertices; int[] triangles = m_referenceMesh.triangles; if (vertices != null && vertices.Length > 0 && triangles != null && triangles.Length > 0) { for (int i = 0; i < m_meshTesselation; ++i) { Vector3[] newVertices = new Vector3[triangles.Length * 4]; int[] newTriangles = new int[triangles.Length * 4]; for (int j = 0; j < triangles.Length / 3; ++j) { Vector3 v0 = vertices[triangles[j * 3 + 0]], v1 = vertices[triangles[j * 3 + 1]], v2 = vertices[triangles[j * 3 + 2]]; Vector3 v3 = (v0 + v1) * 0.5f, v4 = (v1 + v2) * 0.5f, v5 = (v2 + v0) * 0.5f; int i0 = j * 12 + 0, i1 = j * 12 + 1, i2 = j * 12 + 2; int i3 = j * 12 + 3, i4 = j * 12 + 4, i5 = j * 12 + 5; int i6 = j * 12 + 6, i7 = j * 12 + 7, i8 = j * 12 + 8; int i9 = j * 12 + 9, iA = j * 12 + 10, iB = j * 12 + 11; newTriangles[i0] = i0; newTriangles[i1] = i1; newTriangles[i2] = i2; newTriangles[i3] = i3; newTriangles[i4] = i4; newTriangles[i5] = i5; newTriangles[i6] = i6; newTriangles[i7] = i7; newTriangles[i8] = i8; newTriangles[i9] = i9; newTriangles[iA] = iA; newTriangles[iB] = iB; newVertices[i0] = v0; newVertices[i1] = v3; newVertices[i2] = v5; newVertices[i3] = v3; newVertices[i4] = v1; newVertices[i5] = v4; newVertices[i6] = v5; newVertices[i7] = v4; newVertices[i8] = v2; newVertices[i9] = v3; newVertices[iA] = v4; newVertices[iB] = v5; } vertices = newVertices; triangles = newTriangles; } int[] uniqueVerts = new int[vertices.Length]; int[] originalToUniqueMap = new int[vertices.Length]; int particleCount = FlexExt.CreateWeldedMeshIndices(ref vertices[0], vertices.Length, ref uniqueVerts[0], ref originalToUniqueMap[0], m_weldingThreshold); Vector4[] particles = new Vector4[particleCount]; for (int i = 0; i < particleCount; ++i) { Vector3 v = vertices[uniqueVerts[i]]; particles[i] = new Vector4(v.x * m_meshLocalScale.x, v.y * m_meshLocalScale.y, v.z * m_meshLocalScale.z, 1.0f); } foreach (var i in fixedParticles) { if (i < particleCount) { particles[i].w = 0.0f; } } int indexCount = triangles.Length; int[] indices = new int[indexCount]; for (int i = 0; i < indexCount; ++i) { indices[i] = originalToUniqueMap[triangles[i]]; } FlexExt.Asset.Handle assetHandle = FlexExt.CreateClothFromMesh(ref particles[0], particles.Length, ref indices[0], indices.Length / 3, m_stretchStiffness, m_bendStiffness, m_tetherStiffness, m_tetherGive, m_pressure); if (assetHandle) { StoreAsset(assetHandle.asset); FlexExt.DestroyAsset(assetHandle); } } } }