public void AttachIt() { if (target) { attached = true; if (!InitSkin()) { Mesh mesh = target.mesh; Vector3 objSpacePt = target.transform.InverseTransformPoint(pt); Vector3[] verts = target.sverts; int[] tris = mesh.triangles; int index = -1; MegaNearestPointTest.NearestPointOnMesh1(objSpacePt, verts, tris, ref index, ref BaryCoord); if (index >= 0) { BaryVerts[0] = tris[index]; BaryVerts[1] = tris[index + 1]; BaryVerts[2] = tris[index + 2]; } MegaNearestPointTest.NearestPointOnMesh1(objSpacePt + attachforward, verts, tris, ref index, ref BaryCoord1); if (index >= 0) { BaryVerts1[0] = tris[index]; BaryVerts1[1] = tris[index + 1]; BaryVerts1[2] = tris[index + 2]; } } } }
void OnDrawGizmos() { pt = transform.position; Gizmos.color = Color.white; Gizmos.DrawSphere(pt, radius); if (target) { if (attached) { Vector3 pos = GetCoordMine(target.sverts[BaryVerts[0]], target.sverts[BaryVerts[1]], target.sverts[BaryVerts[2]], BaryCoord); Vector3 worldPt = target.transform.TransformPoint(pos); Gizmos.color = Color.green; Gizmos.DrawSphere(worldPt, radius); Vector3 nw = target.transform.TransformDirection(norm * 40.0f); Gizmos.DrawLine(worldPt, worldPt + nw); } else { Mesh mesh = target.mesh; Vector3 objSpacePt = target.transform.InverseTransformPoint(pt); Vector3[] verts = target.sverts; //mesh.vertices; int[] tris = mesh.triangles; int index = -1; Vector3 tribary = Vector3.zero; Vector3 meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt, verts, tris, ref index, ref tribary); Vector3 worldPt = target.transform.TransformPoint(meshPt); if (index >= 0) { Vector3 cp2 = GetCoordMine(verts[tris[index]], verts[tris[index + 1]], verts[tris[index + 2]], tribary); worldPt = target.transform.TransformPoint(cp2); //meshPt); // Calc the normal } Gizmos.color = Color.red; Gizmos.DrawSphere(worldPt, radius); //.01f); //transform.position = worldPt; Gizmos.color = Color.blue; meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt + attachforward, verts, tris, ref index, ref tribary); Vector3 worldPt1 = target.transform.TransformPoint(meshPt); Gizmos.DrawSphere(worldPt1, radius); //.01f); Gizmos.color = Color.yellow; Gizmos.DrawLine(worldPt, worldPt1); } } }
float GetDistance(Vector3 p, Vector3 p0, Vector3 p1, Vector3 p2) { return(MegaNearestPointTest.DistPoint3Triangle3Dbl(p, p0, p1, p2)); }
void DeformMeshNew() { if (vertdist == null || vertdist.Length != verts.Length) { vertdist = new float[verts.Length]; vertoffsets = new Vector3[verts.Length]; nearest = new Vector3[verts.Length]; vels = new Vector3[verts.Length]; } float dst = distance * 0.001f; int index = -1; Vector3 bary = Vector3.zero; //bool collision = false; float totalpen = 0.0f; int count = 0; for (int i = 0; i < verts.Length; i++) { Vector3 p = verts[i]; // + offsets[i]; Vector3 origin = transform.TransformPoint(p + (normals[i] * dst)); if (col.bounds.Contains(origin)) { Vector3 lp = col.transform.worldToLocalMatrix.MultiplyPoint(origin); Vector3 np = MegaNearestPointTest.NearestPointOnMesh1(lp, colmesh.verts, colmesh.tris, ref index, ref bary); Vector3 dir = lp - np; float dist = Vector3.Distance(lp, np); Vector3 norm = FaceNormal(colmesh.verts, colmesh.tris, index); if (Vector3.Dot(norm, dir) < 0.0f) { totalpen += dist; dist = -dist; //collision = true; } np = col.transform.localToWorldMatrix.MultiplyPoint(np); nearest[i] = transform.worldToLocalMatrix.MultiplyPoint(np); //if ( dist < vertdist[i] ) { vertdist[i] = dist; //vertoffsets[i] = nearest[i] - verts[i]; } } else { Vector3 lp = col.transform.worldToLocalMatrix.MultiplyPoint(origin); // Distance is calculated in here Vector3 np = MegaNearestPointTest.NearestPointOnMesh1(lp, colmesh.verts, colmesh.tris, ref index, ref bary); float dist = Vector3.Distance(lp, np); //if ( dist < vertdist[i] ) { vertdist[i] = dist; } //vertdist[i] = Vector3.Distance(lp, np); // out of range np = col.transform.localToWorldMatrix.MultiplyPoint(np); nearest[i] = transform.worldToLocalMatrix.MultiplyPoint(np); count++; } } //Debug.Log("Totalpen " + totalpen); if (totalpen == 0.0f) { for (int i = 0; i < verts.Length; i++) { //sverts[i] = verts[i]; sverts[i] = verts[i] + vertoffsets[i]; vertoffsets[i] *= retspd; } } else { for (int i = 0; i < verts.Length; i++) { //Vector3 p = verts[i]; // + offsets[i]; if (vertdist[i] < 0.0f) { vertoffsets[i] = nearest[i] - verts[i]; } else { Vector3 newpos = normals[i] * ((totalpen / (float)count) * bulgeValue); vertoffsets[i] = Vector3.SmoothDamp(vertoffsets[i], newpos, ref vels[i], btime); //normals[i] * ((totalpen / (float)count) * bulgeValue); //vertoffsets[i] = Vector3.zero; } sverts[i] = verts[i] + vertoffsets[i]; vertoffsets[i] *= retspd; } } }
// To do falloff we need connected verts to each vert then just need to do recursive check until none effected void DeformMesh() { float dst = distance * 0.001f; int index = -1; Vector3 bary = Vector3.zero; bool collision = false; for (int i = 0; i < verts.Length; i++) { Vector3 p = verts[i]; // + offsets[i]; Vector3 origin = transform.TransformPoint(p + (normals[i] * dst)); if (col.bounds.Contains(origin)) { // Point in collider space Vector3 lp = col.transform.worldToLocalMatrix.MultiplyPoint(origin); Vector3 np = MegaNearestPointTest.NearestPointOnMesh1(lp, colmesh.verts, colmesh.tris, ref index, ref bary); Vector3 dir = lp - np; //float dist = Vector3.Distance(lp, np); Vector3 norm = FaceNormal(colmesh.verts, colmesh.tris, index); if (Vector3.Dot(norm, dir) < 0.0f) { np = col.transform.localToWorldMatrix.MultiplyPoint(np); sverts[i] = transform.worldToLocalMatrix.MultiplyPoint(np); sverts[i] = sverts[i] - (normals[i] * dst); collision = true; } else { sverts[i] = verts[i]; } //Debug.Log("[" + i + "] = " + dist.ToString("0.00000")); //np " + np); //np = col.transform.localToWorldMatrix.MultiplyPoint(np); //sverts[i] = transform.worldToLocalMatrix.MultiplyPoint(np); } else { sverts[i] = verts[i]; } } if (collision && bulge) { for (int i = 0; i < verts.Length; i++) { Vector3 p = verts[i]; // + offsets[i]; Vector3 origin = transform.TransformPoint(p + (normals[i] * dst)); Vector3 lp = col.transform.worldToLocalMatrix.MultiplyPoint(origin); Vector3 np = MegaNearestPointTest.NearestPointOnMesh1(lp, colmesh.verts, colmesh.tris, ref index, ref bary); float bulgeDist = Vector3.Distance(lp, np); float relativedistance = bulgeDist / (bulgeExtendValue + 0.00001f); // get the bulge curve float bulgeAmount = bulgeCrv.Evaluate(relativedistance); float delta = bulgeAmount * bulgeValue; // set the point position for indirect collision deformation sverts[i].x = sverts[i].x + normals[i].x * delta; //bulgeExtendValue * (bulgeValue / 5.0f) * envelopeValue*bulgeAmount * maxdeformation; sverts[i].y = sverts[i].y + normals[i].y * delta; //bulgeExtendValue * (bulgeValue / 5.0f) * envelopeValue*bulgeAmount * maxdeformation; sverts[i].z = sverts[i].z + normals[i].z * delta; //bulgeExtendValue * (bulgeValue / 5.0f) * envelopeValue*bulgeAmount * maxdeformation; //sverts[i] = verts[i]; } } }
void OnDrawGizmosSelected() { pt = transform.position; Gizmos.color = Color.white; Gizmos.DrawSphere(pt, radius); if (target) { if (attached) { SkinnedMeshRenderer skin = target.GetComponent <SkinnedMeshRenderer>(); if (skin) { Vector3 pos = transform.position; Vector3 worldPt = pos; Gizmos.color = Color.green; Gizmos.DrawSphere(worldPt, radius); } else { Vector3 pos = GetCoordMine(target.sverts[BaryVerts[0]], target.sverts[BaryVerts[1]], target.sverts[BaryVerts[2]], BaryCoord); Vector3 worldPt = target.transform.TransformPoint(pos); Gizmos.color = Color.green; Gizmos.DrawSphere(worldPt, radius); Vector3 nw = target.transform.TransformDirection(norm * 40.0f); Gizmos.DrawLine(worldPt, worldPt + nw); } } else { SkinnedMeshRenderer skin = target.GetComponent <SkinnedMeshRenderer>(); if (skin) { CalcSkinVerts(); Mesh mesh = target.mesh; Vector3 objSpacePt = pt; Vector3[] verts = calcskinverts; int[] tris = mesh.triangles; int index = -1; Vector3 tribary = Vector3.zero; Vector3 meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt, verts, tris, ref index, ref tribary); Vector3 worldPt = target.transform.TransformPoint(meshPt); if (index >= 0) { Vector3 cp2 = GetCoordMine(verts[tris[index]], verts[tris[index + 1]], verts[tris[index + 2]], tribary); worldPt = cp2; } Gizmos.color = Color.red; Gizmos.DrawSphere(worldPt, radius); Gizmos.color = Color.blue; meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt + attachforward, verts, tris, ref index, ref tribary); Vector3 worldPt1 = meshPt; Gizmos.DrawSphere(worldPt1, radius); Gizmos.color = Color.yellow; Gizmos.DrawLine(worldPt, worldPt1); } else { Mesh mesh = target.mesh; Vector3 objSpacePt = target.transform.InverseTransformPoint(pt); Vector3[] verts = target.sverts; int[] tris = mesh.triangles; int index = -1; Vector3 tribary = Vector3.zero; Vector3 meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt, verts, tris, ref index, ref tribary); Vector3 worldPt = target.transform.TransformPoint(meshPt); if (index >= 0) { Vector3 cp2 = GetCoordMine(verts[tris[index]], verts[tris[index + 1]], verts[tris[index + 2]], tribary); worldPt = target.transform.TransformPoint(cp2); } Gizmos.color = Color.red; Gizmos.DrawSphere(worldPt, radius); Gizmos.color = Color.blue; meshPt = MegaNearestPointTest.NearestPointOnMesh1(objSpacePt + attachforward, verts, tris, ref index, ref tribary); Vector3 worldPt1 = target.transform.TransformPoint(meshPt); Gizmos.DrawSphere(worldPt1, radius); Gizmos.color = Color.yellow; Gizmos.DrawLine(worldPt, worldPt1); } } } }
bool InitSkin() { if (target) { SkinnedMeshRenderer skin = target.GetComponent <SkinnedMeshRenderer>(); if (skin) { Quaternion rot = transform.rotation; attachrot = Quaternion.identity; skinned = true; Mesh ms = skin.sharedMesh; Vector3 pt = transform.position; CalcSkinVerts(); Vector3 objSpacePt = pt; Vector3[] verts = calcskinverts; int[] tris = ms.triangles; int index = -1; MegaNearestPointTest.NearestPointOnMesh1(objSpacePt, verts, tris, ref index, ref BaryCoord); //ref tribary); if (index >= 0) { BaryVerts[0] = tris[index]; BaryVerts[1] = tris[index + 1]; BaryVerts[2] = tris[index + 2]; } MegaNearestPointTest.NearestPointOnMesh1(objSpacePt + attachforward, verts, tris, ref index, ref BaryCoord1); if (index >= 0) { BaryVerts1[0] = tris[index]; BaryVerts1[1] = tris[index + 1]; BaryVerts1[2] = tris[index + 2]; } skinverts = new MegaSkinVert[6]; for (int i = 0; i < 3; i++) { int vert = BaryVerts[i]; BoneWeight bw = ms.boneWeights[vert]; skinverts[i] = new MegaSkinVert(); skinverts[i].vert = vert; skinverts[i].weights[0] = bw.weight0; skinverts[i].weights[1] = bw.weight1; skinverts[i].weights[2] = bw.weight2; skinverts[i].weights[3] = bw.weight3; skinverts[i].bones[0] = skin.bones[bw.boneIndex0]; skinverts[i].bones[1] = skin.bones[bw.boneIndex1]; skinverts[i].bones[2] = skin.bones[bw.boneIndex2]; skinverts[i].bones[3] = skin.bones[bw.boneIndex3]; skinverts[i].bindposes[0] = ms.bindposes[bw.boneIndex0]; skinverts[i].bindposes[1] = ms.bindposes[bw.boneIndex1]; skinverts[i].bindposes[2] = ms.bindposes[bw.boneIndex2]; skinverts[i].bindposes[3] = ms.bindposes[bw.boneIndex3]; } for (int i = 3; i < 6; i++) { int vert = BaryVerts1[i - 3]; BoneWeight bw = ms.boneWeights[vert]; skinverts[i] = new MegaSkinVert(); skinverts[i].vert = vert; skinverts[i].weights[0] = bw.weight0; skinverts[i].weights[1] = bw.weight1; skinverts[i].weights[2] = bw.weight2; skinverts[i].weights[3] = bw.weight3; skinverts[i].bones[0] = skin.bones[bw.boneIndex0]; skinverts[i].bones[1] = skin.bones[bw.boneIndex1]; skinverts[i].bones[2] = skin.bones[bw.boneIndex2]; skinverts[i].bones[3] = skin.bones[bw.boneIndex3]; skinverts[i].bindposes[0] = ms.bindposes[bw.boneIndex0]; skinverts[i].bindposes[1] = ms.bindposes[bw.boneIndex1]; skinverts[i].bindposes[2] = ms.bindposes[bw.boneIndex2]; skinverts[i].bindposes[3] = ms.bindposes[bw.boneIndex3]; } GetSkinPos1(); attachrot = Quaternion.Inverse(transform.rotation) * rot; return(true); } else { skinned = false; } } return(false); }