Community
Inventor Programming - iLogic, Macros, AddIns & Apprentice
Inventor iLogic, Macros, AddIns & Apprentice Forum. Share your knowledge, ask questions, and explore popular Inventor topics related to programming, creating add-ins, macros, working with the API or creating iLogic tools.
cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

iLogic rule to renumber BOM items doesn't "stick" -- what can I do?

10 REPLIES 10
SOLVED
Reply
Message 1 of 11
claudio.ibarra
778 Views, 10 Replies

iLogic rule to renumber BOM items doesn't "stick" -- what can I do?

I have an iLogic rule that looks at the part number field, looks for "-D-M" within the part number, and separates the BOM based on whether or not the part numbers contained within have the "-D-M" string within them.

 

"Make" part numbers have it, and "Buy" part numbers don't. The rule then re-numbers the items 1,2,3 for "Make" and 100, 101, 102 for "Buy"

 

But if I add/remove an item, or make some other changes (I'm not sure exactly what causes it), the numbers revert to what they were, and everything is out of order.

 

Is there anything I can do to save the item numbers at the assembly level?

Tags (3)
Labels (3)
10 REPLIES 10
Message 2 of 11
WCrihfield
in reply to: claudio.ibarra

Hi @claudio.ibarra.  In a quick review of your code, the only detail that stands out to me as a possible problem is around Line 30 and Line 35, where you are using a variable in the starter line of those two loops as "bomRow", but then using "BOMRow" variable on the next line within both loops.  Spelling and capitalization are both important with code variables.  The variable you seem to be using inside of those two loops is exactly the same spelling and capitalization as the Type, which is always bad and causes problems.  I do not know if that is the cause of your problems, but should be fixed anyways.

Maybe check something within the BOM dialog.  When you click on the 'BOM Settings' button, a small dialog pops-up with two options in it.  One of those options is for hiding suppressed components, the other is for renumbering items sequentially.  Do you have that second option checked?

 

Edit:  Also, you may want to include a line of code at the end of your Sub Main routine for updating the assembly.  That may be needed before the changes will be seen...or something like that.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 3 of 11
claudio.ibarra
in reply to: WCrihfield

Thank you for noticing the bomRow vsBOMRow -- I have update that, and (un?)luckily for me, it works the same.

 

My BOM settings has both things checked --- I unchecked the 2nd box and that looks like it does the trick!!

 

Am I correct in thinking that checkbox is document-specific? Is there any code I could add to the start of my iLogic script that would un-check the box for me?

 

Message 4 of 11
WCrihfield
in reply to: claudio.ibarra

Hi @claudio.ibarra.  Those 'BOM Settings' settings are saved within that document, not application level settings.  And yes, we can access/control them by code also.  The main BOM API object, that you get right under the AssemblyComponentDefinition, has properties for those two settings.

BOM.HideSuppressedComponentsInBOM 

BOM.RenumberItemsSequentially 

Both are Read/Write Boolean type properties.

Edit:  But those two settings were just added in Inventor 2023, just in case you may be using an earlier version.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 5 of 11
claudio.ibarra
in reply to: WCrihfield

I'm using 2023! 

 

If I add the following text to the start of the rule, would that accomplish the goal of ensuring the setting is off whenever the rule is run? 

ThisApplication.ActiveDocument.BOM.RenumberItemsSequentially = False

Message 6 of 11
WCrihfield
in reply to: claudio.ibarra

Hi @claudio.ibarra.  Actually, you are missing the ComponentDefinition step in that line of code, between the document and the BOM object.  But I would suggest replacing your whole Sub Main section of code with something like the following, just to be a bit more thorough.  This first makes sure that it is really an assembly, and if not exits the rule.  Then gets the BOM to a variable.  Then sets that setting.  Then makes sure that the 'structured' view is enabled.  Then attempts to get that structured BOMView by iterating through the available BOMViews, checking their ViewType property, to make sure we get the correct one.  Going by Index number is not stable, because it changes depending on which ones are enabled.

 

Sub Main()
    Dim asm As AssemblyDocument = TryCast(ThisDoc.Document, Inventor.AssemblyDocument)
	If asm Is Nothing Then Return 'just in case it gets ran on a part or drawing
    Dim oBOM As Inventor.BOM = asm.ComponentDefinition.BOM
	oBOM.RenumberItemsSequentially = False
	oBOM.StructuredViewEnabled = True
	Dim oStructuredBOMView As BOMView = Nothing
	For Each oBomView As BOMView In oBOM.BOMViews
		If oBOMView.ViewType = BOMViewTypeEnum.kStructuredBOMViewType Then
			oStructuredBOMView = oBomView
		End If
	Next
	If oStructuredBOMView Is Nothing Then Return
    SortBomView(oStructuredBOMView)
End Sub

 

 

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 7 of 11
claudio.ibarra
in reply to: WCrihfield

I know I'm an internet stranger (I could be a german shepard, you don't know!), but from the bottom of my heart, thank you. That works exactly like how I want it to. Thank you thank you thank you!

Message 8 of 11
claudio.ibarra
in reply to: WCrihfield

One last question because it never hurts to ask -- is it possible to make this rule agnostic to whether it's being run from an assembly or from a drawing that references that assembly? Right now it needs to be run from the modeling environment, but could it be made to run from the drawing directly?

