Adding ordinate dimension to existing with ilogic

Adding ordinate dimension to existing with ilogic

snichols
Advocate Advocate
2,818 Views
9 Replies
Message 1 of 10

Adding ordinate dimension to existing with ilogic

snichols
Advocate
Advocate

I'm trying to add an ordinate dimension member to an existing view that already has some ordinate dimensions. It is not currently an ordinate set but it can be if it's easier to do. The code below adds centermarks at various elevations between the first and last dimension based on workpoints in the model. I need to add ordinate dimensions to these centermarks. This is for drawing automation so I don't want to have to manually select anything. Any help would be greatly appreciated.

 

snichols_0-1590147143949.png

 

'Get the drawing document
Dim invDrawDoc As DrawingDocument
invDrawDoc = ThisApplication.ActiveDocument

'Set a reference to the active sheet.
Dim oActiveSheet As Sheet
oActiveSheet = invDrawDoc.ActiveSheet
oView = oActiveSheet.DrawingViews(1)

'get the model from the view
Dim oModel as Document
oModel = ActiveSheet.View(oView.Name).ModelDocument
    
'Get the origin workpoint
Dim oWorkPoint As WorkPoint
    For Each oWorkPoint In oModel.ComponentDefinition.WorkPoints
        If oWorkPoint.Name.Contains("Elevation") Then

            oOriginPoint = oModel.ComponentDefinition.WorkPoints(oWorkPoint.Name)
            
            'place center mark
            Dim oCenterMark As Centermark
            oCenterMark = oActiveSheet.Centermarks.AddByWorkFeature(oOriginPoint,oView)
        
            'get center mark co-ordinates
            Dim oPoint As Point2d
            oPoint = oCenterMark.Position

            'Create point intent to anchor the dimension to.
            Dim oDimIntent  As GeometryIntent
            oDimIntent = oActiveSheet.CreateGeometryIntent(oCenterMark, kCenterPointIntent)
            
            Dim oTextOrigin1 As Point2d
            oTextOrigin1 = ThisApplication.TransientGeometry.CreatePoint2d(1, 1)
            
            
'            This Is where I'm lost, Can't figure out how this works.'              'Add the ordinate dimension.'            Dim oOrdinateDimension As OrdinateDimensions'            Dim oOrdinateDimension1 As OrdinateDimension'            oOrdinateDimension1 = oOrdinateDimension1.Add(oDimIntent, oTextOrigin1, kVerticalDimensionType)

        End If
    Next
0 Likes
Accepted solutions (1)
2,819 Views
9 Replies
Replies (9)
Message 2 of 10

WCrihfield
Mentor
Mentor
Accepted solution

See if this works for you.

 

Dim oDDoc As DrawingDocument = ThisDrawing.Document
Dim oSheet As Sheet = oDDoc.ActiveSheet
Dim oView As DrawingView = oSheet.DrawingViews(1)
Dim oMDoc As Document = ThisDrawing.ModelDocument
Dim oWPoint As WorkPoint
Dim oCM As Centermark
Dim oPoint As Point2d
Dim oDimIntent  As GeometryIntent
Dim oTextOrigin As Point2d
Dim oOrdDims As OrdinateDimensions = oSheet.DrawingDimensions.OrdinateDimensions
Dim oOrdDim As OrdinateDimension

For Each oWPoint In oMDoc.ComponentDefinition.WorkPoints
    If oWPoint.Name.Contains("Elevation") Then
        oCM = oSheet.Centermarks.AddByWorkFeature(oWPoint,oView)
        oPoint = oCM.Position
        oDimIntent = oSheet.CreateGeometryIntent(oCM, PointIntentEnum.kCenterPointIntent)
        oTextOrigin = ThisApplication.TransientGeometry.CreatePoint2d(1, 1)
		oOrdDim = oOrdDims.Add(oDimIntent,oTextOrigin,DimensionTypeEnum.kHorizontalDimensionType)
    End If
