Three.js 射线碰撞检测

发布于 2021-10-10 08:57:20 字数 2253 浏览 1631 评论 0

下面代码是通过 threejs 射线计算的方法来计算两个网格模型是否发生了碰撞,下面代码用到的 threejs 类比较多,能顺序阅读下面代码,需要对 threejs 向量 Vector3、矩阵 Matrix4、射线 Ray 和射线投射器 Raycaster 有一定的理解。

//检测球体sphereMesh网格模型是否和立方体网格模型boxMesh发生了碰撞,也就是两个模型是否是相互交叉状态
//设置球体位于不同位置,用来测试碰撞
sphereMesh.position.x = 40; //两个网格模型不交叉
sphereMesh.position.x = 25; //两个网格模型相互交叉
//声明一个变量用来表示是否碰撞
var bool = false;
// threejs的几何体默认情况下几何中心在场景中坐标是坐标原点。
// 可以通过position属性或.getWorldPosition()方法获得模型几何中心的世界坐标
var centerCoord = sphereMesh.position.clone();
//球体网格模型几何体的所有顶点数据
var vertices = sphereMesh.geometry.vertices
//1.循环遍历球体几何体所有顶点坐标
//2.把几何体的每一个顶点和几何体中心构建一个射线
//3.
for (var i = 0; i < vertices.length; i++) {
  // vertices[i]获得几何体索引是i的顶点坐标,
  // 注意执行.clone()返回一个新的向量,以免改变几何体顶点坐标值
  // 几何体的顶点坐标要执行该几何体绑定模型对象经过的旋转平移缩放变换
  // 几何体顶点经过的变换可以通过模型的本地矩阵属性.matrix或世界矩阵属性.matrixWorld获得
  var vertexWorldCoord = vertices[i].clone().applyMatrix4(sphereMesh.matrixWorld);
  var dir = new THREE.Vector3(); //创建一个向量
  // 几何体顶点坐标和几何体中心坐标构成的方向向量
  dir.subVectors(vertexWorldCoord, centerCoord);

  //Raycaster构造函数创建一个射线投射器对象,参数1、参数2改变的是该对象的射线属性.ray
  // 参数1:射线的起点
  // 参数2:射线的方向,注意归一化的时候,需要先克隆,否则后面会执行dir.length()计算向量长度结果是1
  var raycaster = new THREE.Raycaster(centerCoord, dir.clone().normalize());

  // 计算射线和参数1中的模型对象是否相交,参数1数组中可以设置多个模型模型对象,下面参数只设置了立方体网格模型
  var intersects = raycaster.intersectObjects([boxMesh]);
  if (intersects.length > 0) { // 判断参数[boxMesh]中模型对象是否与射线相交
    // intersects[0].distance:射线起点与交叉点之间的距离(交叉点:射线和模型表面交叉点坐标)
    // dir.length():球体顶点和球体几何中心构成向量的长度
    // 通过距离大小比较判断是否碰撞
    // intersects[0].distance小于dir.length(),说明交叉点的位置在射线起点和球体几何体顶点之间,
    //而交叉点又在立方体表面上,也就是说立方体部分表面插入到了球体里面
    if (intersects[0].distance < dir.length()) {
      //循环遍历几何体顶点,每一个顶点都要创建一个射线,进行一次交叉拾取计算,只要有一个满足上面的距离条件,就发生了碰撞
      bool = true;
    }
  }
}
//在浏览器控制显示当前两个模型对象是否碰撞(也就是相互交叉状态)
if (bool) {
  console.log('碰撞');
} else {
  console.log('未碰撞');
}

计算量

通过上面的代码你可以看到,如果要判断一个网格模型和另一个网格模型是否碰撞,需要循环遍历该模型绑定几何体 Geometry 的所有顶点位置坐标,然后分别创建一个射线,然后把创建的射线与其它网格模型进行射线拾取交叉计算,这也就是说该模型几何体的顶点数量阅读,计算量越大。

准确度

threejs 碰撞检测是通过几何体的顶点来判断,也就是说几何体细分数越大,顶点数多,计算越准确,但是计算量会比较大。

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据

关于作者

夜无邪

暂无简介

0 文章
0 评论
19447 人气
更多

推荐作者

qq_Yqvrrd

文章 0 评论 0

2503248646

文章 0 评论 0

浮生未歇

文章 0 评论 0

养猫人

文章 0 评论 0

第七度阳光i

文章 0 评论 0

新雨望断虹

文章 0 评论 0

    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文