0

回転した 2 次元の 2 つの長方形が衝突するかどうかを検出する関数を使用して拡張しています。機能はこちらから。

私の問題:関数は、次の四角形の間の衝突を誤って検出します。

Rect1 = centerX=0, centerY=0, width=8, height=4 angle=0
Rect1 = centerX=16, centerY=0, width=8, height=4 angle=0

私は間違っていますか、それともそれらの長方形が衝突してはいけませんか? 回転した四角形間のピクセル パーフェクトな衝突を検出するには、関数をどのように編集すればよいですか? 最後の 2 行を編集する必要があるような気がしますが、よくわかりません。

int RotRectsCollision(_RotRect * rr1, _RotRect * rr2)
{
 _Vector2D A, B,   // vertices of the rotated rr2
       C,      // center of rr2
       BL, TR; // vertices of rr2 (bottom-left, top-right)

 float ang = rr1->ang - rr2->ang, // orientation of rotated rr1
       cosa = cos(ang),           // precalculated trigonometic -
       sina = sin(ang);           // - values for repeated use

 float t, x, a;      // temporary variables for various uses
 float dx;           // deltaX for linear equations
 float ext1, ext2;   // min/max vertical values

 // move rr2 to make rr1 cannonic
 C = rr2->C;
 SubVectors2D(&C, &rr1->C);

 // rotate rr2 clockwise by rr2->ang to make rr2 axis-aligned
 RotateVector2DClockwise(&C, rr2->ang);

 // calculate vertices of (moved and axis-aligned := 'ma') rr2
 BL = TR = C;
 SubVectors2D(&BL, &rr2->S);
 AddVectors2D(&TR, &rr2->S);

 // calculate vertices of (rotated := 'r') rr1
 A.x = -rr1->S.y*sina; B.x = A.x; t = rr1->S.x*cosa; A.x += t; B.x -= t;
 A.y =  rr1->S.y*cosa; B.y = A.y; t = rr1->S.x*sina; A.y += t; B.y -= t;

 t = sina*cosa;

 // verify that A is vertical min/max, B is horizontal min/max
 if (t < 0)
 {
  t = A.x; A.x = B.x; B.x = t;
  t = A.y; A.y = B.y; B.y = t;
 }

 // verify that B is horizontal minimum (leftest-vertex)
 if (sina < 0) { B.x = -B.x; B.y = -B.y; }

 // if rr2(ma) isn't in the horizontal range of
 // colliding with rr1(r), collision is impossible
 if (B.x > TR.x || B.x > -BL.x) return 0;

 // if rr1(r) is axis-aligned, vertical min/max are easy to get
 if (t == 0) {ext1 = A.y; ext2 = -ext1; }
 // else, find vertical min/max in the range [BL.x, TR.x]
 else
 {
  x = BL.x-A.x; a = TR.x-A.x;
  ext1 = A.y;
  // if the first vertical min/max isn't in (BL.x, TR.x), then
  // find the vertical min/max on BL.x or on TR.x
  if (a*x > 0)
  {
   dx = A.x;
   if (x < 0) { dx -= B.x; ext1 -= B.y; x = a; }
   else       { dx += B.x; ext1 += B.y; }
   ext1 *= x; ext1 /= dx; ext1 += A.y;
  }

  x = BL.x+A.x; a = TR.x+A.x;
  ext2 = -A.y;
  // if the second vertical min/max isn't in (BL.x, TR.x), then
  // find the local vertical min/max on BL.x or on TR.x
  if (a*x > 0)
  {
   dx = -A.x;
   if (x < 0) { dx -= B.x; ext2 -= B.y; x = a; }
   else       { dx += B.x; ext2 += B.y; }
   ext2 *= x; ext2 /= dx; ext2 -= A.y;
  }
 }

 // check whether rr2(ma) is in the vertical range of colliding with rr1(r)
 // (for the horizontal range of rr2)
 return !((ext1 < BL.y && ext2 < BL.y) ||
      (ext1 > TR.y && ext2 > TR.y));
}
4

1 に答える 1

1

これらの長方形が衝突するべきではないと思います。

最初のものは (0,0) に中心があり、幅は 8 => X 軸で -4 から 4 の範囲です。

2 つ目は (16,0) に中心があり、幅が 8 => X 軸上で 16 - 4 = 12 から 16 + 4 = 20 にまたがります。

したがって、1 番目と 2 番目は X 軸上で重なりません。どちらも回転がないので、衝突しません。

私はコードを調べていませんが、長方形の例を考えると、それらは衝突していないようです。

于 2012-08-20T06:22:19.087 に答える