Next

 

I hope this helps.
If this solves your problem, or answers your questions, please click 'Accept As Solution".
Or, if this helps you reach your goal, please click 'LIKES" 👍.

 

Also, if you're interested, here are a few of the 'Ideas' I'd like to get implemented.
If you agree with any of them, please vote for them.

  • Add more capabilities to the 'Customize' dialog box (exe. Add Tab & Add Panel) Click Here
  • Constrain & Dimension Images In Assembly Sketches & Drawing Sketches (TitleBlocks & SketchedSymbols) Click Here
  • Save Section View Status In DesignViewRepresentation (So It Can Be Used In The Drawing) Click Here
  • Add SolidBodies Folder In iLogic Rule Editor Model Tab Click Here
  • Convert All Views To Raster Before Autosave Stores To 'OldVersions' Folder Click Here
  • SetDesignViewRepresentation - Fix limitations for DrawingView of a Part Click Here
  • Create DocumentSubTypeEnum Click Here
  • Add kRevisionTag or kDrawingRevisionTag to ObjectTypeEnum Click Here

Inventor 2020 Help | Inventor Forum | Inventor Customization Forum | Inventor Ideas Forum

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 3 of 10

snichols
Advocate
Advocate

Works like a charm! Kudos 🙂

0 Likes
Message 4 of 10

bhavikpatel311
Explorer
Explorer

Hello @WCrihfield ,

I have a similar application where I have to create ordinate dimensions for all the centremarks. So I used your code above and simplified it to run just based on centermarks.

 

The code runs successfully, however, I receive the following error message after the code.

I think it has to do with the oOrdDim.Add command. 

 

Could you please check it for me?

 

Thank you in advance!

bhavikpatel311_0-1624909484076.png

 

 

Dim oDDoc As DrawingDocument = ThisDrawing.Document
Dim oSheet As Sheet = oDDoc.ActiveSheet
Dim oView As DrawingView = oSheet.DrawingViews(1)
Dim oMDoc As Document = ThisDrawing.ModelDocument
Dim oWPoint As WorkPoint
Dim oCM As Centermark
Dim oPoint As Point2d
Dim oDimIntent  As GeometryIntent
Dim oTextOrigin As Point2d
Dim oOrdDims As OrdinateDimensions = oSheet.DrawingDimensions.OrdinateDimensions
Dim oOrdDim As OrdinateDimension

For Each oCM In oSheet.Centermarks
        oDimIntent = oSheet.CreateGeometryIntent(oCM, PointIntentEnum.kCenterPointIntent)
        oTextOrigin = ThisApplication.TransientGeometry.CreatePoint2d(1, 1)
		oOrdDim = oOrdDims.Add(oDimIntent, oTextOrigin, DimensionTypeEnum.kVerticalDimensionType)
		oOrdDim.AttributeSets.Add ("ilogic_Created")
Next

I'm using Inventor 2018

0 Likes
Message 5 of 10

WCrihfield
Mentor
Mentor

Hi @bhavikpatel311 .  Creating ordinate dimensions by code can be pretty tricky.  They are done differently than other types of dimensions (both manually and by code).  If you have multiple views on your sheet, and there are center marks within the boundaries of multiple views, and you manually click the Ordinate Dimension tool button, it first wants you to select a view, then it wants you to specify where the origin should be for all the ordinate dimensions you are going to be creating, then it's finally ready for you to start selecting geometry to attach the dimensions to.  The iLogic tool (OrdinateDimensions.Add) doesn't ask you to specify a view or an origin, just what initial object to attempt to attach a dimension to.  The first example above was very simple because there was only one view.  And since Centermarks are owned by the Sheet, not by any drawing views, it can be odd.  In your case, I'm thinking that using an OrdinateDimensionSet  and the OrdinateDimensionSets.Add method would likely be an easier route.  With this method you are asked for an ObjectCollection filled with GeometryIntent objects.  So we create the collection before the loop, then add the geometry intent objects to the collection within the loop, then after the loop we can supply that collection object to this method.  However, both methods are still challenging to use when there are multiple views involved, and there are center marks in multiple of them.

 

