-- -- File:: pipeline/util/MeshUtil.ms -- Description:: Set of functions for interacting with meshes -- -- 23/6/2004 -- by Greg Smith -- ----------------------------------------------------------------------------- -- set of functions for interacting with meshes -- returns the face index of the lowest face in a mesh fn GtaGetFaceNormal obj faceID = ( curFace = getface obj.mesh faceID vertA = obj.mesh.verts[curFace[1]].pos * obj.transform vertB = obj.mesh.verts[curFace[2]].pos * obj.transform vertC = obj.mesh.verts[curFace[3]].pos * obj.transform vecA = vertB - vertA vecB = vertC - vertA normal = cross vecA vecB normal = normal / (length normal) ) fn GtaGetLowestVertFromFace obj faceID = ( curFace = getface obj.mesh faceID idxLowestVert = 1 for i = 2 to 3 do ( vertA = obj.mesh.verts[curFace[i]].pos * obj.transform vertB = obj.mesh.verts[curFace[idxLowestVert]].pos * obj.transform if vertA[3] < vertB[3] then ( idxLowestVert = i ) ) return (obj.mesh.verts[curFace[idxLowestVert]].pos * obj.transform) ) fn GtaGetAverageVertFromFace obj faceID = ( curFace = getface obj.mesh faceID averagePos = obj.mesh.verts[curFace[1]].pos averagePos = averagePos + obj.mesh.verts[curFace[2]].pos averagePos = averagePos + obj.mesh.verts[curFace[3]].pos averagePos = averagePos / 3.0 return averagePos ) fn GtaGetLowestFace obj = ( if classof obj != Editable_mesh then ( return -1 ) numFaces = getnumfaces obj.mesh if numFaces < 2 then ( return 1 ) idxBestFace = 1 for i = 2 to numFaces do ( curLowest = GtaGetLowestVertFromFace obj i testLowest = GtaGetLowestVertFromFace obj idxBestFace if curLowest[3] < testLowest[3] then ( idxBestFace = i ) ) return idxBestFace ) fn GtaGetIntersect vertA normalA objB idxFaceB = ( retVec = [0,0,0] faceB = getface objB.mesh idxFaceB vertBA = objB.mesh.verts[faceB[1]].pos * objB.transform vertBB = objB.mesh.verts[faceB[2]].pos * objB.transform vertBC = objB.mesh.verts[faceB[3]].pos * objB.transform edgeA = vertBB - vertBA edgeB = vertBC - vertBA pVec = cross normalA edgeB det = dot edgeA pVec if det < 0.0001 then ( return undefined ) invDet = 1.0 / det tVec = vertA - vertBA retVec[2] = dot tVec pVec if retVec[2] < 0.0 or retVec[2] > det then ( return undefined ) qVec = cross tVec edgeA retVec[3] = dot normalA qVec if retVec[3] < 0.0 or (retVec[3] + retVec[2]) > det then ( return undefined ) retVec[1] = dot edgeB qVec retVec = retVec / det tempVec = vertBA tempVec = tempVec + (retVec[2] * edgeA) tempVec = tempVec + (retVec[3] * edgeB) retVec = tempVec return retVec ) fn GtaAlignToGround objA objB = ( if classof objA != Editable_mesh then ( return -1 ) if classof objB != Editable_mesh then ( return -1 ) idxLowestFace = GtaGetLowestFace objA lowestVert = GtaGetLowestVertFromFace objA idxLowestFace numFaces = getnumfaces objB.mesh for i = 1 to numFaces do ( intersect = GtaGetIntersect lowestVert [0,0,-1] objB i if intersect != undefined then ( moveVec = intersect - lowestVert print moveVec objA.pos = objA.pos + moveVec exit ) ) )