Page 1 of 1

Calculate Area Of Polygons And Irregular Area Rate Topic: ***** 1 Votes

#1 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 16 January 2011 - 11:41 AM

Polygon and irregular area calculation

Years ago I was helping a friend to do some land surveying for area and elevation contour lines. At the time my knowledge of programming was limited to some Fortran IV and a little bit of Wang Basic. Optical theodolites were the only ones in existence and desktop computers were just starting to appear, so the mainframes were the only really available options, but you didn't have access to the computer, you would write the program flow diagram, write the code, punch the cards with program and data and give them to an operator.

Our company's computer was at the accounting department and the computer programmer only worked on COBOL, so he was not able to convert my Fortran program and to compile it, so the survey data was processed by hand.

I had always had that on the back of my mind, and even though I have played a bit with assembler, basic and c, I never decided to write that program. I knew the algorithm was easy to implement but, no need for such a program 30 years later...

Lately I have been writing programs on visual basic for my own consumption and decided to develop that little program.

I see other people dividing polygons on triangles and irregular forms on tiny squares. The best resolution that the computer screen has is the DPI (points per linear inch or pixels) and the best accuracy is ˝ of a square pixel. The screen scale is different from computer to computer according to the settings, the CRT focus, and also it doesn’t correspond to real objects scale, but that can be achieved with the proper factor (squared).

My method of getting the area is to move from point to point on a path and use trapezium areas. These areas are the shadow under the line that connects two consecutive points on a Cartesian chart. Note that the computer screen has the “Y” axis inverted. It increases moving down. The result is the same regardless where you have your coordinate axis, or if you project the shadow to the X-axis or the Y-axis.

The formula for the area of a trapezium is:

Attached Image


But I will use all the distances to x=0 and y=0

A= ˝*(Y1+Y2)*(X2-X1) or A= ˝*(X1+X2)*(Y2-Y1)


Attached Image


The resulting area will be positive or negative depending on what direction we chose to advance on the path. We are calculating areas in excess, but when we advance on the other direction to close the area the excess will be neutralized and we will have a positive or negative balance that would be the area of the enclosed shape. An irregular area needs plenty more points in the path to be defined. But the process is the same.

The creation of the path depends on the type of shape.

On my program I click on the picurebox and fill an arraylist and a datagridview when creating the path for a polygon.

Attached Image
Attached Image