In one of my tests, I had multiple views on my main sheet, but only have center marks within one view.  In this instance the following code works:

 

Sub Main
	Dim oDDoc As DrawingDocument = ThisDrawing.Document
	Dim oSheet As Sheet = oDDoc.ActiveSheet
	Dim oOrdDimSets As OrdinateDimensionSets = oSheet.DrawingDimensions.OrdinateDimensionSets
	Dim oOrdDimSet As OrdinateDimensionSet
	Dim oIntents As ObjectCollection = ThisApplication.TransientObjects.CreateObjectCollection
	Dim oTG As TransientGeometry = ThisApplication.TransientGeometry

	For Each oCM As Centermark In oSheet.Centermarks
		Dim oGIntent As GeometryIntent
		If oCM.Attached Then
'			MsgBox("This Centermark is 'Attached' to a " & TypeName(oCM.AttachedEntity), , "")
			If TypeOf oCM.AttachedEntity Is GeometryIntent Then
				oGIntent = oCM.AttachedEntity
			End If
		Else
'			MsgBox("This Centermark is NOT 'Attached'.", , "")
		End If
		If oGIntent Is Nothing Then
			oGIntent = oSheet.CreateGeometryIntent(oCM, PointIntentEnum.kCenterPointIntent)
		End If
		oIntents.Add(oGIntent)
	Next
	
	If oIntents.Count = 0 Then
		MsgBox("There were no 'Geometry Intents' added to the collection. Exiting.", , "")
		Exit Sub
	Else
'		MsgBox("There were " & oIntents.Count & " 'Geometry Intents' added to the collection.",,"")
	End If
	
'	To Set the value Of 'Placement' based on first Centermark's position
'	Dim o1stPt As GeometryIntent = oIntents.Item(1)
'	Dim oPlacement As Point2d = o1stPt.PointOnSheet.Copy
'	oPlacement.X = (oPlacement.X - 1)
	Dim oPlacement As Point2d = oTG.CreatePoint2d(1, 1)
	
	Try
		oOrdDimSet = oOrdDimSets.Add(oIntents, oPlacement, DimensionTypeEnum.kVerticalDimensionType)
	Catch oEx As Exception
		MsgBox("Failed to 'Add' OrdinateDimensionSet to specified Centermarks." & vbCrLf & _
		vbCrLf & "Error Message:" & vbCrLf & oEx.Message & vbCrLf & _
		vbCrLf & "Error StackTrace:" & vbCrLf & oEx.StackTrace & vbCrLf & _
		vbCrLf & "Error Source:" & vbCrLf & 	oEx.Source,vbExclamation, "")
	End Try
End Sub

 

 

However, with the same exact drawing, and the same views, if I have center marks within multiple of the views, now the code above doesn't work.  There were similar results when using the OrdinateDimensions.Add() method.  So, after observing this behavior, I'm guessing that these methods for these specific types of dimensions may need to be created for the target objects residing within the boundaries of one view at a time (normally a single set of dimensions do not span across multiple views).  To make that happen, I'm thinking we may need to create a helper Sub or Function that will look at the boundaries of one view at a time, checking which center marks are within its bounds and adding them to a collection, then process that collection.  Then loop to the next view and do the same...and so on.  I'm thinking this may be necessary, so it won't try to create a single dimension set that tries to span across multiple possible views, for all center marks on the sheet at once.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 6 of 10

WCrihfield
Mentor
Mentor

Hi@bhavikpatel311 .

