I am looking robust collision detection algorithms and found an awesome book called Realtime Collision Detection by Christer Ericson. I am trying to use a particular algorithm which checks whether a given point is inside convex polyhedron (in 3D space these are the square pyramid, cube and tetrahedron (aka pyramid with all sides being a triangle)). In my case I have a square pyramid. The validation of the point is done by using the intersection volume for a given number of halfspaces and determining whether the point is in front or behind all of the planes that are spanned by the polyhedron's sides. I have difficulties understanding the usage of the argument n
(see below) which represents the number of halfspaces for the given polyhedron:
// Test if point p inside polyhedron given as the intersection volume of n halfspaces
int TestPointPolyhedron(Point p, Plane *h, int n) {
for (int i = 0; i < n; i++) {
if(DistPointPlane(p, h[i]) > 0.0f) return 0;
}
return 1;
}
with DistPointPlane(...)
calculating the distance between a given point and a plane
float DistPointPlane(Point q, Plane p) {
return Dot(q, p.n) - p.d;
}
and Plane
being a structure that represents a plane in 3D space
struct Plane {
Vector n; // Plane normal. Point X on the plane satisfies Dot(n, X) = d
float d; // d = dot(n, p) for a given point on the plane
}
Plane ComputePlane(Point a, Point b, Point c) {
Plane p;
p.n = Normalize(Cross(b - a, c - a));
p.d = Dot(p.n, a);
return p;
}
What the algorithm does is basically the following:
- For a given point calculate its distance to each plane of the convex polyhedron
- Check if distance is negative or positive
- If distance is negative point lies on the opposite side of the plane's normal so it's behind it.
- Else point lies on the same side as the plane's normal so it's in front of it
- If point behind all planes of the given polyhedron it lies inside else it lies outside
Now in terms of a square pyramid as far as I can tell there are 10 halfspaces since we have 4 sides and a base each representing a separate plane (so in total there are 5 planes) that divides the 3D space in two halfspaces (5 planes * 2 = 10 halfspaces
). What I don't get is the usage of n
in the code for the algorithm above. It is used as a termination condition for the loop which iterates through an array of Plane
instances. However as mentioned there are 10 halfspaces.
One thing I have thought about after some digging is the fact that the intersection between two planes is a line (edge of the pyramid). Further quoting Wolfram Mathworld
To uniquely specify the line, it is necessary to also find a particular point on it. This can be determined by finding a point that is simultaneously on both planes
Each of the pyramid's vertices fulfill this requirement since for any given two sides (including the base) we get a line which is between two of the pyramid's vertices. So in terms of intersection we do have 5 (4 for the base and 1 for the apex) however the text in the book (including the comment above the function's implementation) is vague and reading it one might get the wrong idea (at least that's my case).
Is my line of thought close to the truth or am I missing some big chunk in terms of math knowledge?
I have ported the code to Python 3 and altered the algorithm to loop through just my list of planes without taking an additional argument (which, if my thoughts are correct, is basically the same as the original one) and plotted it with matplotlib
. It works perfectly fine but I still want to know whether I have understood it correctly or not: