Three-mesh-bvh套件加速搜尋原理簡介這篇文章介紹Three-mesh-bvh套件加速搜尋的原理,且該文提到判斷兩個模型是否相交的功能,只需簡單呼叫Three-mesh-bvh套件提供的函式即可實現。
shapecast讓我們能參與加速搜尋的過程,如果有更進階的需求,例如想找出所有相交的點,可以通過shapecast函式實作。
附上Demo鏈接:Three-mesh-bvh shapecast demo
// 一些參數、函式資訊資訊不完整,完整版可參考上方Demo鏈接
// 準備參數
const tempPoint = new THREE.Vector3();
const { frogMesh, staticMesh } = Editor;
const frogGeometry = frogMesh.geometry;
const frogIndexAttr = frogGeometry.index;
const staticGeometry = staticMesh.geometry;
const staticGeometryRelativeMatrix = staticMesh.matrix.clone().multiply(frogMesh.matrix.clone().invert());
const staticMeshRelativeBox = staticGeometry.boundingBox.clone().applyMatrix4(staticGeometryRelativeMatrix);
// 利用shapecast,找出frogMesh與staticMesh所有相交的點
const intersectPointSet = new Set();
frogGeometry.boundsTree.shapecast({
// 持續細分有相交的包圍框
intersectsBounds: (box) => {
if (!box.intersectsBox(staticMeshRelativeBox)) return NOT_INTERSECTED;
return INTERSECTED;
},
// 分別判斷三角形三個點是否在staticMesh內,是就收集到intersectPointSet內
intersectsTriangle: (triangle, triIndex) => {
if (!triangle.intersectsBox(staticMeshRelativeBox)) return false;
if (checkIfMeshIncludePoint(staticMesh, tempPoint.copy(triangle.a).applyMatrix4(frogMesh.matrix)))
intersectPointSet.add(frogIndexAttr.getX(triIndex * 3));
if (checkIfMeshIncludePoint(staticMesh, tempPoint.copy(triangle.b).applyMatrix4(frogMesh.matrix)))
intersectPointSet.add(frogIndexAttr.getX(triIndex * 3 + 1));
if (checkIfMeshIncludePoint(staticMesh, tempPoint.copy(triangle.c).applyMatrix4(frogMesh.matrix)))
intersectPointSet.add(frogIndexAttr.getX(triIndex * 3 + 2));
},
});