How can I make my rule refer to the part number of a component rather than the component name?

How can I make my rule refer to the part number of a component rather than the component name?

OliverXL5YM
Contributor Contributor
1,713 Views
19 Replies
Message 1 of 20

How can I make my rule refer to the part number of a component rather than the component name?

OliverXL5YM
Contributor
Contributor

I have a rule that is a super simple if statement that when one of the components is active, then it suppresses the other. But, when I go to use this assembly in a different project, the project updates all the components name to have the prefix of that project, but the part number always stays the same. This means the ilogic does not work unless I change the component names in the rule manually by adding the prefix. How do I get it to refer to the same component by just the part number since that stays the same in every project this assembly is used. Or possibly automatically update the component name in the rule to match the component name in the model tree for the assembly.

 

If cover_type = "regular" Then
	Component.IsActive("Flange RV - Vent_Cover:1") = True
	Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = False
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = False
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = False
Else If cover_type = "coned" Then
	Component.IsActive("Flange RV - Vent_Cover:1") = False
	Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = True
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = True
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = True
Else If cover_type = "N/A" Then
	Component.IsActive("Flange RV - Vent_Cover:1") = True
	Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = True
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = True
	Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = True
End If

 How do I make these component names update when the prefix is added automatically , for example, if the prefix is "29019 -" and is automatically added to all the part names. The part numbers remain the same as well so I was assuming I would be able to use that.

0 Likes
Accepted solutions (1)
1,714 Views
19 Replies
Replies (19)
Message 2 of 20

A.Acheson
Mentor
Mentor

The easiest approach here is to stabilize the occurrence name by renaming to a generic name that will become static. If you say your part number doesn't change then you can add a description and the part number. The main thing is that the occurrence name is unique. Now when you the file name changes the occurrence name won't. You have removed the out of the box occurrence renaming tool. Now in your code refer to the static occurrence name and your code will work. 

 

See this article here it has a handy renaming code in case you have a lot to rename.

If this solved a problem, please click (accept) as solution.‌‌‌‌
Or if this helped you, please, click (like)‌‌
Regards
Alan
0 Likes
Message 3 of 20

Michael.Navara
Advisor
Advisor

You can create your own collection of occurrences to do something with them. You can also separate the selection process to separate method.

 

Dim asm As AssemblyDocument = ThisDoc.Document

Dim lookedPartNumber As String  = "MyPartNumber"
Dim isActive As Boolean = False

'Get occurrences to process by its document PartNumber
Dim occList As New List(Of ComponentOccurrence)

For Each occ As ComponentOccurrence In asm.ComponentDefinition.Occurrences
	Dim doc As Document =occ.Definition.Document
	Dim partNumber As String = doc.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value
	If partNumber = lookedPartNumber Then
		occList.Add(occ)
	End If
Next

'Do something with occurrences in list
For Each occ In occList
	Component.IsActive(occ.Name) = isActive
Next

 

Message 4 of 20

OliverXL5YM
Contributor
Contributor

Would I need to do this for every component in the same rule or do I need to do a seperate rule for every component?

0 Likes
Message 5 of 20

OliverXL5YM
Contributor
Contributor
This is a good article. How can I make it so that it removes the prefix of the file name for the occurrence name then automatically. When I use this assembly in a project and put it in someone wrote iLogic that automatically saves a copy with the prefix of the job name, but how do I remove that for all the possible job names without having to tell the rule manually what the job name is?
0 Likes
Message 6 of 20

A.Acheson
Mentor
Mentor

Hi @OliverXL5YM 

The rule and assembly will need to have the occurrence name updated. Any future assemblies when copied will work but any previous assembly will have the incorrect rule and occurrence names. 

AAcheson_0-1694040171698.png

 

If this solved a problem, please click (accept) as solution.‌‌‌‌
Or if this helped you, please, click (like)‌‌
Regards
Alan
Message 7 of 20

OliverXL5YM
Contributor
Contributor
It is okay if previous assemblies are different than future assemblies. I have an already made assembly that suppresses and unsuppresses parts based on what I need. So I generate it into a project that I am working on and then the file name and all the parts in the assembly has their names updated to have a prefix of the job name, I just don't understand iLogic the best so I need a way to automaticaly change the occurrence name to something consistent when the assembly is copied into the new job. Kind of like how in the article he removes the ":1" from all the parts, I just need to remove the prefix.
0 Likes
Message 8 of 20

A.Acheson
Mentor
Mentor

