Distance from a point to a polygon
If you have a working point to line segment distance function, you can use it to calculate the distance from the point to each of the edges of the polygon. Of course, you have to check if the point is inside the polygon first.
Your best bet is to iterate over all the lines and find the minimum distance from a point to a line segment.
To find the distance from a point to a line segment, you first find the distance from a point to a line by picking arbitrary points P1
and P2
on the line (it might be wise to use your endpoints). Then take the vector from P1
to your point P0
and find (P2-P1) . (P0 - P1)
where .
is the dot product. Divide this value by ||P2-P1||^2
and get a value r
.
Now if you picked P1
and P2
as your points, you can simply check if r
is between 0 and 1. If r
is greater than 1, then P2
is the closest point, so your distance is ||P0-P2||
. If r
is less than 0, then P1
is the closest point, so your distance is ||P0-P1||
.
If 0<r<1
, then your distance is sqrt(||P0-P1||^2 - (r * ||P2-P1||)^2)
The pseudocode is as follows:
for p1, p2 in vertices:
var r = dotProduct(vector(p2 - p1), vector(x - p1))
//x is the point you're looking for
r /= (magnitude(vector(p2 - p1)) ** 2)
if r < 0:
var dist = magnitude(vector(x - p1))
else if r > 1:
dist = magnitude(vector(p2 - x))
else:
dist = sqrt(magnitude(vector(x - p1)) ^ 2 - (r * magnitude(vector(p2-p1))) ^ 2)
minDist = min(dist,minDist)
In the event that this helps someone else, I reverse engineered doverbin's answer to understand why it worked showing graphically what the three cases are computing. (doverbin, feel free to incorporate this into your answer if you wish.)