# Thread: Finding closest point on line to a point

1. ## Finding closest point on line to a point

I have been going bonkers trying to figure out what I'm doing wrong.

I am using the proper formula to get the point on a segment which is tangent (closest) to a point not on the segment. It is working but instead of it giving me a perpendicular point on segment A-B, the point on segment A-B is perpendicular to segment B-C.

Needless to say, I have switch the values around and tried numerous variations of this formula...I get the wrong answer.

James

-------------------------------------------------------------
From uwa.edu.au

This note describes the technique and gives the solution to finding the shortest distance from a point to a line or line segment.
The equation of a line defined through two points P1 (x1,y1) and P2 (x2,y2) is

P = P1 + u (P2 - P1)

The point P3 (x3,y3) is closest to the line at the tangent to the line which passes through P3, that is, the dot product of the tangent and line is 0, thus

(P3 - P) dot (P2 - P1) = 0

Substituting the equation of the line gives

[P3 - P1 - u(P2 - P1)] dot (P2 - P1) = 0

Solving this gives the value of u

Substituting this into the equation of the line gives the point of intersection (x,y) of the tangent as

x = x1 + u (x2 - x1)
y = y1 + u (y2 - y1)

The distance therefore between the point P3 and the line is the distance between (x,y) above and P3.

Notes

• The only special testing for a software implementation is to ensure that P1 and P2 are not coincident (denominator in the equation for u is 0)
• If the distance of the point to a line segment is required then it is only necessary to test that u lies between 0 and 1.
• The solution is similar in higher dimensions.
---------------------------------------------------------------------
PHP program in question...

[php]function square($B,$A){
$sq = pow(($B-$A),2); return$sq;
}

// Compute the vector of the intersection point

function findU($A,$B,$C){$U =(($C[0] -$A[0])*($B[0]-$A[0]) + ($C[1] -$A[1])*($B[1]-$A[1]))/ pow(distance($A,$B, $C),2); return$U;

}
// Compute the coordinate of the intersection
function intersection($A,$B,$C){$intersection_X = $A[0] + findU($A,$B,$C)*($B[0]-$A[0]);
$intersection_Y =$A[1] + findU($A,$B,$C)*($B[1]-$A[1]);$P = array($intersection_X,$intersection_Y);
return $P; } function distance ($C,$B,$A){

$d = sqrt(square($C[0],$A[0]) + square($C[1],$A[1]));$D = sqrt(square($C[0],$B[0]) + square($C[1],$B[1]));

if($d <$D) return $D; else return$d;

}

$B = array(-83.463135, 29.659416);$C = array(-83.638916, 29.869229);
$A = array(-84.012451, 30.069094); print_r(intersection($A,$B,$C));

[/php]

2. The mathematics looks correct, in particular the formulas for u and for x and y are correct.

The error seems to be in the programming. I don't know anything about PHP, but the line

$U =(($C[0] - $A[0])*($B[0]-$A[0]) + ($C[1] - $A[1])*($B[1]-$A[1]))/ pow(distance($A, $B,$C),2);

and the function distance ($C,$B,$A) look very odd. Shouldn't it just be distance ($B,$A), defined as sqrt(square($B[0],$A[0]) + square($B[1],\$A[1]))?

3. ## Direction error

The distance(A,B,C) function used the third coord to determine which
of the segment ab vs. bc was shorter...you are right though, and I since
have removed it to just return a single value.

I beat this thing to a pulp. The problem is with the direction of the segment. If its sloping upward to the right you have to be on the right side for it to work accurately...similar results with other directions (you have to be on the proper side of the segment).

So now I have to figure out how to make code to determine where you are in relationship to the segment and then swap signs or values to get