.NET
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

Jig polyline and rotation keyword

3 REPLIES 3
Reply
Message 1 of 4
wojciech_janik
1841 Views, 3 Replies

Jig polyline and rotation keyword

Hallo,

 

I want to create jig to insert hallow slab (polyline) everything works fine until I am trying to use an added keyword for rotation then Autocad crashes really bad (no error inforamtion). Can anyone tell me what I am doing wrong? Here is a code, in comment place where program crashes.

 

Thanks

 

Ps: I've already been on through the interface and tried to use text jig but no result in my case 😞

 

Imports System
Imports Autodesk.AutoCAD.Runtime
Imports Autodesk.AutoCAD.ApplicationServices
Imports Autodesk.AutoCAD.DatabaseServices
Imports Autodesk.AutoCAD.Geometry
Imports Autodesk.AutoCAD.EditorInput

Namespace AutoCAD_VB_plug_in1

    Public Class MyCommands

        Inherits Autodesk.AutoCAD.EditorInput.DrawJig

        Dim BasePt As Point3d

        Dim angle As Double

        Dim myPR As PromptPointResult


        Function StartJig() As PromptPointResult

            Dim ed As Editor = Application.DocumentManager.MdiActiveDocument.Editor

            myPR = ed.Drag(Me)

            Do
                Select Case myPR.Status

                    Case PromptStatus.OK

                        Return myPR
                        Exit Do

                End Select

            Loop While myPR.Status <> PromptStatus.Cancel

            Return myPR

        End Function

        Protected Overrides Function Sampler(ByVal prompts As Autodesk.AutoCAD.EditorInput.JigPrompts) As Autodesk.AutoCAD.EditorInput.SamplerStatus

            Dim po As New JigPromptPointOptions(vbLf & "Position of slab")

            po.SetMessageAndKeywords(vbLf & "Specify position of slab or " & "[Rotate]", "R")

            myPR = prompts.AcquirePoint(po)

            If myPR.Status = PromptStatus.Keyword Then


                Select Case myPR.StringResult

                    Case "R"

                        angle = angle + 90 * Math.PI / 180

                        'Program crash here

                        Exit Select

                End Select

                Return SamplerStatus.OK

            ElseIf myPR.Status = PromptStatus.OK Then

                If myPR.Value.IsEqualTo(BasePt) Then

                    Return SamplerStatus.NoChange

                End If

                BasePt = myPR.Value

                Return SamplerStatus.OK

            End If

            Return SamplerStatus.Cancel

        End Function

        Protected Overrides Function WorldDraw(ByVal draw As Autodesk.AutoCAD.GraphicsInterface.WorldDraw) As Boolean

            Dim x As Integer = BasePt.X
            Dim y As Integer = BasePt.Y

            Dim c As Integer = 2
            Dim l As Integer = 600
            Dim b As Integer = 150
            Dim bk As Integer = 26
            Dim lk1 As Integer = 100
            Dim so As Integer = 10

            Dim acPoly As Polyline = New Polyline()

            acPoly.SetDatabaseDefaults()
            acPoly.AddVertexAt(0, New Point2d(x, y - c), 0, 0, 0)
            acPoly.AddVertexAt(1, New Point2d(x + bk / 2 + c, y - c), 0, 0, 0)
            acPoly.AddVertexAt(2, New Point2d(x + bk / 2 + c, y + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(3, New Point2d(x + b / 2, y + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(4, New Point2d(x + b / 2, y - l + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(5, New Point2d(x - b / 2, y - l + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(6, New Point2d(x - b / 2, y + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(7, New Point2d(x - bk / 2 - c, y + lk1 + so), 0, 0, 0)
            acPoly.AddVertexAt(8, New Point2d(x - bk / 2 - c, y - c), 0, 0, 0)

            acPoly.Closed = True

            Dim curUCSMatrix As Matrix3d = Application.DocumentManager.MdiActiveDocument.Editor.CurrentUserCoordinateSystem
            Dim curUCS As CoordinateSystem3d = curUCSMatrix.CoordinateSystem3d

            acPoly.TransformBy(Matrix3d.Rotation(angle, curUCS.Zaxis, BasePt))

            draw.Geometry.Polyline(acPoly, 1, 8)

        End Function

        <CommandMethod("DoJigA")> Sub DoJigA()

            StartJig()

        End Sub

    End Class

End Namespace

 

 

 

3 REPLIES 3
Message 2 of 4

From your Jig class, it is hard to tell what the purpose of the jig. if you are to draw a polyline from nothing, using EntityJig might be better option. DrawJig is usually used for presenting a visual clue of how an existing entity would be transformed. But for your case, I guess you use Jig to get the start point and a rotation angle for a fixed sized polyline to be drawn.

 

From your code I can see 2 issues:

 

1. The code crash when user select keywork "R", while moving cursor is OK. You may want to try a loop to enclose the prompts.AcquirePoint(), so that user enters keywork, the code set variable "angle" and loop back to prompts.AcquirePoint(). It only breaks out the loop the PromptResult is OK or Cancel. Something like:

 

Protected Overrides Function Sampler(ByVal prompts As Autodesk.AutoCAD.EditorInput.JigPrompts) As Autodesk.AutoCAD.EditorInput.SamplerStatus

Do
            Dim po As New JigPromptPointOptions(vbLf & "Position of slab")

            po.SetMessageAndKeywords(vbLf & "Specify position of slab or " & "[Rotate]", "R")

            myPR = prompts.AcquirePoint(po)

            If myPR.Status = PromptStatus.Keyword Then


                Select Case myPR.StringResult

                    Case "R"

                        angle = angle + 90 * Math.PI / 180

                        'Program crash here

                        Exit Select

                End Select

                ''Remove this
                ''Return SamplerStatus.OK

            ElseIf myPR.Status = PromptStatus.OK Then

                If myPR.Value.IsEqualTo(BasePt) Then

                    Return SamplerStatus.NoChange

                End If

                BasePt = myPR.Value

                Return SamplerStatus.OK

            End If

 

Loop While (True)

            Return SamplerStatus.Cancel

        End Function

 

I guess the crash has something to do with the fact that in your code, if user enter keywork R, the sSampler()method still returns samplerStatus.OK, which triggers WorldDraw(), but somehow, the BasePt is unchanged, thus some calculation in the WorldDraw() cannot go ahead (I did not looked into, though).

 

2. The biggest issue I can see is taht in the WorldDraw() method, your code actaully create many (or too many) polyline objects without dispose them. With minor move of the mouse, the WorldDraw(0 is triggered, and a polyline object is created, and only used for rendering a visual image and yoru code leave it behind. If user drag the Jig for a few seconds, there could be hundreds of thousands of polyline being created in the memory.

 

You shold create a polyline at class level, and only update/transform it in WordDraw() for the changed location/angle. And at the end of the Jig, you either add this Polylne into database (that is why I suggest to use EntityJig), or retrieve the points/angle to update existing polylne and dispose the polyline iin the Jig class (you may implement IDisposable interface).

 

 

Norman Yuan

Drive CAD With Code

EESignature

Message 3 of 4

Hallo Thanks for your feedback and your time. The problem was in StartJig function I didn't protected case when PromptStatus is Keyword. The correct code for this function is:

 

 

        Function StartJig() As PromptPointResult
            Dim ed As Editor = Application.DocumentManager.MdiActiveDocument.Editor
            Dim stat As PromptStatus = PromptStatus.Keyword
            While stat = PromptStatus.Keyword
                Dim res = ed.Drag(Me)
                stat = res.Status
                If stat <> PromptStatus.OK AndAlso stat <> PromptStatus.Keyword Then
                    Return myPR
                End If
            End While
            Return myPR
End Function



 

I have got two more questions.

 

1. Like you mentioned before I don't know how to dispose DrawJig, (debbuger asks me Forgot to Dispose?). How should I use or where I can learn about IDisposable interface

 

2. EntityJig will be better for my function. Still I am learing how to do it. When I finish it i will paste a code, maybe it will be helpful to someone

Message 4 of 4

You are new-ing a Polyline in your worldDraw, this is what you need to dispose. Basically you need to dispose any AutoCAD entity that is NOT added to the database, because AutoCAD won't do it for you. The worldDraw callback is invoked quite often during the jig, which will lead to non neglectible leak in your code.

 

An easy way to do it is to use the "using" keyword along the Polyline you are creating.

 

There are many examples of Jigs on our blogs, please take a look if you are not familiar with it:

 

http://adndevblog.typepad.com/autocad/2012/10/autocadnet-lesson-7-jig.html

 

http://through-the-interface.typepad.com/through_the_interface/2010/12/jigging-an-autocad-polyline-w...

 

http://adndevblog.typepad.com/autocad/2012/05/how-to-combine-a-net-jig-and-messagefilter-to-catch-us...

 

Regards,

Philippe.



Philippe Leefsma
Developer Technical Services
Autodesk Developer Network

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

Post to forums  

Autodesk DevCon in Munich May 28-29th


Autodesk Design & Make Report

”Boost