1

There are two connected lines (EPSG:4326 line1, line2). When the direction of the two lines is from line1 to line2, I want to do a calculation to determine whether the direction is left or right.

  • Welcome to GIS SE! As a new user be sure to take the Tour to learn about our focussed Q&A format. What GIS software are you using? – PolyGeo Aug 10 '18 at 6:21
  • I've answered for simple cartesian geometric lines. This will work in ESPG4326 as long as you consider it a cartesian system and not a sphere. I'm not sure that left and right are well-defined for great circle line segments on a sphere. – Spacedman Aug 10 '18 at 7:39
3

The dot product of two vectors, A and B, A.B, is the component of vector A in the direction of vector B. If this is positive then A is going forward with respect to B, and if it is negative then A is going backwards with respect to B.

If you rotate A by 90 degrees clockwise, to create A', then the dot product of A' with B tells you if A' is on the right or left of vector B, which is your turn status. Computing A' and A`.B is fairly simple arithmetic.

Here's an R function that takes two vector and return R (right turn) L (left turn) or S (straight ahead or straight back):

# helper function that returns the length:
d <- function(v){
  sqrt(sum(v^2))
}

turn <- function(v1, v2){
    ## v1 and v2 are vectors with (x,y) components.

    ## scale to unit length
    v1 = v1 / d(v1)
    v2 = v2 / d(v2)

    ## rotate 90 degrees
    v1r = c(v1[2], -v1[1])

    ## compute dot product
    v1r.v2 = v1r[1]*v2[1] + v1r[2]*v2[2]
    if(v1r.v2 > 0){
        return("R")
    }
    if(v1r.v2 < 0){
        return("L")
    }
    return("S")

}

Here's the output from my test plot which colours red arrows for right turns from the black direction, and green for left turns:

test plot

If you want to do this with simple line segments defined as (x1,y1)->(x2, y2), use the vectors (x2-x1, y2-y1).

You can use the magnitude as well as the sign of the dot product to decide if a turn is "slight left" (perhaps 0 to 45 degrees left) or "sharp left" (more than 135 degrees, ie almost back on yourself).

  • what is mean 'd()' function? – Byung-Jo Kim Aug 13 '18 at 3:03
  • Good spot! d(x) returns the distance length of x using Pythagoras' theorem. I've included it now. – Spacedman Aug 13 '18 at 6:46
  • it looks like R code. for example... can I run it like this # inputV1= cbind(c(0, 0), c(2, 2)); # inputV2= cbind(c(2, 2), c(3, 0)); # turn(inputV1, inputV2) but.. answer is 'S' (expected value is 'R') – Byung-Jo Kim Aug 13 '18 at 9:41
  • No - in this context a "vector" has two components, like it's a line starting from (0,0). Because you didn't say if you were interested in a particular implementation, or say what your data looked like, I explained the calculation, I explained the calculation and did not spend much time explaining the code. Subtract your "start" coordinate from your "end" coordinate to get the vector. turn(c(2,2)-c(0,0), c(3,0)-c(2,2)) is "R". The turn direction doesn't matter where the line segments start, only their direction. – Spacedman Aug 13 '18 at 14:01

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.