Message 9 of 11
WCrihfield
in reply to: claudio.ibarra

Hi @claudio.ibarra.  Yes.  That is an odd combination of possible document types that a rule could start from, so the code I injected is maybe a bit longer than it might need to be, but I think this should work OK for you.  I copied the whole rule, with the new Sub Main section. Then modified the Sub Main area again.  Then modified a couple minor things within the SortBomView Sub routine's code.  Mostly just changed your "bomRow" variable to "oBomRow", because the "bomRow" variable kept changing back to "BOMRow" automatically on me, for some odd reason, which is bad.  I also got the BOMRows collection to a variable before the start of the loop, because that is more efficient when running (does not have to 'get' the collection again each time).

Sub Main()
	Dim oDoc As Inventor.Document = ThisDoc.Document
	Dim oBOM As Inventor.BOM = Nothing
	If oDoc.DocumentType = DocumentTypeEnum.kAssemblyDocumentObject Then
		oBOM = oDoc.ComponentDefinition.BOM
	ElseIf oDoc.DocumentType = DocumentTypeEnum.kDrawingDocumentObject Then
		Dim oModelDoc As Inventor.Document = ThisDoc.ModelDocument
		If oModelDoc Is Nothing Then Return 'no model referenced in drawing yet
		If oModelDoc.DocumentType = DocumentTypeEnum.kAssemblyDocumentObject Then
			oBOM = oModelDoc.ComponentDefinition.BOM
		Else
			Return 'drawing model may have been a part, so no BOM
		End If
	Else
		Return 'main document may have been a part
	End If
	If oBOM Is Nothing Then Return
	oBOM.RenumberItemsSequentially = False
	oBOM.StructuredViewEnabled = True
	Dim oStructuredBOMView As BOMView = Nothing
	For Each oBomView As BOMView In oBOM.BOMViews
		If oBomView.ViewType = BOMViewTypeEnum.kStructuredBOMViewType Then
			oStructuredBOMView = oBomView
		End If
	Next
	If oStructuredBOMView Is Nothing Then Return
    SortBomView(oStructuredBOMView)
End Sub

Private Sub SortBomView(bomView As BOMView)
    Dim makeItems As New List(Of BOMRow)
    Dim buyItems As New List(Of BOMRow)
	'good to get collection to a variable before start of loop (unless adding/removing from collection)
	Dim oRows As BOMRowsEnumerator = bomView.BOMRows
    For Each oBomRow As BOMRow In oRows
        Dim rowDocument As Document = oBomRow.ComponentDefinitions(1).Document
        Dim partNumber As String = rowDocument.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value.ToString()

        If IsMake(partNumber) Then
            makeItems.Add(oBomRow)
        Else
            buyItems.Add(oBomRow)
        End If
    Next

    makeItems = makeItems.OrderBy(Function(item) item.ComponentDefinitions(1).Document.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value.ToString()).ToList()
    buyItems = buyItems.OrderBy(Function(item) item.ComponentDefinitions(1).Document.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value.ToString()).ToList()

    Dim makeCounter = 1
    Dim buyCounter = 100

    For Each oBomRow In makeItems
        oBomRow.ItemNumber = makeCounter
        makeCounter += 1
    Next

    For Each oBomRow In buyItems
        oBomRow.ItemNumber = buyCounter
        buyCounter += 1
    Next
End Sub

Private Function IsMake(partNumber As String) As Boolean
    If partNumber.Length >= 3 Then
        Return partNumber.Substring(3).StartsWith("-D-M")
    Else
        Return False
    End If
End Function

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 10 of 11
claudio.ibarra
in reply to: WCrihfield

I don't know if these are helpful for understanding the error, but it did give me an error. (I've attached screenshots)

Message 11 of 11
WCrihfield
in reply to: claudio.ibarra

Hi @claudio.ibarra.  That error says that the line of code (Line 18) that is attempting to 'Set' the value of the RenumberItemsSequentially property caused the error.  We can try to step through a process of elimination to figure this out.  We know that the oBOM variable does have a value assigned to it at that point, due to the line of code just above that line, which actually checks if it 'Is Nothing', so that is not the problem.  And we know that it is understood as being a BOM object, due to how it was declared, because otherwise it would have thrown a different type of error (for example Type mismatch or can not Cast obj1 Type to obj2 type), plus it correctly understood exactly what that line of code was trying to do.  So, the next thought that comes to mind is that maybe either the assembly, or the BOM itself are ReadOnly for some reason.

 

If the assembly has multiple ModelStates, and maybe the assembly document reference we got earlier in the code is a ModelState 'member' document, instead of the ModelState 'factory' document, that might cause a ReadOnly type status.  Because ModelState member documents are generally ReadOnly if accessed directly.  To avoid this, we may have to add more code in there to check if the assembly has 2 or more ModelStates, and if so, then we know that we will need to make sure we are working with the ModelState factory document and/or make sure the MemberEditScope of the assembly is set to 'factory scope' or 'all members' so that we can make changes to the member.  I know, ModelStates really complicated a lot of stuff, when it comes to controlling things by code.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

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

Post to forums  

Autodesk Design & Make Report