Calculate the coordinates of the orthogonal projection of a point on a segment
Project for creating drawings in svg
, in native js
.
Faced with the following task:
Known coordinates 3x points A B C
on the plane. The points A B
are the beginning and end of the segment AB
. You need to find the coordinates of the orthogonal projection (точка D)
of the point С
on the segment АВ
. How do I do this?
2 answers
The projection can be found using the scalar product of the vectors
D = A + AB * Dot(AC, AB) / Dot(AB, AB)
In pseudocode:
abx = B.X - A.X
aby = B.Y - A.Y
dacab = (C.X - A.X) * abx + (C.Y - A.Y) * aby
dab = abx * abx + aby * aby
t = dacab / dab
D.X = A.X + abx * t
D.Y = A.Y + aby * t
Here slightly different notation (C=P, N=D) and explanations
-
"Intersection" method:
If you plot a point
С' = (Cx - (By - Ay), Cy + (Bx - Ax))
, then the lineCC'
will be perpendicular to the lineAB
. The intersection of the linesAB
andCC'
will give you a pointD
.The method is "heavy" from a computational point of view due to the fact that it uses the intersection of two straight lines as a primitive. But it is easy to implement, if such a primitive is already at hand.
-
Distance method:
If
AA
,BB
andCC
- coefficients equations of a straight line containing a segmentAB
(easily calculated using the coordinates of the pointsA
andB
), then the valueDD = AA * Cx + BB * Cy + CC
Will give you the signed distance from this straight line to the point
C
, multiplied by|(AA, BB)|
. If we add the vectorDD * (-AA, -BB)
to the pointC
, we get a point that is shifted relative toC
in the right direction, but, conditionally speaking, "too far": the distance exceeds the required|(AA, BB)|^2
times. It is enough to divide the offset by this value - we get the required pointD
DD D = C + ------------ * (-AA, -BB) |(AA, BB)|^2
This method is also somewhat cumbersome due to the "extra" calculations of the equation of a straight line, but it can be useful if you already know/calculate the equation of a straight line, and also if you need to calculate the distance from
C
toAB
in addition to the projection point. -
"Scalar product" method:
It is obvious that
|(A, D)| D = A + -------- * (A, B) |(A, B)|
In this case, the scalar product of the vector
(A, C)
by the vector(A, B)
is the length of the projection(A, D)
, multiplied by|(A, B)|
.(A, C)•(A, B) = |(A, D)| * |(A, B)|
Then
(A, C)•(A, B) D = A + ------------- * (A, B) |(A, B)|^2
(It can be shown that if you put all the calculations of the second method into one formula, it will "reduce" to the third method.)