Here is another version of the code that is built to deal with when there are multiple views on the sheet, and there are center marks within multiple views.  This version is also using the OrdinateDimensionSets.Add() method.  Since Ordinate type dimensions need to indicate an origin, then the other dimensions specify distance away from that origin, there needs to be more than one dimension in the set for them to work as intended.  If there is only one dimension, it will be the origin dimension, so its value will be zero, which doesn't accomplish anything.  So this code checks the Count of the resulting collection to see if it is either zero or 1, and if so, it doesn't attempt to create ordinate dimensions for the one (or none) center mark that was within that view.  This helps avoid some of the errors.  As stated at the end of my previous post, this version first starts looping through each view on the sheet.  Then it defines the view's bounding box.  Then it starts looping through all the center marks on the sheet.  When one of the center marks is found to be within the bounds of that view, it then gets its geometry intent and adds it to the collection to be processed.  After the center marks loop is done, it checks the count of the collection as mentioned above.  Then if more than 1, it attempts to create the ordinate dimensions for them.  Then loops to the next view on the sheet.  Please note that the 'collection' is defined within the loop of the views, instead of at the top (or outside of the loop).  This is important, so it cleans itself (recreates itself) fresh for each loop, and doesn't keep the previous intent objects in it.  There are a lot of checks and messages in this code, so once your comfortable with how everything works, you can comment out some of those messages (because they can get irritating after a while).

Here's the new version code:

Sub Main
	Dim oDDoc As DrawingDocument = ThisDrawing.Document
	Dim oSheet As Sheet = oDDoc.ActiveSheet
	Dim oOrdDimSets As OrdinateDimensionSets = oSheet.DrawingDimensions.OrdinateDimensionSets
	Dim oOrdDimSet As OrdinateDimensionSet
	Dim oTG As TransientGeometry = ThisApplication.TransientGeometry
	
	For Each oView As DrawingView In oSheet.DrawingViews
		'define the view's bounding box
		Dim oBottomLeft As Point2d = oTG.CreatePoint2d(oView.Left, oView.Top - oView.Height)
		Dim oTopRight As Point2d = oTG.CreatePoint2d(oView.Left + oView.Width, oView.Top)
		Dim oViewBounds As Box2d = oTG.CreateBox2d()
		oViewBounds.MinPoint = oBottomLeft
		oViewBounds.MaxPoint = oTopRight
		
		'create the collection object
		Dim oIntents As ObjectCollection = ThisApplication.TransientObjects.CreateObjectCollection
		
		'loop through the center marks, checking which ones are within this view
		For Each oCM As Centermark In oSheet.Centermarks
			If oViewBounds.Contains(oCM.Position) Then
				'this center mark is within this view, so add its 'Intent' to the collection
				Dim oGIntent As GeometryIntent
				If oCM.Attached Then
'					MsgBox("This Centermark is 'Attached' to a " & TypeName(oCM.AttachedEntity), , "")
					If TypeOf oCM.AttachedEntity Is GeometryIntent Then
						oGIntent = oCM.AttachedEntity
					End If
				Else
					MsgBox("This Centermark is NOT 'Attached'.", , "")
				End If
				If oGIntent Is Nothing Then
					oGIntent = oSheet.CreateGeometryIntent(oCM, PointIntentEnum.kCenterPointIntent)
				End If
				oIntents.Add(oGIntent)
			End If
		Next
		'check the count of the resulting collection, before trying to use it
		If oIntents.Count = 0 Then
			MsgBox("There were no 'Intents' found in the view named " & oView.Name & vbCrLf & _
			"Skipping to the next View (if any).", , "")
			Continue For
		ElseIf oIntents.Count = 1 Then
			MsgBox("There was only 1 'Intent' found in the view named " & oView.Name & vbCrLf & _
			"Skipping to the next View (if any).", , "")
			Continue For
		Else
			MsgBox("There were " & oIntents.Count & " 'Intents' found for view named " & oView.Name,,"")
		End If
	
	'	To Set the value Of 'Placement' based on first Centermark's position
	'	Dim o1stPt As GeometryIntent = oIntents.Item(1)
	'	Dim oPlacement As Point2d = o1stPt.PointOnSheet.Copy
	'	oPlacement.X = (oPlacement.X - 1)
		Dim oPlacement As Point2d = oTG.CreatePoint2d(1, 1)
	
		Try
			oOrdDimSet = oOrdDimSets.Add(oIntents, oPlacement, DimensionTypeEnum.kVerticalDimensionType)
		Catch oEx As Exception
			MsgBox("Failed to 'Add' OrdinateDimensionSet to specified Centermarks." & vbCrLf & _
			vbCrLf & "Error Message:" & vbCrLf & oEx.Message & vbCrLf & _
			vbCrLf & "Error StackTrace:" & vbCrLf & oEx.StackTrace & vbCrLf & _
			vbCrLf & "Error Source:" & vbCrLf & 	oEx.Source,vbExclamation, "")
		End Try
	Next
