 # Line Segment & Rotated Rectangle Intersection Detection

a guest
Sep 17th, 2014
259
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
1. // Returns the distance of the intersection point from the ray's origin.
2. // Negative results mean no intersection.
3. // Fails when the origin is contained in the rectangle, test for that separately, if needed.
4. float intersect(Ray ray, Box box) {
5.  Vector2D verts; // array to store the vertices of the box. verts = verts to make things easier
6.  box.getVerts(verts);
7.  float sin_phi = sinf(-ray.dir);
8.  float cos_phi = cosf(-ray.dir);
9.
10.  // Rotate everything so the ray is aligned with the y-axis, its x-coord is zero
11.  ray.orig.rotateM(sin_phi,cos_phi);
12.  float xshift = -ray.orig.r; // we'll skip shifting the ray itself, x is zero, y is unaffected anyway
13.  for (int i=0; i<4; ++i) {
14.   verts[i].rotateM(sin_phi,cos_phi);
15.   verts[i].r += xshift;
16.  }
17.  verts = verts; // makes the next loop simpler
18.  for (int i=0; i<4; ++i) {
19.   if ((verts[i].x() < 0) && (verts[i+1].x() >= 0)) { // intersection
20.    Vector2D diff = verts[i+1] - verts[i];
21.    return verts[i].y() - diff.y()/diff.x() * verts[i].x() - ray.orig.y();
22.   }
23.  }
24.  // Why the above if() works:
25.  // - the ray's direction vector is (0,1), so the sides facing the ray have a normal vector with n.y < 0
26.  // - the vertices are in CCW order, so the normal of an edge will be (d.y,-d.x), where d = v[i+1] - v[i]
27.  // - substituting into n.y < 0 we get v[i].x - v[i+1].x < 0, which is v[i].x < v[i+1].x
28.  // - thus, we are only interested in the edges going left to right, so we needn't test for the opposite case
29.  return -1;
30. }