Author Topic: Is there a way to make 2d poly retain shape when converting to poly  (Read 2751 times)

0 Members and 1 Guest are viewing this topic.

Proctor

  • Guest
Hello: I have code that converts objects to polylines (e.g. 2d to poly, spline to poly).
When my code converts most of the objects, the object still appears the same as what it did before; however,
a user allerted me of a few 2d polys that once converted, looked way different (see attached pic).

Here's my code for converting - it's fairly staight forward:
Code: [Select]

 Private Shared Function ConvertToPolylines(ByVal ids() As ObjectId, ByVal tr As Transaction) As List(Of Polyline)
        Dim polyList As New List(Of Polyline)

        Dim blockTable As BlockTable = tr.GetObject(HostApplicationServices.WorkingDatabase.BlockTableId, OpenMode.ForRead)
        Dim modelSpace As BlockTableRecord = tr.GetObject(blockTable(BlockTableRecord.ModelSpace), OpenMode.ForWrite)
        Dim sLayerName As String = "'"
        Try
            For Each id As ObjectId In ids
                Dim ent As Entity = tr.GetObject(id, OpenMode.ForWrite)
                If TypeOf ent Is Polyline Then
                    ' there is nothing to do
                    polyList.Add(ent)
                ElseIf TypeOf ent Is Polyline2d Then

                    Dim oldPoly As Polyline2d = ent
                    Dim newPoly As New Polyline

                    newPoly.SetDatabaseDefaults()
                    For Each vertId As ObjectId In oldPoly
                        Dim vert As Vertex2d = tr.GetObject(vertId, OpenMode.ForRead)
                        newPoly.AddVertexAt(newPoly.NumberOfVertices, New GE.Point2d(vert.Position.X, vert.Position.Y), 0, 0, 0)
                    Next
                    newPoly.Closed = oldPoly.Closed
                    Dim lLength As Double = newPoly.Length
                    Dim aArea As Double = newPoly.Area
                    ' add new object
                    modelSpace.AppendEntity(newPoly)
                    tr.AddNewlyCreatedDBObject(newPoly, True)
                    ' delete old one
                    oldPoly.Erase()
                    polyList.Add(newPoly)
                ElseIf TypeOf ent Is Ellipse Or TypeOf ent Is Circle Or TypeOf ent Is Spline Then
                    Dim curve As Curve = ent
                    Dim length As Double = AenLoop.GetCurveLength(ent)
                    Dim segmentNumber As Integer = length / kPolysegmentLength + 1
                    Dim newPoly As New Polyline
                    newPoly.SetDatabaseDefaults()
                    For i As Integer = 0 To segmentNumber
                        Dim param As Double = curve.StartParam + ((curve.EndParam - curve.StartParam) * i / segmentNumber)
                        Dim pt As GE.Point3d = curve.GetPointAtParameter(param)
                        newPoly.AddVertexAt(newPoly.NumberOfVertices, New GE.Point2d(pt.X, pt.Y), 0, 0, 0)
                    Next
                    ' it it is circle or ellipse then it is closed
                    newPoly.Closed = TypeOf ent Is Ellipse Or TypeOf ent Is Circle
                    ' add new object
                    modelSpace.AppendEntity(newPoly)
                    tr.AddNewlyCreatedDBObject(newPoly, True)
                    ' delete old one
                    curve.Erase()
                    polyList.Add(newPoly)
                End If
            Next

            Return polyList
        Catch ex As Autodesk.AutoCAD.Runtime.Exception
            MsgBox("ConvertToPolylines error: " & ex.Message)
            tr.Abort()
        Finally
        End Try
    End Function

Is there a way to have the object retain it's original shape when converting? Thanks,
Proctor

Jeff H

  • Needs a day job
  • Posts: 6150
Re: Is there a way to make 2d poly retain shape when converting to poly
« Reply #1 on: October 27, 2010, 04:10:19 PM »
For a 2dPoly you can try this.

It creates a new PolyLine then uses the PolyLine.ConvertFrom()

Here is info from the docs instead trying to sound smart and putting in my own words
Quote
This fills the Polyline with data from the Polyline2d pointed to by entity. entity must point to a SimplePoly or FitCurvePoly type of Polyline2d object in a database. This function should be called from an Polyline that is not yet database-resident.

If transferId is true, the calling Polyline will become database-resident. The calling Polyline will assume the ObjectId and handle, plus any extended entity data (except data on vertices), the extension dictionary, and reactors of the Polyline2d entity entity. entity will then be deleted and set to NULL.

If transferId is false, entity will remain in the database as is and the caller must close it. The resulting Polyline will not be database-resident, and if not appended to a database, should be deleted.




I tried setting the transferId to true but AutoCad hung up.
I also commented out to erase the the original PolyLine2d so you could compare.

Code: [Select]
<CommandMethod("PolyConvert")> _
        Public Sub PolyConvert()
            Dim doc As Document = Application.DocumentManager.MdiActiveDocument
            Dim db As Database = doc.Database
            Dim ed As Editor = doc.Editor
            Using trx As Transaction = db.TransactionManager.StartTransaction()
                Dim btrMs As BlockTableRecord = SymbolUtilityServices.GetBlockModelSpaceId(db).GetObject(OpenMode.ForRead)
                For Each objId As ObjectId In btrMs
                    Dim ent As Entity = objId.GetObject(OpenMode.ForRead)
                    If TypeOf ent Is Polyline2d Then
                        ent.UpgradeOpen()
                        btrMs.UpgradeOpen()
                        Dim polyLne As New Polyline
                        polyLne.ConvertFrom(ent, False)
                        ed.WriteMessage(vbCrLf & "Converted")
                        'ent.Erase()
                        btrMs.AppendEntity(polyLne)
                        trx.AddNewlyCreatedDBObject(polyLne, True)
                    End If
                Next
                trx.Commit()
            End Using
        End Sub

Also you might want look at Polyline2d.ConvertToPolyType() since there was no mention of SplineFit in docs
And PLINETYPE system variable.




kaefer

  • Guest
Re: Is there a way to make 2d poly retain shape when converting to poly
« Reply #2 on: October 28, 2010, 07:12:22 AM »
I tried setting the transferId to true but AutoCad hung up.

You might want to look up the DBObject.HandOverTo() Method, where it is written:
Quote
Note
This method is not allowed on objects that are transaction resident. If the object on which the method is called is transaction resident, then no handOverTo operation is performed and Acad::eInvalidContext is returned.

This leads me to suspect that something along those lines also should apply to Polyline.ConvertFrom().

Cf.
Code: [Select]
[<CommandMethod "MyPolyConvert">]
let polyConvert() =
    let doc = acApp.DocumentManager.MdiActiveDocument
    let db = doc.Database
    let ed = doc.Editor

    let btrMs = (SymbolUtilityServices.GetBlockModelSpaceId db).Open(OpenMode.ForWrite, false) :?> BlockTableRecord
       
    let n = ref 0
    for objId in btrMs do
        if typeof<Polyline2d> |> RXClass.GetClass |> objId.ObjectClass.IsDerivedFrom then
            let pl2d = objId.Open(OpenMode.ForWrite, false) :?> Polyline2d
            let polyLne = new Polyline()
            polyLne.ConvertFrom(pl2d, true)
            polyLne.Close()
            incr n
         
    btrMs.Close()
    ed.WriteMessage("\n{0} converted", !n)