End Sub

If this solved your problem, or answered your question, please click ACCEPT SOLUTION.
Or, if this helped you, please click (LIKE or KUDOS) 👍.

If you want and have time, I would appreciate your Vote(s) for My IDEAS 💡or you can Explore My CONTRIBUTIONS

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 7 of 10

bhavikpatel311
Explorer
Explorer

@WCrihfield.. Wow thank you so much for the detailed explanation. I will try to create multiple sets and follow your code above. This really helps. I will ask more questions if needed.

0 Likes
Message 8 of 10

suneelkumarYX7P2
Contributor
Contributor

Hii @WCrihfield 
I am working on giving the ordinate dimensions for my component occurrences in my assembly view, which is the only view placed  in my drawing sheet. for creating the center marks i had choosen the centerpoint of req component and convert it to proxy and then create geometryintent for it but getting expecting object local error at last last line. can you help with my code?

Dim oOrdDimSets As OrdinateDimensionSets = oSheet.DrawingDimensions.OrdinateDimensionSets
	Dim oOrdDimSet As OrdinateDimensionSet
	'	For Each oView As DrawingView In oSheet.DrawingViews
	Dim oIntents As ObjectCollection = ThisApplication.TransientObjects.CreateObjectCollection
	For Each occ As ComponentOccurrence In assCompDef.Occurrences
		If occ.Name.StartsWith("ntp") Or occ.Name.StartsWith("otp") Then
			Dim oProxy As WorkPointProxy = GetPartCenterPoint(occ.Name, oFrontView)
			Dim oCenter As Centermark = oSheet.Centermarks.AddByWorkFeature(oProxy, oFrontView)
			Dim oPointIntent As GeometryIntent = oSheet.CreateGeometryIntent(oCenter)
			oIntents.Add(oPointIntent)
		End If
	Next
	Dim oPlacement As Point2d = oTg.CreatePoint2d(1, 1)
'	Try
		oOrdDimSet = oOrdDimSets.Add(oIntents, oPlacement, DimensionTypeEnum.kVerticalDimensionType)
0 Likes
Message 9 of 10

WCrihfield
Mentor
Mentor

Hi @suneelkumarYX7P2.  It has been a long time since I was involved with this topic, and I rarely do this type of process where I work, so I likely won't be able to test any code posted here.  Looking at your code example, I am not sure what the method named 'GetPartCenerPoint' is doing, or how it is doing it, so I am not sure if the value it returns is going to be OK to use in that situation.  Proxies can be tricky to work with, because they are 'context' (component definition / 3D coordinate space) specific.  The WorkPoint it returns must be in the context of the assembly document that the view is directly referencing, not within the context of a sub assembly or part within that assembly, otherwise it may not work.  I also don't know where the 'oFrontView' variable was created, or a value set to it, but I assume it represents a DrawingView type object.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

0 Likes
Message 10 of 10

suneelkumarYX7P2
Contributor
Contributor

Thanks for the reply @WCrihfield i found the issue and its due to the origin point intent and now it's solved.

0 Likes