VBA
Discuss AutoCAD ActiveX and VBA (Visual Basic for Applications) questions here.
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Polyline X,Y,Area source code

12 REPLIES 12
Reply
Message 1 of 13
Anonymous
3408 Views, 12 Replies

Polyline X,Y,Area source code

 Hi All

 

I need a help to implement polyline function to give an output text file of X,Y coordinate and Area of selected and the entire portion of a plan.

 

Expecting everyone's kind help 

 

 

12 REPLIES 12
Message 2 of 13
Alfred.NESWADBA
in reply to: Anonymous

Hi,

 

welcome @Anonymous.autodesk.com!

 

Please show us your code, so we know where you are and at which position you have difficulties.

 

- alfred -

------------------------------------------------------------------------------------
Alfred NESWADBA
ISH-Solutions GmbH / Ingenieur Studio HOLLAUS
www.ish-solutions.at ... blog.ish-solutions.at ... LinkedIn ... CDay 2024
------------------------------------------------------------------------------------

(not an Autodesk consultant)
Message 3 of 13
Anonymous
in reply to: Alfred.NESWADBA

Thank you @Alfred.NESWADBA

 

Here is a screenshot and dll file

Message 4 of 13
Alfred.NESWADBA
in reply to: Anonymous

Hi,

 

a dll-file is not attached ... and even if there would be one I would never open it (out of security reasons).

 

I meant to show the source code where you are at the moment.

 

- alfred -

------------------------------------------------------------------------------------
Alfred NESWADBA
ISH-Solutions GmbH / Ingenieur Studio HOLLAUS
www.ish-solutions.at ... blog.ish-solutions.at ... LinkedIn ... CDay 2024
------------------------------------------------------------------------------------

(not an Autodesk consultant)
Message 5 of 13
Anonymous
in reply to: Alfred.NESWADBA

/*ClassLibrary code*/

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Autodesk.AutoCAD.ApplicationServices;
using Autodesk.AutoCAD.DatabaseServices;
using Autodesk.AutoCAD.Geometry;
using Autodesk.AutoCAD.EditorInput;
using Autodesk.AutoCAD.Runtime;


