【问题标题】:Check Intersection Between Line and Rotated Rectangle检查直线和旋转矩形之间的交点
【发布时间】:2013-12-13 04:22:38
【问题描述】:

我尝试了很多事情但没有找到好的解决方案,所以我在这里。
在我的游戏(2D)中,我必须检查与Rotated Rectangle 内部图像的所有对象(房屋、车库..)的碰撞,在从Point APoint B 的射线之间。

我正在使用 Xna 并且有一些代码:

public void Update(List<Obstacle> Lob, DragObj Ldo)
{
    bool inter = false;
    Point A;
    Point B;

    A = new Point((int)pos.X, (int)pos.Y);
    B = new Point((int)Ldo.Position.X, (int)Ldo.Position.Y);
    for (int j = 0; j < Lob.Count(); j++) 
    {
        if (inter = interclass.LineIntersectsRect(A, B, Lob[j].Shape)) // I have this for the moment, Shape is the rectangle but not rotated )
        {
            inter = true;
            islight = false;
        }
        else
        {
            inter = false;
        }
    }
}

所以为了解决我的问题,我是否找到了一个解决方案,让 rotatedRectangle 对象具有检查与线碰撞的方法。是否完全不同,也许只检查 yy 直线和每个旋转的矩形轴之间的碰撞?

感谢您的建议。

【问题讨论】:

  • 尝试旋转线,这只是一个小触发。
  • 旋转线会改变我的二维空间组织,不是吗?我将尝试旋转我的 2 个点,但在我当前的代码中实现起来并不容易。
  • 但是你可以想象的对吗?如果将两者放在一起并旋转使矩形是直的,则可以使用常规的轴对齐矩形功能
  • Y 我已经画了它来想象它,它还可以。但它有一个奇怪的行为。交叉点工作但不在正确的位置,我也尝试过弧度角。我用它来旋转我的观点:在 2D 中,您从 (x,y) 旋转角度 t 来制作 (X,Y):X = x cos t - y sin t Y = x sin t + y cos t

标签: c# algorithm xna collision-detection


【解决方案1】:

我不懂 C# 但是... 有这种算法可以从一个点获取一条线上最近的点。 (注意closestPointOnLine函数不是我的代码)

var closestPointOnLine = function(line1, point1)
{ 
    var A1 = line1.y2 - line1.y1;
    var B1 = line1.x1 - line1.x2;

    var C1 =  A1 * line1.x1 + B1 * line1.y1;
    var C2 = -B1 * point1.x + A1 * point1.y;

    var det = A1 * A1 + B1 * B1;

    var cx = 0;
    var cy = 0;

    if(det !== 0)
    { 
        cx = ((A1 * C1 - B1 * C2) / det);
        cy = ((A1 * C2 + B1 * C1) / det);
    }else{
        cx = point1.x;
        cy = point1.y;
    }

    return {
        x : constrain(cx, Math.min(line1.x1, line1.x2), Math.max(line1.x1, line1.x2)),
        y : constrain(cy, Math.min(line1.y1, line1.y2), Math.max(line1.y1, line1.y2)),
    }; 
};

在我们继续之前,让我们明确一点: 我们的线路是:

var lineToTest = {
    x1: someNumber
    y1: someNumber,
    x2: someNumber,
    y2: someNumber
};

我们的旋转矩形包含:

var rectToTest = {
    points: [
       {
          x : someNumber,
          y : someNumber,
       },
       {
          x : someNumber,
          y : someNumber,
       },
       {
          x : someNumber,
          y : someNumber,
       },
       {
          x : someNumber,
          y : someNumber,
       },
    ],
};

然后我们取lineToTest 并取它的第一个点并开始使用closestPointOnLinerectToTest 的一条线上得到一个点, 然后我们检查该点是否与lineToTest 接触,如果矩形中的其他线没有重复。

现在我实际上并不知道检查点是否接触线的代码: 但它可能会是这样的:

function isLineTouchingPoint(line1, point)
{
     //Other code here
     //You'll have to use trigonometry for this one though

     return boolean;
}

现在您可以将此代码转换为 C# 以使其工作。

【讨论】:

    【解决方案2】:

    我通过检查我的线和旋转矩形的每一边之间的交点来解决这个问题(我必须先旋转矩形的每一边)。 我会尽快发布这个小算法。

    【讨论】:

      猜你喜欢
      • 2013-03-09
      • 2012-06-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-06-09
      • 1970-01-01
      相关资源
      最近更新 更多