GJK实现中支持函数方向变换:非均匀缩放时为何逆矩阵失效转置矩阵可行?
非均匀缩放下GJK支持函数的方向向量变换问题
在GJK算法实现中,为支持函数将世界空间搜索方向转换至局部空间时,非均匀缩放场景下使用模型矩阵的逆会导致错误结果,经实验验证,改用模型矩阵的转置矩阵可解决问题。
问题表现
当碰撞体为沿X、Z轴存在强烈非均匀缩放的截棱锥网格时,算法进入窄边区域会出现明显抖动,且穿透分辨率不符合预期。
原理分析
支持映射中,方向向量的变换规则与位置点不同:
- 位置点从局部空间转世界空间用模型矩阵(包含平移、旋转、缩放)
- 方向向量属于向量空间(平移无关),在非均匀缩放下,正确的逆变换需要对模型矩阵的旋转缩放分量取逆后转置。若模型矩阵无剪切操作,旋转分量的逆等于自身转置,缩放分量的逆对应转置矩阵中的缩放倒数,因此直接使用模型矩阵的转置即可正确完成世界空间到局部空间的方向向量转换。
修正后的代码实现
Mxm::Vec3 PhysicsSystem::furthestPoint(const Collider* collider, const Mxm::Vec3& dir) { auto& transform = collider->getObject()->transform(); const auto& worldMatrix = transform.getWorldMatrix(); // 使用模型矩阵转置变换方向向量(非均匀缩放下正确) Mxm::Vec3 localDir = (worldMatrix.transposed() * Mxm::Vec4(dir, 0.0f)).toVec3(); Mxm::Vec3 furthestPoint = collider->support(localDir); // 位置点用模型矩阵转世界空间 return (transform.getWorldMatrix() * Mxm::Vec4(furthestPoint, 1.0f)).toVec3(); }
内容的提问来源于stack exchange,提问作者glitch
相关产品推荐
相关产品推荐