namespace ClassLibrary1
{
public class Class1
{
[CommandMethod("CalculateDefinedArea")]
public static void CalculateDefinedArea()
{
// Prompt the user for 5 points
Document acDoc = Application.DocumentManager.MdiActiveDocument;

PromptPointResult pPtRes;
Point2dCollection colPt = new Point2dCollection();
PromptPointOptions pPtOpts = new PromptPointOptions("");

// Prompt for the first point
pPtOpts.Message = "\nSpecify first point: ";
pPtRes = acDoc.Editor.GetPoint(pPtOpts);
colPt.Add(new Point2d(pPtRes.Value.X, pPtRes.Value.Y));

// Exit if the user presses ESC or cancels the command
if (pPtRes.Status == PromptStatus.Cancel) return;

int nCounter = 1;

while (nCounter <= 4)
{
// Prompt for the next points
switch (nCounter)
{
case 1:
pPtOpts.Message = "\nSpecify second point: ";
break;
case 2:
pPtOpts.Message = "\nSpecify third point: ";
break;
case 3:
pPtOpts.Message = "\nSpecify fourth point: ";
break;
case 4:
pPtOpts.Message = "\nSpecify fifth point: ";
break;
}

// Use the previous point as the base point
pPtOpts.UseBasePoint = true;
pPtOpts.BasePoint = pPtRes.Value;

pPtRes = acDoc.Editor.GetPoint(pPtOpts);
colPt.Add(new Point2d(pPtRes.Value.X, pPtRes.Value.Y));

if (pPtRes.Status == PromptStatus.Cancel) return;

// Increment the counter
nCounter = nCounter + 1;
}

// Create a polyline with 5 points
using (Polyline acPoly = new Polyline())
{
acPoly.AddVertexAt(0, colPt[0], 0, 0, 0);
acPoly.AddVertexAt(1, colPt[1], 0, 0, 0);
acPoly.AddVertexAt(2, colPt[2], 0, 0, 0);
acPoly.AddVertexAt(3, colPt[3], 0, 0, 0);
acPoly.AddVertexAt(4, colPt[4], 0, 0, 0);

// Close the polyline
//acPoly.Closed = true;

acPoly.Length.ToString();


// Query the area of the polyline
Application.ShowAlertDialog("Area of polyline: " +
acPoly.Area.ToString());

// Dispose of the polyline
}
}
[CommandMethod("CalulatePerimeter")]
public static void CalculateDefinedPerimeter()

{
// Prompt the user for 5 points
Document acDoc = Application.DocumentManager.MdiActiveDocument;

PromptPointResult pPtRes;
Point2dCollection colPt = new Point2dCollection();
PromptPointOptions pPtOpts = new PromptPointOptions("");

// Prompt for the first point
pPtOpts.Message = "\nSpecify first point: ";
pPtRes = acDoc.Editor.GetPoint(pPtOpts);
colPt.Add(new Point2d(pPtRes.Value.X, pPtRes.Value.Y));

// Exit if the user presses ESC or cancels the command
if (pPtRes.Status == PromptStatus.Cancel) return;

int nCounter = 1;

while (nCounter <= 4)
{
// Prompt for the next points
switch (nCounter)
{
case 1:
pPtOpts.Message = "\nSpecify second point: ";
break;
case 2:
pPtOpts.Message = "\nSpecify third point: ";
break;
case 3:
pPtOpts.Message = "\nSpecify fourth point: ";
break;
case 4:
pPtOpts.Message = "\nSpecify fifth point: ";
break;
}

// Use the previous point as the base point
pPtOpts.UseBasePoint = true;
pPtOpts.BasePoint = pPtRes.Value;

pPtRes = acDoc.Editor.GetPoint(pPtOpts);
colPt.Add(new Point2d(pPtRes.Value.X, pPtRes.Value.Y));

if (pPtRes.Status == PromptStatus.Cancel) return;

// Increment the counter
nCounter = nCounter + 1;
}

// Create a polyline with 5 points
using (Polyline acPoly = new Polyline())
{
acPoly.AddVertexAt(0, colPt[0], 0, 0, 0);
acPoly.AddVertexAt(1, colPt[1], 0, 0, 0);
acPoly.AddVertexAt(2, colPt[2], 0, 0, 0);
acPoly.AddVertexAt(3, colPt[3], 0, 0, 0);
acPoly.AddVertexAt(4, colPt[4], 0, 0, 0);

// Close the polyline
//acPoly.Closed = true;

acPoly.Length.ToString();


// Query the area of the polyline
Application.ShowAlertDialog("Length of polyline:-" + acPoly.Length.ToString());

// Dispose of the polyline
}
}
}


}

 

I'm able to calculate Area, iPerimeter from this.ButI can't get exact vertices for marking to get the proper measurements. In addition i would like to have the output to be displayed in a pop-up text window like below

 

x= 66  x'=66

y=60  y'=60

Area= 3960

 

It is better to have an option to get this parameter in an Excel file too.

 

Tool              :     Cadsofttool
Language      :     C#
Framwork      :     3.5
.Net              :    2012
 
Also another issue, I couldn't open any AutoCAD dwg file with this program.so i need a code that must be compatible to above program to open DWG file in this Cadsofttool.Or give me a solution to implement the above-mentioned function in CAD editor.
 

 

Message 6 of 13
Alfred.NESWADBA
in reply to: Anonymous

Hi,

 

>> open DWG file in this Cadsofttool.Or give me a solution to implement the above-mentioned function in CAD editor.

Please ask the vendor or that tool, or search for a forum that discusses development based on that tool.

I don't know their API and this forum (VB for AutoCAD) does not handle that tool.

 

This code here is not VB or VBA, it's C#.

Also it uses directly the AutoCAD API, maybe that the tool "Cadsofttool" works based on AutoCAD then it might work, but that's all guessing now.

 

Sorry, - alfred -

------------------------------------------------------------------------------------
Alfred NESWADBA
ISH-Solutions GmbH / Ingenieur Studio HOLLAUS
www.ish-solutions.at ... blog.ish-solutions.at ... LinkedIn ... CDay 2024
------------------------------------------------------------------------------------

(not an Autodesk consultant)
Message 7 of 13
Anonymous
in reply to: Anonymous

Hi, i'm not sure if your intention is to generate polylines and export values.

I'm making that task  by inversing the process.

 

i will write pseudo code, if needed i can write the full one and deliver in few days.

 

 

