Options

# Lines and angles from points

edited June 2013

(Originally posted by gjermund on 10/03/2007)

Hello
This is my problem:
I would like to measure salmon hearts by 5 lengths and one angle. All of the above are defined by 4 points, see fig a. The lengths are the distances between P1-P2, P1-P3, P2-P3, P3-P4 and P4 - Line 1 (on the line between P3 and P4) green line in fig b. Finally I would like to measure the angle between line L1 and L4, see AF1 in fig c.

We have 6000 hearts, and need a macro that can measure these parameters based on the four points, which will have to be put in interactively with the mouse.

Appreciate any good tips on macro functions that can do this. Thanks.

• Options

(Originally posted by KevinR on 10/3/2007)

The simplest way would be to prompt the user to draw the polygon using either the AOI or annotation tool, then look at the points in the polygon and calculate the geometric properties thereof.

I would run a small loop that prompts the user with IpDocClick to click on the various points, drawing an annotation line with IpAnCreateObj( ) for each segment. After the 4th point draw the last connecting line, use IpAnGet with GO_ATTR_NUMPOINTS and GO_ATTR_POINTS to obtain the points for the lines, and then calculate your values using sin, cos, and atan.

• Options
edited June 2013

(Originally posted by KevinR on 10/8/2007)

Here's a few useful IpBasic routines for this sort of calculation. OffsetToAngle( ) converts an X and Y distance (from the differences between two points, for example) into an angle. TrimAngle is a utility function that makes certain angles remain between 0-2*pi. AngleDiff( ) gives you the difference between two angles.

Lengths of lines defined by two points are simple geometry, the Euclidian distance:

```
Length = [ (x1-x2)^2 + (y1-y2)^2 ] ^0.5
```

Here's the set of utility routines. These are written so that zero degrees is a vertical line, pointing to 12 o-clock as you look at the screen. This matches with angles produced by Count/Size, for example.

```
Const PI = 3.14159265

Function TrimAngle(angle As Single) As Single
If angle = 0.0 Then
TrimAngle = 0.0
Exit Function
End If

Do Until angle > 0.0
angle = angle + 2.0 * PI
Loop

Do Until angle <= 2.0 * PI
angle = angle - 2.0 * PI
Loop

TrimAngle = angle
End Function

Function OffsetToAngle(xOff As Long, yOff As Long) As Single
If xOff = 0 Then
If yOff < 0 Then
OffsetToAngle = 0.0
Else
OffsetToAngle = PI
End If
Else
OffsetToAngle = Atn(CSng(yOff)/CSng(xOff))
If xOff >= 0 And yOff >= 0 Then
' No change
ElseIf xOff < 0 And yOff >= 0 Then
OffsetToAngle = PI + OffsetToAngle
ElseIf xOff < 0 And yOff < 0 Then
OffsetToAngle = PI + OffsetToAngle
Else
OffsetToAngle = 2.0 * PI + OffsetToAngle
End If
End If
OffsetToAngle = OffsetToAngle + PI/2.0
OffsetToAngle = TrimAngle(OffsetToAngle)

End Function

Function AngleDiff(ByVal angle1 As Single, ByVal angle2 As Single) As Single
Dim diff1 As Single, diff2 As Single

diff1 = Abs(angle1 - angle2)

If angle1 > angle2 Then
angle2 = angle2 + 2.0*PI
Else
angle1 = angle1 + 2.0*PI
End If

diff2 = Abs(angle1 - angle2)

If diff1 < diff2 Then
AngleDiff = diff1
Else
AngleDiff = diff2
End If
End Function
```

For information such as distance between points and a line, projections of one line on another, and other geometric calculations, I would recommend checking with a geometry text or Googling the measurement of interest for the basic equations. Searching on "distance between point and line" gave the essential equations in four of the first five references.

• Options

(Originally posted by gjermund on 10/15/2007)

Thanks! The advice was just what I needed!
I now have a macro that does all the neccessary calculations from the four points.