Can you remove it manually? Edit the occurrence name in the assembly. It will take you longer to prepare a code to replace the occurrence name but if you really need to you can use the String.Replace method to remove the prefix number and "-" Character. Replace it with a blank string ""

 

Dim TestString As String = Occ.Name
   
Dim aString As String = Replace(TestString, "12345-", "") 
 Occ.Name = aString
If this solved a problem, please click (accept) as solution.‌‌‌‌
Or if this helped you, please, click (like)‌‌
Regards
Alan
0 Likes
Message 9 of 20

Michael.Navara
Advisor
Advisor
Accepted solution

Here is complete sample for your original code. It assumes your occurrence names is based on PartNumber.

There are three usage samples, how you can use the method IsActiveByPartNumber. You can choose which one best fits your needs. This method accepts multiple part numbers as the last argument(s).

 

 

 

 

Sub Main()

    'For syntax only
    'Dim cover_type As String = ""
    Dim asm As AssemblyDocument = ThisDoc.Document


    If cover_type = "regular" Then
        'Usage sample 1 - Call the method separately for each PartNumber
        IsActiveByPartNumber(asm, True, "Flange RV - Vent_Cover")
        IsActiveByPartNumber(asm, False, "Flange RV - Coned_Cover_Flange_1")
        IsActiveByPartNumber(asm, False, "Flange RV - Coned_Vent_Cover_1")

        'Component.IsActive("Flange RV - Vent_Cover:1") = True
        'Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = False
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = False
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = False

    ElseIf cover_type = "coned" Then
        'Usage sample 1 - Combine multiple PartNumbers to single method call
        IsActiveByPartNumber(asm, False, "Flange RV - Vent_Cover")
        IsActiveByPartNumber(asm, True, "Flange RV - Coned_Cover_Flange_1", "Flange RV - Coned_Vent_Cover_1")

        'Component.IsActive("Flange RV - Vent_Cover:1") = False
        'Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = True
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = True
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = True

    ElseIf cover_type = "N/A" Then
        'Usage sample 3 - Prepare list of PartNumbers separately
        Dim partNumbers  = {
            "Flange RV - Vent_Cover",
            "Flange RV - Coned_Cover_Flange_1",
            "Flange RV - Coned_Vent_Cover_1"
        }
        IsActiveByPartNumber(asm, True, partNumbers)

        'Component.IsActive("Flange RV - Vent_Cover:1") = True
        'Component.IsActive("Flange RV - Coned_Cover_Flange_1:1") = True
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:1") = True
        'Component.IsActive("Flange RV - Coned_Vent_Cover_1:2") = True
    End If
End Sub


Sub IsActiveByPartNumber(asm As AssemblyDocument, isActive As Boolean, ParamArray partNumbers() As String)

    'Get occurrences to process by its document PartNumber
    Dim occList As New List(Of ComponentOccurrence)

    For Each occ As ComponentOccurrence In asm.ComponentDefinition.Occurrences
        Dim doc As Document = occ.Definition.Document
        Dim partNumber As String = doc.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value
        If partNumbers.Contains(partNumber) Then
            occList.Add(occ)
        End If
    Next

    'Do something with occurrences in list
    For Each occ In occList
        Component.IsActive(occ.Name) = isActive
    Next
End Sub

 

 

 

 

Message 10 of 20

OliverXL5YM
Contributor
Contributor

This ended up working the very first time I ran the rule and changed it to be the coned cover, but afterwords I would get this message but I do not know which error it is talking about. 

0 Likes
Message 11 of 20

A.Acheson
Mentor
Mentor

Post the more info tab as that is where the information of error is, tab 1 just says there is an error. 

If this solved a problem, please click (accept) as solution.‌‌‌‌
Or if this helped you, please, click (like)‌‌
Regards
Alan
Message 12 of 20

OliverXL5YM
Contributor
Contributor

Here it is, was I supposed to add more to the code?

0 Likes
Message 13 of 20

WCrihfield
Mentor
Mentor

That error suggest it encountered the error when it tried to access the Definition of an assembly component.  If the component was suppressed at the time, that would cause it to throw an error when you tried to access its definition.  You can not do much with a component that is currently suppressed, so you may need to include some filtering code to help avoid that.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

Message 14 of 20

OliverXL5YM
Contributor
Contributor

How would it be best I go about doing that, should I just have an if statement that for the "N/A " parameter that unsuppresses everything. That might be okay if I just make sure to select that to unsuppress everything before I select the coned cover or the regular cover.

