I am having a fatal error while moving a line that has grip overrides on it. The line is connected to a data object which I call a slice. The slice has previous slices and next slices. When the line is moved by the grip I move the line and all previous and next lines from the MoveGripPointsAt method. All the lines move fine but when I go to select the line that had the move grip selected the error occurs. I set a debug in GetGripPoints method and I could step though it but when it returns from the method that is where the crash happens. The error is "Unhandled e0434f4dh Exception at fd78aa7dh". I have attached the two methods I talked about above. If you need more info let me know. The code will not run however unless you have all my dependant projects and saved data.
Public Overrides Sub GetGripPoints(ByVal entity As Autodesk.AutoCAD.DatabaseServices.Entity, _
ByVal grips As Autodesk.AutoCAD.DatabaseServices.GripDataCollection, _
ByVal curViewUnitSize As Double, _
ByVal gripSize As Integer, _
ByVal curViewDir As Autodesk.AutoCAD.Geometry.Vector3d, _
ByVal bitFlags As Autodesk.AutoCAD.DatabaseServices.GetGripPointsFlags)
Dim rb As ResultBuffer = GetData(entity)
'Only draw custom grips if we have valid data and entity is a Line
If (Not rb Is Nothing) And (TypeOf entity Is Line) Then
'Explode entity and use returned entity set to calc intersections whole overruled entity
Dim oEntity As Line = entity
Using entSet As New DBObjectCollection
SliceExplodeFragments(oEntity, entSet)
Dim frontline As Line = entSet.Item(0)
Dim backline As Line = entSet.Item(1)
'front stretch grip
Dim pt1 As Point3d = CAD.Functions.GetMidPoint(frontline.StartPoint, frontline.EndPoint)
Dim grip1 As New SliceFrontStretchGrip
grip1.Ordinal = 0
grip1.GripPoint = pt1
grips.Add(grip1)
'back stretch grip
Dim pt2 As Point3d = CAD.Functions.GetMidPoint(backline.StartPoint, backline.EndPoint)
Dim grip2 As New SliceBackStretchGrip
grip2.Ordinal = 0
grip2.GripPoint = pt2
grips.Add(grip2)
'front move grip
Dim pt3 As Point3d = frontline.StartPoint
Dim grip3 As New SliceMoveGrip
grip3.Ordinal = 0
grip3.GripPoint = pt3
grips.Add(grip3)
'back move grip
Dim pt4 As Point3d = backline.StartPoint
Dim grip4 As New SliceMoveGrip
grip4.Ordinal = 0
grip4.GripPoint = pt4
grips.Add(grip4)
End Using
Else
Stop
End If
End Sub
Public Overrides Sub MoveGripPointsAt(ByVal entity As Autodesk.AutoCAD.DatabaseServices.Entity, _
ByVal grips As Autodesk.AutoCAD.DatabaseServices.GripDataCollection, _
ByVal offset As Autodesk.AutoCAD.Geometry.Vector3d, _
ByVal bitFlags As Autodesk.AutoCAD.DatabaseServices.MoveGripPointsFlags)
''We only take action when we get this call on a database resident entity
''A dragging operation makes a shallow clone of line, and setting CloneMeForDragging to false is generally a bad idea.
''(If you do set CloneMeForDragging to false, then don't call base class overridden methods).
If entity.Id.IsValid Then
'Get slice data
Dim rb As ResultBuffer = GetData(entity)
'Only draw custom grips if we have valid data and entity is a Line
If (Not rb Is Nothing) And (TypeOf entity Is Line) Then
'Cast to a Line so we can access properties
Dim oEntity As Line = entity
Dim offsetDist As Double = offset.X
Dim oSlice As Graphics.CncSlice
' Lets see if the slice keyed by the entity id is in the table
If Graphics.CncSlice.Slices.ContainsKey(oEntity.ObjectId) = True Then
oSlice = Graphics.CncSlice.Slices.Item(oEntity.ObjectId)
Else
MsgBox("The slice keyed by " & oEntity.ObjectId.ToString & " is not in the slices table")
End If
''Iterate through list of all grips being moved
For Each g As GripData In grips
' see if it is the slice move grip
If TypeOf g Is SliceMoveGrip Then
' We are working with a move grip so lets move the slice. Now we need to call the move of the slice
oSlice.Move(offsetDist)
Dim ans As System.Windows.Forms.DialogResult ' holds if the form was canceled
' Lets see if there is a previous slice and ask what to do
If oSlice.PreviousSlice IsNot Nothing Then
' show the form
ans = Application.ShowModalDialog( _
New PromptForm("Adjust Previous Slice", _
"How do you want to handle the previous slice?", _
True, _
New PromptAction("Cancel", Nothing, Windows.Forms.DialogResult.Cancel, Nothing), _
New PromptAction("Do Nothing", Nothing, Windows.Forms.DialogResult.OK, Nothing), _
New PromptAction("Stretch", AddressOf oSlice.StretchPreviousSliceDuringSliceMove, Windows.Forms.DialogResult.OK, offsetDist), _
New PromptAction("Move", AddressOf oSlice.MovePreviousSliceDuringSliceMove, Windows.Forms.DialogResult.OK, offsetDist)))
End If
' See if the user canceled the operation
If ans = Windows.Forms.DialogResult.Cancel Then Exit Sub
' Lets see if there is a next slice and ask what they want to do
If oSlice.NextSlice IsNot Nothing Then
' show the form
ans = Application.ShowModalDialog( _
New PromptForm("Adjust Next Slice", _
"How do you want to handle the next slice?", _
True, _
New PromptAction("Cancel", Nothing, Windows.Forms.DialogResult.Cancel, Nothing), _
New PromptAction("Do Nothing", Nothing, Windows.Forms.DialogResult.OK, Nothing), _
New PromptAction("Stretch", AddressOf oSlice.StretchNextSliceDuringSliceMove, Windows.Forms.DialogResult.OK, offsetDist), _
New PromptAction("Move", AddressOf oSlice.MoveNextSliceDuringSliceMove, Windows.Forms.DialogResult.OK, offsetDist)))
End If
' Did the user cancel the operation
If ans = Windows.Forms.DialogResult.Cancel Then Exit Sub
End If
' see if it is the slice front stretch grip
If TypeOf g Is SliceFrontStretchGrip Then
End If
' see if it is the slice back stretch grip
If TypeOf g Is SliceBackStretchGrip Then
End If
Next
End If
End If
End Sub
I forgot to mension that when I move just the one slice without the previous and next slices the grip move works fine. The slice will stay highlighted in autocad and I can select it again fine. But when I move other entities then the error occurs.
Noticed that in GetGripPoints() method you use
If (Not rb Is Nothing) And ...Then
...
Else
Stop
End If
Using Stop statement, thouth being inherited from legacy Basic language and still legal in VB.NET, is totally not necessary and could do more bad than good. Since you methioned the error broke out at the end of GetGripPoints(), have you debugged into the method and the execution route could actually run through "Stop" statement?
In non-debuggung mode (running the code outside a debugger and the JIT debugging is not enabled, "Stop" is equivalent to "End" statement (another legacy statement in VB, which one should never use), which unconditionally terminate the code execution. If the VB code is an stand-alone app, it may be OK, but since this is Acad DLL, running in the same process as AutoCAD, it may cause fatal result.
See this link on the topic of "Stop" statement in VB.NET:
http://msdn.microsoft.com/en-us/library/8a094y2f.aspx
Even you can prove the error is not caused by the "Stop", I'd suggest you do not use it. In your code, that If...End If statement never needs a Else clause anyway.
The another issue (but unlikely being he cause of the error) is that you show a prompt window in MoveGripPointsAt() method without disposing it. So there couldbe many hidden forms end up staying memory used by AutoCAD, a kind of memory leak. It may not be a big issue, considering the prompt form may not have big memory foot print, but is not "best practice". You'd better use one single static/Shared instance of the prompt form for the entire couse of Acad session when the Overrule is loaded, or dispose the propt form after each time it shows.
If it turned out the "Stop" statement is not the error source, you may have to simplify your code be gradually stripping out the dependencies to re-produce the error until the code is simple enought and the source of error is identified.
Norman Yuan
I'm experiencing a similar problem i haven't be able to solve for one week. Autocad will throw a Unhandled acces violation when trying to stretch a custom grip applied by the grip overrule on polylines. The same thing will happen trying to copy the polyline.
Here is a copy of the Overrule Helper Class and a subset of the whole code wich will reproduce the error in attached file.
Friend Class UtilOverrules
Private Structure OverruleRec
Public Instance As Overrule
Public EntitéCiblée As RXClass
Public Sub New(ByVal _EntitéCiblée As RXClass, ByVal _Instance As Overrule)
EntitéCiblée = _EntitéCiblée
Instance = _Instance
End Sub
End Structure
Private Shared _Overrules() As OverruleRec
Private Shared _OverrulesEnregistrés As Boolean
Private Shared Sub PopulOverrules()
ReDim _Overrules(1)
_Overrules(0) = New OverruleRec(RXClass.GetClass(GetType(Polyline)), New PolyDrawOverrule)
_Overrules(1) = New OverruleRec(RXClass.GetClass(GetType(Polyline)), New PolyGripOverrule)
End Sub
Friend Shared Property OverrulesEnregistrés() As Boolean
Get
Return _OverrulesEnregistrés
End Get
Set(ByVal value As Boolean)
If value = True Then
If Not _OverrulesEnregistrés Then
PopulOverrules()
For Each ov As OverruleRec In _Overrules
Overrule.AddOverrule(ov.EntitéCiblée, ov.Instance, False)
ov.Instance.SetXDataFilter(Projet.NomRegAppLineaTrace)
Next
_OverrulesEnregistrés = True
End If
Else
If _OverrulesEnregistrés Then
For Each ov As OverruleRec In _Overrules
Overrule.RemoveOverrule(ov.EntitéCiblée, ov.Instance)
ov.Instance.Dispose()
Next
End If
End If
End Set
End Property
Protected Class PolyDrawOverrule
Inherits Autodesk.AutoCAD.GraphicsInterface.DrawableOverrule
Public Overrides Function WorldDraw(ByVal drawable As Autodesk.AutoCAD.GraphicsInterface.Drawable, ByVal wd As Autodesk.AutoCAD.GraphicsInterface.WorldDraw) As Boolean
Dim poly As Polyline = DirectCast(drawable, Polyline)
Dim rb As ResultBuffer = poly.XData
Select Case rb.AsArray(1).Value.ToString
Case TraceEnPlan.NomExtDataTraPlan
Dim tra As TraceEnPlan = VariablesPartagées.Projet.Axe(CInt(rb.AsArray(2).Value)).TraceEnPlan
For Each seg As ISegTracePlan In tra.segments
wd.Geometry.Circle(seg.ptDeb.Point3DAcad, 1.0, Vector3d.ZAxis)
Next
If tra.ModeEdition Then
tra.Editeur.RegenTransients()
End If
Return MyBase.WorldDraw(drawable, wd)
Case Else
Return MyBase.WorldDraw(drawable, wd)
End Select
End Function
End Class
Public Class PolyGripOverrule
Inherits Autodesk.AutoCAD.DatabaseServices.GripOverrule
Dim _GripsSommets() As GripData
Public Overrides Sub GetGripPoints(ByVal entity As Autodesk.AutoCAD.DatabaseServices.Entity, ByVal grips As Autodesk.AutoCAD.DatabaseServices.GripDataCollection, ByVal curViewUnitSize As Double, ByVal gripSize As Integer, ByVal curViewDir As Autodesk.AutoCAD.Geometry.Vector3d, ByVal bitFlags As Autodesk.AutoCAD.DatabaseServices.GetGripPointsFlags)
Dim rb As ResultBuffer = entity.XData
Select Case rb.AsArray(1).Value.ToString
Case TraceEnPlan.NomExtDataTraPlan
Dim tra As TraceEnPlan = VariablesPartagées.Projet.Axe(CInt(rb.AsArray(2).Value)).TraceEnPlan
If Not tra.ModeEdition Then
tra.ModeEdition = True
Dim i As Integer
For Each sommet As Vect2D In tra.Editeur.sommets
ReDim Preserve _GripsSommets(i)
_GripsSommets(i) = New SommetTraPlanGrip
_GripsSommets(i).GripPoint = sommet.Point3DAcad
grips.Add(_GripsSommets(i))
i = +1
Next
Else
Dim i As Integer
For Each sommet As Vect2D In tra.Editeur.sommets
grips.Add(_GripsSommets(i))
i = +1
Next
End If
End Select
End Sub
Public Overrides Sub MoveGripPointsAt(ByVal entity As Autodesk.AutoCAD.DatabaseServices.Entity, ByVal indices As Autodesk.AutoCAD.Geometry.IntegerCollection, ByVal offset As Autodesk.AutoCAD.Geometry.Vector3d)
End Sub
End Class
Protected Class SommetTraPlanGrip
Inherits GripData
Public Overrides Function ViewportDraw(ByVal worldDraw As Autodesk.AutoCAD.GraphicsInterface.ViewportDraw, ByVal entityId As Autodesk.AutoCAD.DatabaseServices.ObjectId, ByVal type As Autodesk.AutoCAD.DatabaseServices.GripData.DrawType, ByVal imageGripPoint As Autodesk.AutoCAD.Geometry.Point3d?, ByVal gripSizeInPixels As Integer) As Boolean
Dim unit As Point2d = worldDraw.Viewport.GetNumPixelsInUnitSquare(GripPoint)
worldDraw.Geometry.Circle(GripPoint, gripSizeInPixels / unit.X, worldDraw.Viewport.ViewDirection)
Return True
End Function
End Class
Since the error only occured when I tried to edit any entity other than the entity that has the custom grip attach to it. I created a table and added the entities that needed to be modified. Then when the event OnGripStatusChanged is called with the status of GripsToBeDeleted I would then do the edits on the entities in the table. Since I was not in the event MoveGripPointsAt anymore the error did not occur. That is how I worked around the error.
Thanks for the help.
Can't find what you're looking for? Ask the community or share your knowledge.