Search code examples
c++c++11mathmathematical-expressions

Need to draw ">" shape on beginning of line


Lines in 2d Plane

I have a line drawn in red color(basically, i have co-ordinates (x1,y1) and (x2,y2)). Now I'm supposed to draw two line which are in green color intersecting at the beginning point of line(x1, y1)

The red line can be in any angle, so i need some help here. How do i mathematically get the co-ordinates for two green lines. i.e. I already have (x1, y1), so i need (x3, y3) and (x4, y4)

Angle between green lines should be between 85 to 90 degrees, and length of each green line should not exceed 10pixels(Fixed size)

I have an API to draw a line which expects the co-ordinates, so I need code to calculate co-ordinates for green line in C++/C++11.


Solution

  • First step: compute a "vector" of length 10 in the direction of red line you have:

    v = 10 * (x1-x2, y1-y2) / length of (x1-x2, y1-y2)
    

    The length of a vector comes from Pythagoras: the length of (X,Y) is sqrt(X*X+Y*Y). There is a standard math library function for this: std::hypot.

    This vector should be pointing to the same side where you want the green lines.

    The second step is rotating this vector v by a 45 degree angle to both sides, giving you vectors representing the two green lines. The general formulation of rotation would give you this:

    green1 = (v.x cos(45) - v.y sin(45), v.x sin(45) + v.y cos(45))
    green2 = (v.x cos(45) + v.y sin(45), -v.x sin(45) + v.y cos(45))
    

    Thanks to the 45 degree angle being special this will simplify a lot: cosine and sine have the same value cos(45) = sin(45) = sqrt(1/2).

    Once you have these two vectors, you just need to add them to (x1,y1).

    Putting it all together:

    length_of_red = std::hypot(x1 - x2, y1 - y2);
    sqrt_half = std::sqrt(.5);
    
    x = 10*(x1 - x2) / length_of_red;
    y = 10*(y1 - y2) / length_of_red;
    x3 = x1 + sqrt_half*(x - y);
    y3 = y1 + sqrt_half*(x + y);
    x4 = x1 + sqrt_half*(x + y);
    y4 = y1 + sqrt_half*(-x + y);