0 Likes
Message 15 of 20

WCrihfield
Mentor
Mentor

In any other situation, where you are about to access the ComponentOccurrence.Definition property, you usually need to filter out any that are suppressed first using something like:

If occ.Suppressed Then Continue For

...where 'Continue For' is used to skip to the next item in a loop (if used within a loop), or use 'Exit Sub' if just inside a custom Sub routine just for that component.  However, given what the code in this situation is trying to achieve, that may not work as intended.  You are trying to access the Part Number iProperty of that component, which is normally not going to be possible while it is suppressed, making this a challenging request to fulfill.  I'm guessing that you may be able to avoid using these lines of code, due to the inherent problem mentioned.

Dim doc As Document = occ.Definition.Document
Dim partNumber As String = doc.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value

...and instead try using the iLogic shortcut snippet:

Dim partNumber As String = iProperties.Value(occ.Name, "Project", "Part Number")

But I still do not recall if that will work if that component is suppressed.  It's worth a try though.

 

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

0 Likes
Message 16 of 20

WCrihfield
Mentor
Mentor

Another idea would be to use the built-in tool to rename all of your assembly component browser nodes to reflect their Part Number, instead of Filename.  That tool is usually on the Assemble tab, Productivity panel (may not always be showing), then within its drop-down list, named "Rename Browser Nodes".  It has 3 options for the name (Filename, Part Number, Default).  If all the components were renamed to their Part Numbers, you would no longer need to try to extract the Part Number from each component.  If there are more than one of the same part though, you will still have to deal with the "PN:1" & "PN:2" scenario (automatically adds an Index Integer at the end).  That is super simple to deal with though.

Dim sPN As String = occ.Name.Split(":").First

...where Split creates an Array of Strings, divided by that ":" character, then gets the 'First' String in that Array.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

0 Likes
Message 17 of 20

OliverXL5YM
Contributor
Contributor

This one does not let me set the browser nodes to the part number, it greys out the accept button, but if it didn't that would be exactly what I need

0 Likes
Message 18 of 20

OliverXL5YM
Contributor
Contributor

would I be able to just put "asm" in the "project" part since the project name varies for every project and would not be able to go into the rule and edit that name of the project in the rule.

0 Likes
Message 19 of 20

WCrihfield
Mentor
Mentor

The word "Project" there is referring to the PropertySet that the Part Number iProperty is found within.  That is sort of like its nickname that can be used when using that iProperti.Value() snippet.  You should not need to change that.  You can see the 'InternalName' of that specific PropertySet being used in the previous example by Michael, it is also known by the English name "Design Tracking Properties", if accessing it through normal Inventor API code, like Michael was doing.  That "Project" loosely represents the contents of the tab within the iProperties dialog, but that 'set' includes much more properties than what is shown in that tab.

 

Edit:  If you are not using an English version of Inventor, then you might be able to use that 'InternalName' shown in Michael's example to refer to that PropertySet in the iProperties.Value() snippet, instead of "Project".  The PropertySet.InternalName property's value is stable across all languages.

Wesley Crihfield

EESignature

(Not an Autodesk Employee)

0 Likes
Message 20 of 20

Michael.Navara
Advisor
Advisor

Sorry, yesterday must have been some spots on sun or something. Here is updated version of IsActiveByPartNumber. When the component is suppressed, you can't read its definition. Component must be activated before.

Sub IsActiveByPartNumber(asm As AssemblyDocument, isActive As Boolean, ParamArray partNumbers() As String)

    'Get occurrences to process by its document PartNumber
    Dim occList As New List(Of ComponentOccurrence)

    For Each occ As ComponentOccurrence In asm.ComponentDefinition.Occurrences
        Dim isActiveBefore = Component.IsActive(occ.Name)
        If Not isActiveBefore Then
            Component.IsActive(occ.Name) = True
        End If

        Dim doc As Document = occ.Definition.Document
        Dim partNumber As String = doc.PropertySets("{32853F0F-3444-11D1-9E93-0060B03C1CA6}")("Part Number").Value
        If partNumbers.Contains(partNumber) Then
            occList.Add(occ)
        ElseIf Not isActiveBefore Then
            Component.IsActive(occ.Name) = False
        End If
    Next

    'Do something with occurrences in list
    For Each occ In occList
        Component.IsActive(occ.Name) = isActive
    Next
End Sub
0 Likes