OpenGL 2D 圆 - 旋转 AABB 碰撞

Posted

技术标签:

【中文标题】OpenGL 2D 圆 - 旋转 AABB 碰撞【英文标题】:OpenGL 2D Circle - Rotated AABB Collision 【发布时间】:2021-11-12 21:20:50 【问题描述】:

我无法找到一种方法来检测圆形和旋转矩形之间的碰撞。我的方法是先将圆和矩形旋转-angle,其中angle 是矩形旋转的弧度数。因此,矩形和圆形与轴对齐,所以我可以执行基本的圆形 - AABB 碰撞检测。

bool CheckCollision(float circleX, float circleY, float radius, float left, float bottom, float width, float height, float angle)

        // Rotating the circle and the rectangle with -angle
            circleX = circleX * cos(-angle) - circleY * sin(-angle);
            circleY = circleX * sin(-angle) + circleY * cos(-angle);

            left = left * cos(-angle) - bottom* sin(-angle);
            bottom = left * sin(-angle) + bottom * cos(-angle);

       

glm::vec2 center(circleX, circleY);
        // calculate AABB info (center, half-extents)
        glm::vec2 aabb_half_extents(width / 2.0f, height / 2.0f);
        glm::vec2 aabb_center(
            left + aabb_half_extents.x,
            bottom + aabb_half_extents.y
        );
        // get difference vector between both centers
        glm::vec2 difference = center - aabb_center;
        glm::vec2 clamped = glm::clamp(difference, -aabb_half_extents, aabb_half_extents);
        // add clamped value to AABB_center and we get the value of box closest to circle
        glm::vec2 closest = aabb_center + clamped;
        // retrieve vector between center circle and closest point AABB and check if length <= radius
        difference = closest - center;

        return glm::length(difference) < radius;

【问题讨论】:

【参考方案1】:

设矩形中心为rcx, rcy。在该点设置坐标原点,围绕该点旋转圆心(cx, cy是相对于矩形中心的坐标):

cx = (circleX - rcx) * cos(-angle) - (circleY - rcy) * sin(-angle);
cy = (circleX - rcx) * sin(-angle) + (circleY - rcy) * cos(-angle);

现在得到圆心到矩形最近点的平方距离(零表示圆心在矩形内):

dx = max(Abs(cx) - rect_width / 2, 0)
dy = max(Abs(cy) - rect_height / 2, 0)
SquaredDistance = dx * dx + dy * dy

然后将其与平方半径进行比较

【讨论】:

以上是关于OpenGL 2D 圆 - 旋转 AABB 碰撞的主要内容,如果未能解决你的问题,请参考以下文章

Cocos2d-三维拾取Ray-AABB碰撞检测算法转

在 OpenGL 中的 3D 模型上创建 AABB

2D 碰撞检测和 OpenGL 的东西

C ++ / OpenGL - 2D - 如何在矩形边界框中剪切圆

“等一下,我碰!”——常见的2D碰撞检测

OpenGL 2D旋转问题