1

i am trying to find the perpendicular closest point to a line, given:

line is given by p1 and p2:
p1= [833974.3939975424, 10.741845010809124]
p2= [833972.1988621169, 9.989807874318076]

point: [833972.4500000001, 10.200000000000001]

I used these functions:


point1, point2 = nearest_points(shp.LineString([shp.Point(p1[0], p1[1]), shp.Point(p2[0], p2[1])]), shp.Point([point[0], point[1]]))

# and
line= shp.LineString([shp.Point(p1[0], p1[1]), shp.Point(p2[0], p2[1])])
pdist= line.project(shp.Point([point[0], point[1]]))
newpoint= line.interpolate(pdist)

when I use shapely functions, scikit-spatial, etc. I get the nearest non-perpendicular point as given in red (projected from green): points

PLease, if anyone can help: I have been trying for hours to project the red point perpendicular to the line. I couldnt find a proper similar stack overflow answer.

4
  • 4
    Please provide your code and expected vs. actual outcome. Note the scale of your two axes are different, so it won't look perpendicular. Commented Jun 10 at 15:16
  • better say the line is defined by the blue (p1) and yellow (p2) points, and the additional point is the green one. As required above give your code Commented Jun 10 at 15:27
  • If q is the point off the line and p1, p2 the two points on the line then just project q-p1 onto p2-p1 with a scalar product. The resulting point is p1+[q-p1,p2-p1](p2-p1)/[p2-p1,p2-p1], where [,] is about the only inline way of writing a scalar product. Commented Jun 10 at 15:39
  • added the code! Commented Jun 10 at 16:10

2 Answers 2

3

I stretched your image horizontally so that the visual distance of 0.5 units is the same horizontally as vertically:

enter image description here

Your calculation of the red point's coordinates seems to be fine.

Sign up to request clarification or add additional context in comments.

Comments

2

The distance from p1 to the base of the perpendicular will just be the dot product of q-p1 with a unit direction vector along the displacement p2-p1. Then just multiply this by the unit vector and add to p1.

import numpy as np

def perpendicular( p1, p2, q ):
   return p1 + np.dot( q - p1, p2 - p1 ) * ( p2 - p1 ) / np.dot( p2 - p1, p2 - p1 )


p1 = np.array( [ 833974.3939975424, 10.741845010809124 ] )
p2 = np.array( [ 833972.1988621169,  9.989807874318076 ] )
q  = np.array( [ 833972.4500000001, 10.200000000000001 ] )

print( perpendicular( p1, p2, q ) )

Output:

[8.33972488e+05 1.00888871e+01]

As already pointed out in comments, this won't look right unless your axis scales are the same, so preserving orthogonality.

1 Comment

ah thanks, so it's my axis scales that mess up so it doesn't look right!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.