dim POLYAREA as double

dim PERIMETER as double

dim stringpolydata as string

query polyline from model

select polyline

add to selection

lock document

open transaction

get id of selection

POLYAREA = polylineID.area

perimeter=  by method or simple math iteration through vertices x,y deltas

stringdatapoly = polyarea & format delimiter & perimeter convert to string, round decimals, format the string etc.

close and dispose transaction

unlock document

use streamwriter to write the data in external txt file

embed variable into msgbox("data: " & stringpolydata)

in excel create file with data connection to point the path of streamwriter export txt (you can use csv formating here same as stringdata poly)

let me know if needed to work on code or this is enough for you.

 

Message 8 of 13
Anonymous
in reply to: Anonymous

Hello Kacarikalen

 

I'm glad to hear from you. It will be kind if you could help in this coding.

 

Here i can explain to you the Aim of my program

Case 1

1) Import the AutoCAD DWG file to open in developing software

2) Implement polyline function to calculate x,y, length , Area and Perimeter.(including the measurement of polygonal plan)

3) get the measurements of selected portions such as Bedroom /kitchen so on.  In general, like on AutoCAD by using a polyline to get inner and outer measurements.

3)Display the output in a pop-up text file like on AutoCAD.

4) it is good to have the result to be download in excel file

 

 

if you still have any doubt, please feel free to ask me

 

Best Regards

Wintereskimo

 

Message 9 of 13
Anonymous
in reply to: Anonymous

Hello again wintereskimo, 

 

thank you for providing me more details.

 

I will code that today/tomorrow for you. 🙂

 

Take care!

Message 10 of 13
Anonymous
in reply to: Anonymous

That sounds awesome..

 

talk to you soon..

 

Regards

wintereskimo

Message 11 of 13
Anonymous
in reply to: Anonymous

Hi, here is your code as i promised.

I'm sorry for slight delay, i was in rush and couldn't write it earlier.

Please let me know if you like it, however i'd extend the options more but i believe this is enough to get you going. I know the struggle and feel when you can't find the resources.

 

I've also added some extra options which you may find useful when working with this similar tasks.

 

please open blank dll project...

add winform item named form1 to solution and drop the savefiledialog from toolbox onto the form, add one button and one textbox.

 

you need to have a layer named "polylinelayer" in dwg and polylines on that layer but this can be changed in various ways to improve the usability

 

 

this is the code for dll ... class1.vb

 

Imports Autodesk.AutoCAD.ApplicationServices
Imports Autodesk.AutoCAD.Colors
Imports Autodesk.AutoCAD.ComponentModel
Imports Autodesk.AutoCAD.DatabaseServices
Imports Autodesk.AutoCAD.EditorInput
Imports Autodesk.AutoCAD.Geometry
Imports Autodesk.AutoCAD.GraphicsSystem
Imports Autodesk.AutoCAD.Internal
Imports Autodesk.AutoCAD.LayerManager
Imports Autodesk.AutoCAD.PlottingServices
Imports Autodesk.AutoCAD.Publishing
Imports Autodesk.AutoCAD.Runtime
Imports Autodesk.AutoCAD.Windows

Imports System.Windows.Forms

Imports System.IO
Imports System.Math
Imports System.Reflection
Imports System.Resources
Imports System.Runtime
Imports System.Dynamic
Imports System.Data

Imports System.Globalization

Imports System
Imports System.Collections.Generic
Imports System.Linq
Imports System.Text
Imports System.Threading

Imports XYsourcecode.Form1


