4
$\begingroup$

I am going through an undocumented function that takes in three points and a Z-value that projects three points on the plane defined by Z-value. I want to understand the mathematical theory behind it and I need your help to decode the function:

SlicerSegment project2D(Point3& p0, Point3& p1, Point3& p2, int32_t z) const
{
    SlicerSegment seg;
    seg.start.X = p0.x + int64_t(p1.x - p0.x) * int64_t(z - p0.z) / int64_t(p1.z - p0.z);
    seg.start.Y = p0.y + int64_t(p1.y - p0.y) * int64_t(z - p0.z) / int64_t(p1.z - p0.z);

seg.end.X = p0.x + int64_t(p2.x - p0.x) * int64_t(z - p0.z) / int64_t(p2.z - p0.z);
    seg.end.Y = p0.y + int64_t(p2.y - p0.y) * int64_t(z - p0.z) / int64_t(p2.z - p0.z);
    return seg;
}
$\endgroup$
2
$\begingroup$

The function calculates the intersection points between two edges of a triangle and a plane that is assumed to cut it. It returns a line segment running along the cut.

Or more generally, the function calculates where the intersection points with the two edges would be, if the edges were extended to infinite lines. Given that it's called "project", that might be the intended use-case; hard to know without seeing how this gets used in context.

The first two lines of math are calculating the intersection point of the $p_0 p_1$ edge with the z-plane. It works by linearly interpolating the $x, y$ values along the edge based on the proportion between $z$ values. The second two lines do the same thing for the $p_0 p_2$ edge.

One odd thing is that the function is using integers everywhere. Presumably it's because the program is using fixed-point coordinates (which makes good sense for a lot of geometry processing applications due to its uniform precision). However, the way it's done here seems oblivious to rounding: the integer divisions will truncate any fractional component instead of rounding to nearest.

$\endgroup$
1
$\begingroup$

Let us look at the first line in detail:

  • int64_t(p1.x - p0.x) is the distance between p1 and p0 in the x (also y later) direction lets call this dx for later discussion.
  • int64_t(z - p0.z) is the distance from z and p0 for simplicity lets us call this a later.
  • int64_t(p1.z - p0.z) is the distance from p0 and p1 or vector length simplicity lets us call this len later.
  • lets look at a/len well that is simply the length of the ratio of the each point to 0. This equals to how much the vector p1-p0 must be scaled to reach the plane intersection.

Finally the entire expression is can be read as follows:

vector p0 + vector p0-1 * length to intersection

And visually its as follows:

enter image description here

Image 1: The vectors in the calculation, (blue lines sow offsets and projections for feeling of 3D)

And the entire function gives the same for the two edges of your triangle. Please note that it is perfectly possible that the result is degenerate as the choice of what edges to use is not checked for so one edge MIGHT be parallel to the plane. Also selection of points to send changes what is being projected.

enter image description here

Image 2: input blue triangle as 3 points (black), return value projected segment in orange on plane.

$\endgroup$
  • $\begingroup$ The diagrams are nice, but you might want to label the points (p0, p1, p2) to make them easier to understand. :) $\endgroup$ – Nathan Reed May 26 '16 at 17:16
  • 1
    $\begingroup$ There are just sketches @NathanReed I threw away the sources, but yes i can do that. $\endgroup$ – joojaa May 26 '16 at 18:29

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.