Private Sub PictureBox1_MouseClick(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PureBox1.Click  

Dim pt As Point  
Dim p As String  
Dim myBrush As New SolidBrush(Color.Red)  
Dim drawFormat As New StringFormat()  
Dim drawFont As New Font("Arial", 10, FontStyle.Bold)  
    
drawFormat.FormatFlags = StringFormatFlags.NoFontFallback  
Button4.Enabled = True  

pt.X = e.X  
pt.Y = e.Y  

p = "P" & (Count + 1).ToString  
    
DataGridView1.Item(0, Count).Value = e.X  
DataGridView1.Item(1, Count).Value = e.Y  

ThePts.Add(pt)  
myGraphics.DrawString(p, drawFont, myBrush, ThePts(Count).x + 4, ThePts(Count).y, drawFormat)  
myGraphics.DrawEllipse(Pens.Red, e.X, e.Y, 3, 3)  
Count += 1  
    
End Sub  



For the area I need some string and integer conversions to Double.

Private Function Area()  

Dim Ar As Double = 0  
Dim m As Integer  

For m = 0 To Count - 2  

Ar = Ar + (CDbl((myPoints(m).Y) + CDbl(myPoints(m + 1).Y)) * CDbl((myPoints(m + 1).X) - CDbl(myPoints(m).X)) / 2)  
Next  

Ar = Ar + ((CDbl(myPoints(0).Y) + CDbl(myPoints(m).Y)) * CDbl((myPoints(0).X) - CDbl(myPoints(m).X)) / 2)  
Ar = Ar / (myGraphics.DpiX * myGraphics.DpiY)  

Return Math.Abs(Ar) 'Clockwise/Counterclockwise  

End Function 



For the irregular shape I left-click and drag the mouse to fill an arraylist, clean the duplicated points, and then do some string manipulation.

Private Sub PictureBox1_MouseDown(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseDown  

iniPointX = e.X  
inipointY = e.Y  
TextBox32.Text = "" 
    
Select Case e.Button  
Case MouseButtons.Left  
eventString = "L" 
Case MouseButtons.Right  
eventString = "R" 
Case MouseButtons.Middle  
eventString = "M" 
Case MouseButtons.XButton1  
eventString = "X1" 
Case MouseButtons.XButton2  
eventString = "X2" 
Case MouseButtons.None  
eventString = Nothing  

End Select  

End Sub 


Private Sub PictureBox1_MouseMove(ByVal sender As Object, ByVal e As System.Windows.Forms.MouseEventArgs) Handles PictureBox1.MouseMove  

LocalMousePosition = PictureBox1.PointToClient(Cursor.Position)  
Dim myArray As Point() = {New Point(p1, q1), New Point(e.X, e.Y)}  
Dim myPath As New GraphicsPath  

Label19.Text = "(X=" & LocalMousePosition.X & "  " & "Y=" & LocalMousePosition.Y & ")" 

If eventString = "L" Then  
myPath.StartFigure()  
myPath.AddLines(myArray)  
myPath.CloseFigure()  
myGraphics.DrawPath(Pens.Blue, myPath)  

If Not (p1 = e.X And q1 = e.Y) Then 'Weed out consecutive points with same coordinates  

TextBox32.Text = TextBox32.Text & LocalMousePosition.X & "," & LocalMousePosition.Y & vbNewLine  

End If  

T_lines += 1 'Textbox Line #  

End If  

If eventString = Nothing Then  
myPath.Reset()  
myGraphics.Flush()  
End If  

p1 = e.X  
q1 = e.Y  

End Sub 



And use a different algorithm for the path construction.

Private Sub HandMovePoints()  

Dim counter As Integer = 2  
Dim list As String = Trim(TextBox32.Text)  
Dim pts() As String = TextBox32.Text.Split(CChar(vbNewLine)) '(New Char() {" "c})  
Dim pts1() As String  
Dim Area As Double  
Dim ArStruct As New ArrayList  
Dim myPath As New GraphicsPath  
Dim TransBrush As New SolidBrush(Color.FromArgb(128, 100, 255, 255))  

list = "" 

Dim word As String  

For Each word In pts  
If word.Length > 2 Then  
list = list & word & vbNewLine  
counter += 1  
End If  
Next  

TextBox32.Text = iniPointX.ToString & "," & inipointY.ToString & vbNewLine & list & iniPointX.ToString & "," & inipointY.ToString  

pts = Nothing  
Label2.Text = "Trace Points:" & (counter.ToString)  
pts = TextBox32.Text.Split(CChar(vbNewLine))  
Dim px(pts.Count + 1) As Point  
    
For counter = 0 To UBound(pts)  
Dim ms As New MyStruct  
pts1 = pts(counter).Split(","c)  
px(counter).X = CInt(pts1(0))  
px(counter).Y = CInt(pts1(1))  
ms.L = CDbl(pts1(0))  
ms.R = CDbl(pts1(1))  
ArStruct.Add(ms)  
Next  

px(UBound(pts)) = px(0)  
myGraphics.FillPolygon(TransBrush, px)  
For counter = 0 To ArStruct.Count - 2  
Area = Area + (ArStruct(counter).L + ArStruct(counter + 1).L) * (ArStruct(counter + 1).R - ArStruct(counter).R) / 2  
Next  

Area = Math.Abs(Area)  
Label3.Text = "Area= " & (Area / (myGraphics.DpiX * myGraphics.DpiY)).ToString & " In.˛" 
End Sub 



In both cases the last point is equal to the first one, but the program takes care of that automatically. Please note that the lines on the path should not intersect each other. On mousemove the click point is not detected so it's stored on a pubic variable.

I didn't take care of making the graphics permanent, so the drawing will disappear if the window is covered or a large picture scrolled.

You can play with this program, change the location of the coordinates axis, adapt it to your particular situation and change the way you input data. The results should be similar. On this case my textbox and datagridview are readonly, but that is just because this demo. There is also no error checking.

Attached File  Area of Polygon.zip (589.5K)
Number of downloads: 929

Is This A Good Question/Topic? 3
  • +

Replies To: Calculate Area Of Polygons And Irregular Area

#2 Raith  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 38
  • Joined: 06-May 11

Posted 14 May 2011 - 11:40 AM

Oh my, the math here is amazing.
Was This Post Helpful? 0
  • +
  • -

#3 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 14 May 2011 - 12:29 PM

View PostRaith, on 14 May 2011 - 11:40 AM, said:

Oh my, the math here is amazing.


Thank You!

You made my day.
Was This Post Helpful? 0
  • +
  • -

#4 mar09  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 1
  • Joined: 15-June 11

Posted 15 June 2011 - 01:50 PM

I had a question on the area calculation. In the area calculation with the for loop the equation is
area = area + ((point1_y + point2_y) * (point2_x - point1_x) / 2.0);

Then the area calculation for the first and last point uses equation
area = area + ((point1_y + point2_y) * (point1_x - point2_x) / 2.0);

The x coordinates are switched. Why is that?

Thanks! This article was very helpful :-)
Was This Post Helpful? 0
  • +
  • -

#5 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 17 June 2011 - 07:59 AM

Hi mar09

That's just nomenclature. We need to close the polygon, so the first point is the last one, but we have a last trapezium and we need to calculate that area too. The last point is not the last point, it is the one before the last, and the first one is the last one. It is used twice, one for the first trapezium and one for the last. Remember that the program closes the figure automatically by creating a last point with the coordinates of the first one.

Cheers,

ricardosms
Was This Post Helpful? 0
  • +
  • -

#6 MarkH007  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 2
  • Joined: 20-April 12

Posted 21 April 2012 - 01:21 PM

nice work. New to VB.net and you address several things I'm trying to figure out.
Was This Post Helpful? 0
  • +
  • -

#7 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 21 April 2012 - 03:28 PM

Thank you.

On this site you will find several experts on different fields that are willing to help you with your doubts and questions.
I you have a problem, post it and someone will help you.
Was This Post Helpful? 0
  • +
  • -

#8 MarkH007  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 2
  • Joined: 20-April 12

Posted 21 April 2012 - 06:26 PM

View Postricardosms, on 21 April 2012 - 03:28 PM, said:

Thank you.

On this site you will find several experts on different fields that are willing to help you with your doubts and questions.
I you have a problem, post it and someone will help you.


I have an idea to compute cross section area of an arbitrary section. Then drag a circle onto section to make a subtractive hole in the section. Have the program interactivally subtract out the hole (as I drag it across the section). I'm not sure the best way to do this.

My first thought was to just work with standard known shapes and look for intersections. That can get complicated fast. My lastest thought is to somehow find the outline of a arbitrary shape by finding the edge where pixels change color (colored shape). Not sure if that makes sense either. Could have an additive color and a subtractive color, then, add up the pixels of each color and equate that to area. An evolving idea.

I will keep thinking and looking at your site.
Your work helped understand the graphics and how VB.net deals with that.
I have used OWC11 in VBA code. It has worked well over the years, but, it is time to move on.
The coding here has been clear and readable (as much as it can be). I get lost on the Microsoft sites...

Thanks,
Mark
Was This Post Helpful? 0
  • +
  • -

#9 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 21 April 2012 - 07:12 PM

I have worked a bit with edges, but it is not too accurate, you need to check pixels above, below, forward and maybe diagonals. I guess you could count pixels on every row but that may be tedious.Also the edge detection usually will shift the image one pixel to the left. Doing it using lockbits may be a solution, otherwise it will be too slow. Clipping may give you the section, but not the area.
Was This Post Helpful? 0
  • +
  • -

#10 salih.abb  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 1
  • Joined: 06-February 13

Posted 06 February 2013 - 10:18 PM

nice work
Was This Post Helpful? 0
  • +
  • -

#11 minnie mouse  Icon User is offline

  • New D.I.C Head

Reputation: 0
  • View blog
  • Posts: 1
  • Joined: 05-August 13

Posted 05 August 2013 - 12:57 AM

can i get example answer for this vb.net question by using switch statement
Was This Post Helpful? 0
  • +
  • -

#12 ricardosms  Icon User is offline

  • D.I.C Regular
  • member icon

Reputation: 73
  • View blog
  • Posts: 301
  • Joined: 02-April 10

Posted 09 March 2014 - 07:42 AM

Hey minnie mouse

I'm sorry, I didn't log in for few months and I didn't see your post until now.


What do you mean with the switch statement. Where are you on the code?
Was This Post Helpful? 0
  • +
  • -

Page 1 of 1