Public Class Class1
    ' !!!!!!!!!!
    'this is hardcoded layer name, this can be obtained by selecting iterations from layer records
    'for the scope of this code in your working dwg there must be a layer with this name. !!! make a layer with name "polylinelayer"
    Public ply As String = "polylinelayer"

    'number of polylines
    Public polycount As Integer = 0

    'our value string, needs proper formating to get it more efficient i just wrote some description formatting
    Public Shared EXPORT_FORMATSTRING As String

    'this is to make sure that PLarea is done, you can implement threads on this
    Public process_thread As Boolean = False


    'this is your acad command
    <CommandMethod("areafrompolyline")>
    Public Sub areafrompolyline()

        'main sub
        PLarea()




        'if succeded open export form, i made this so you can move on after you get values
        If process_thread = True Then

            'opens form, you can continue from there
            Dim export_form As New Form1
            export_form.Show()

        Else
            MsgBox("haven't processed PLarea sub", MsgBoxStyle.Information)
        End If


    End Sub


    Private Sub PLarea()

        'counts the polylines
        EntitiesOnLayer(ply)

        'if there is a polyline get the values
        If polycount > 0 Then

            Dim doc As Document = Core.Application.DocumentManager.MdiActiveDocument
            Dim ed As Editor = doc.Editor
            Dim db As Database = doc.Database

            Using docloc As DocumentLock = doc.LockDocument()


                Dim PLINEidOBJdb As ObjectIdCollection = New ObjectIdCollection()

                'dxf code
                Dim filterlistPOL As TypedValue() = New TypedValue(1) {}
                filterlistPOL(0) = New TypedValue(0, "LWPOLYLINE")
                filterlistPOL(1) = New TypedValue(8, ply)

                'selection set
                Dim filterPOL As New SelectionFilter(filterlistPOL)
                Dim selPOLRes As PromptSelectionResult = ed.SelectAll(filterPOL)
                Dim POLids As ObjectId() = selPOLRes.Value.GetObjectIds()

                'polyline id collection
                PLINEidOBJdb = New ObjectIdCollection(POLids)

                Using ts As Transaction = db.TransactionManager.StartTransaction
                    Dim polilinije As New ObjectIdCollection(selPOLRes.Value.GetObjectIds())

                    'some description
                    EXPORT_FORMATSTRING = "Number of polylines: " & polycount & vbCrLf

                    'this is iterator to count polylines
                    Dim j As Integer = 1

                    'for loop to iterate for every polyline
                    For Each tid As ObjectId In polilinije
                        If tid.ObjectClass.Name.Equals("AcDbPolyline") Then


                            EXPORT_FORMATSTRING = EXPORT_FORMATSTRING

                            Using polylocker As DocumentLock = doc.LockDocument()

                                'get polyline values
                                Dim pl As Polyline = TryCast(ts.GetObject(tid, OpenMode.ForWrite), Polyline)
                                Dim plArea As Double = Math.Round(pl.Area, 2)
                                Dim plPerimeter As Double = Math.Round(pl.Length, 2)
                                Dim plVertexcount As Integer = pl.NumberOfVertices
                                Dim plSegment As Double

                                'using delimeters instead of vbclrf could increase productivity if you format your strings properly for upcoming processes
                                'notice the " " as delimiter so you can open it in excel
                                EXPORT_FORMATSTRING = EXPORT_FORMATSTRING & "polyline" & j & vbCrLf & "Area:" & " " & plArea & vbCrLf & "Perimeter:" & " " & plPerimeter & vbCrLf

                                'iterate through polyline segments between vertices and get distance value
                                For i As Integer = 0 To plVertexcount - 2

                                    Dim ln As LineSegment2d = pl.GetLineSegment2dAt(i)

                                    'this is the polyline segment value
                                    plSegment = ln.Length

                                    'round it to 2 decimal places, or more ofc
                                    plSegment = Math.Round(plSegment, 2)

                                    'format string for polyline segments
                                    EXPORT_FORMATSTRING = EXPORT_FORMATSTRING & "l" & (i + 1) & ":" & " " & plSegment & vbCrLf


                                    'move on next polylines segment
                                Next


                            End Using


                        End If
                        j = j + 1 'this just counts polylines


                        'moves on next polyline
                    Next


                    'we didnt stored any changed so it is important to abort the transaction
                    ts.Abort()

                End Using 'close transaction

            End Using

        Else

            MsgBox("There are no polylines on this layer", MsgBoxStyle.Information)

        End If

        'this is just for showing, it will open form
        process_thread = True


    End Sub


    Public Sub EntitiesOnLayer(ByVal ply As String)
        'this sub returns polyline entities count on layer where desired polylines are living

        Dim ents As ObjectIdCollection = GetEntitiesOnLayer(ply)

        'number of polylines 
        polycount = ents.Count

    End Sub

    Private Function GetEntitiesOnLayer(ByVal ply As String) As ObjectIdCollection
        'this function returns ids of polylines on layer with name stored in ply string variable

        Dim doc As Document = Core.Application.DocumentManager.MdiActiveDocument

        Dim ed As Editor = doc.Editor

        ' Build a filter list so that only entities
        ' on the specified layer are selected
        ' this is the DXF code specification
        '0 = DxfCode.entity
        '8 = DxfCode.LayerName

        Dim tvs As TypedValue() = New TypedValue(1) {}

        tvs(0) = New TypedValue(0, "LWPOLYLINE")

        tvs(1) = New TypedValue(8, ply)

        Dim sf As New SelectionFilter(tvs)
        Dim psr As PromptSelectionResult = ed.SelectAll(sf)
        'this is writen just to click ok
        If psr.Status = PromptStatus.OK Then

            Return New ObjectIdCollection(psr.Value.GetObjectIds())
        Else
            Return New ObjectIdCollection()
        End If
    End Function

