# Android QuestionGet an angle between 2 lines

#### ilan

##### Expert
Longtime User
hi

i would like to rotate a polygon around his center.
i have already the formula for the center point my problem is how to get the angle

so what i do now is when i touch the screen i create a vector (polygon center (x,y)) and the touch x,y
so i have 1 line and this line is 0 angle (its the starting point) now when i move my finger i create everytime a new line (polygon center) and the new x,y and i want to rotate the polygon with the angle between both lines

i tried several formulas i found in the web but nothing gave me the result i wanted
i also found here something but still its not turning correctly. i get to a point where it turns back

does anyone can help me please?

the polygon center is the first point for both vectors! (like in the image)

#### ilan

##### Expert
Longtime User
great @udg and thanx a lot, do you have also b4j installed? can you try the example?

#### klaus

##### Expert
Longtime User
Try this routine:
B4X:
'Calculates the smaller angle between 2 lines defined by 2 points each
'cordinates line 1 point1 : x11, y11
'cordinates line 1 point2 : x12, y12
'cordinates line 2 point1 : x21, y21
'cordinates line 2 point1 : x22, y22
'Degrees = True result in degrees, Degrees = False result in radians
Public Sub CalcAngleBetween2Lines(xx11 As Double, yy11 As Double, xx12 As Double, yy12 As Double, xx21 As Double, yy21 As Double, xx22 As Double, yy22 As Double, Degree As Boolean) As Double
Private Angle As Double

Angle = Abs((ATan2D(y12 - y11, x12 - x11) - ATan2D(y22 - y21, x22 - x21)))

If Angle > 180 Then
Angle = 360 - Angle
End If

If Degree = True Then
Return Angle
Else
Return Angle *cPI / 180
End If
End Sub
Attached a small test project.

#### Attachments

• AngleBetween2Lines.zip
7.2 KB · Views: 207

#### udg

##### Expert
Longtime User
Hi Ilan, using Klaus' code you obtain same result as your getangle corrected as follows:

B4X:
Sub getangle (p1 As vector, p2 As vector,p0 As vector) As Double
Dim mr,ms As Double
mr = (p1.x-p0.x) / (p1.y-p0.y)
ms = (p2.x-p0.x) / (p2.y-p0.y)
Log("AtanD: "&ATanD(Abs((mr-ms)/(1+(mr*ms)))))
Return ATanD(Abs((mr-ms)/(1+(mr*ms))))
End Sub

fundamentally you missed the abs function.

udg

#### ilan

##### Expert
Longtime User
thank you very much @klaus now your example is working great only 1 little issue

when the degree is 180 it starts to go down
is it possible to keep going up until 359.99 then again 0?

#### ilan

##### Expert
Longtime User
Hi Ilan, using Klaus' code you obtain same result as your getangle corrected as follows:

B4X:
Sub getangle (p1 As vector, p2 As vector,p0 As vector) As Double
Dim mr,ms As Double
mr = (p1.x-p0.x) / (p1.y-p0.y)
ms = (p2.x-p0.x) / (p2.y-p0.y)
Log("AtanD: "&ATanD(Abs((mr-ms)/(1+(mr*ms)))))
Return ATanD(Abs((mr-ms)/(1+(mr*ms))))
End Sub

fundamentally you missed the abs function.

udg

with klaus example i get from 0 to 180 and then start from 180 get back to 0 with your updated example i get from 0 to 9- and then back to 0 and then back to 90 and then back to 0

#### klaus

##### Expert
Longtime User
A modified version:
B4X:
'Calculates the angle between 2 lines defined by 2 points each
'cordinates line 1 point1 : x11, y11
'cordinates line 1 point2 : x12, y12
'cordinates line 2 point1 : x21, y21
'cordinates line 2 point1 : x22, y22
'Degrees = True result in degrees, Degrees = False result in radians
'Mode360 = True 0 - 360  Mode360 = False 0 -180 - 0
Public Sub CalcAngleBetween2Lines(xx11 As Double, yy11 As Double, xx12 As Double, yy12 As Double, xx21 As Double, yy21 As Double, xx22 As Double, yy22 As Double, Degree As Boolean, Mode360 As Boolean) As Double
Private Angle As Double

If Mode360 = True Then
Angle = ATan2D(y12 - y11, x12 - x11) - ATan2D(y22 - y21, x22 - x21)
If Angle < 0 Then
Angle = 360 + Angle
End If
Else
Angle = Abs((ATan2D(y12 - y11, x12 - x11) - ATan2D(y22 - y21, x22 - x21)))
If Angle > 180 Then
Angle = 360 - Angle
End If
End If

If Degree = True Then
Return Angle
Else
Return Angle *cPI / 180
End If
End Sub
And the test project.

#### Attachments

• AngleBetween2Lines1.zip
7.3 KB · Views: 202

#### ilan

##### Expert
Longtime User
@klaus & @udg

thank you so much. klaus your code is perfect

i only changed 1 thing:

Angle = ATan2D(yy22 - yy21, xx22 - xx21)-ATan2D(yy12 - yy11, xx12 - xx11)

i wanted the degrees to go CW but everything is perfect thank you very much!!

and also lots of thanx to @udg.

(such great people here )

#### Beja

##### Expert
Longtime User
Klaus, UDG and Ilan
Thanks guys for this very useful solution.. I benefit from it as well.
If we added the length of the line to the angle then we can find absolute location on the screen with a single number, instead of the x,y coords. (in a special application)

#### ilan

##### Expert
Longtime User
If we added the length of the line to the angle

B4X:
Sub distance(x1 As Float, x2 As Float, y1 As Float, y2 As Float) As Double
Return Sqrt(Power(x2-x1,2)+Power(y2-y1,2)) 'simple distance calculation
End Sub

#### ilan

##### Expert
Longtime User
is this what you wanted @Beja ?

#### Attachments

• t8.zip
1.3 KB · Views: 192

#### ilan

##### Expert
Longtime User

thank you so much guys!!! Big Respect from me

Last edited:

#### klaus

##### Expert
Longtime User
@Beja
In geometry you have two coordinate systems:
- cartesian: which uses x and y
- polar: which uses angle and distance
Anyway, both need two coordinates.
Conversion:
B4X:
x = r * Cos(a)
y = r * Sin(a)

r = Sqrt(x * x + y * y)
a = ATan2(y, x)

#### Informatix

##### Expert
Longtime User
You can also spare you a lot of headaches by using the math functions of libGDX or Steering Behaviors (e.g. AngleWith, GetAngleWith) for such computations. You're not the first to have such needs; they are already covered by most game libraries.

Replies
38
Views
4K
Replies
18
Views
2K
Replies
2
Views
4K
Replies
34
Views
51K
Replies
49
Views
80K