End Class

 

 

this is the code for form1 class

i made it this way for you to get it easier, so you can export excel and move on winforms functions with that

just note about delimiters and you will be fine.

 

 

 

 

 

form1.JPGImports Autodesk.AutoCAD.ApplicationServices
Imports Autodesk.AutoCAD.Colors
Imports Autodesk.AutoCAD.ComponentModel
Imports Autodesk.AutoCAD.DatabaseServices
Imports Autodesk.AutoCAD.EditorInput
Imports Autodesk.AutoCAD.Geometry
Imports Autodesk.AutoCAD.GraphicsSystem
Imports Autodesk.AutoCAD.Internal
Imports Autodesk.AutoCAD.LayerManager
Imports Autodesk.AutoCAD.PlottingServices
Imports Autodesk.AutoCAD.Publishing
Imports Autodesk.AutoCAD.Runtime
Imports Autodesk.AutoCAD.Windows

Imports System.Windows.Forms



Imports System.IO
Imports System.Math
Imports System.Reflection
Imports System.Resources
Imports System.Runtime
Imports System.Dynamic
Imports System.Data

Imports System.Globalization

Imports System
Imports System.Collections.Generic
Imports System.Linq
Imports System.Text
Imports System.Threading

Imports XYsourcecode.Class1

Public Class Form1

    Public dr As DialogResult
    'you can define additional dialog options

    Public export As String = XYsourcecode.Class1.EXPORT_FORMATSTRING
    'notice that in class1 EXPORT_FORMATSTRING is shared declared


    Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load



        TextBox1.Text = export



    End Sub

    Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
        'opens dialog
        dr = SaveFileDialog1.ShowDialog


        SaveFileDialog1.Filter = "spreadsheet|*.xls|All files|*.*"
        ' PUT .xls AS FORMAT



        If dr = DialogResult.OK Then
            'gets path to save a file
            Dim savepath As String = SaveFileDialog1.FileName

            Dim file As StreamWriter

            file = My.Computer.FileSystem.OpenTextFileWriter(savepath, False)
            file.WriteLine(export) 'here in brackets goes the string 
            file.Close()
            MsgBox("File at destination " & vbCrLf & savepath & vbCrLf & " successfully saved!")
        Else
            'if you exit the dialog without saving
            MsgBox("Export cancelled by user", MsgBoxStyle.Information)

        End If
    End Sub


End Class

 

i hope you find this usefull.

 

This app could be done in many various ways, i've done it like this and still can be improved a lot, just a basic working example, now it is up to you to extend it how you like more. If you need coordinates x,y of vertices let me know, however you can get them in vertex iterations.

If you have any additional questions don't hesitate to ask, i'll help if i can and don't forget to kudo or solution accept please im here active just from 2 days ago but having account long time.

 

Have a nice day and please let me know your thoughts. 🙂

 

Message 12 of 13
Anonymous
in reply to: Anonymous

hello

 

thanks a lot for your immediate help. I will get back to you soon after test it.

will keep in contact with you !!

 

Best Regard

Winter

 

 

Message 13 of 13
Anonymous
in reply to: Anonymous

Hello,

I am sending details of project and problems in coding
 
 
Tools used 
1) Visual Studio 2012(VB.NET)
2) .net Framework 4.5
 
Problem:-
 
1) AutoCAD images are opening in picture box in bitmap(.bmp) format
2) Image quality is not clear.
 
 
Coding and one screen shot are here enclosed.

Can't find what you're looking for? Ask the community or share your knowledge.

Post to forums  

Forma Design Contest


Autodesk Design & Make Report