A Closer Look at the Code
In previous lessons, you learned that a class can have functions/subs and properties. Classes also generate events when things happen for your code to respond to: you want to respond to your button’s click event, for instance, and it’s in your handler for this event (which is a special kind of function) that you’ve added the rest of the code in this lesson.
Private Sub Button1_Click(ByVal sender As Object,
ByVal e As System.EventArgs) Handles Button1.Click
When the button is clicked you want to get the components in the assembly that the user has already selected. To do this you need to use the SelectSet property of the document.
To make sure the rest of your code can function, you first need to check Inventor has a document open. You do this by checking the number of items in the Documents collection from the Inventor Application object via the collection’s Count property. Notice how you’re using the dot notation to “walk the hierarchy”, going from one object to another via properties.
If _invApp.Documents.Count = 0 Then
MsgBox("Need to open an Assembly document")
An “If Then” statement lets you execute code conditionally: if the condition between the “If” and the “Then” evaluates to true, then the code between the “Then” and the “End If” gets executed. In this example, when the Count property is zero, you know that no documents are open in Inventor. At this point you tell the user to open an assembly and you then Return from the Sub – jumping to the end of the Sub without executing any further code. It’s much better to check for problematic situations in this way than to let the code fail and generate a confusing error message. The Return keyword does not cause your application to exit completely – it only Returns from the Sub – so the user can simply open an assembly and click the button again.
The next piece of code is another “If Then” statement: this time to make sure the document that’s active in Inventor is an assembly, as your code only works with assembly components. In this case you use a slightly different comparison: you use the inequality operator (<>) rather than the equality operator (=). So if the active document is not an assembly you present a different message to the user and Return from the Sub.
If _invApp.ActiveDocument.DocumentType <> DocumentTypeEnum.kAssemblyDocumentObject Then
MsgBox("Need to have an Assembly document active")
If your code gets past these two “If Then” statements then you know an assembly is active and you can proceed to get the SelectSet from it.
Dim asmDoc As AssemblyDocument
asmDoc = _invApp.ActiveDocument
If asmDoc.SelectSet.Count = 0 Then
MsgBox("Need to select a Part or Sub Assembly")
You use the Dim statement to declare a variable named “asmDoc” of type “AssemblyDocument” and directly assign the contents of the Inventor Application’s ActiveDocument property to it using the equals sign (which is also the assignment operator in VB.NET). If you make changes to asmDoc using one of its properties, the change will take effect on the active document. Here you are just using one of the properties, “SelectSet”, in an “If Then” statement – you’re not modifying the document at all. Once again you’re checking the Count property, to see whether the SelectSet contains any items: if the user did not select anything then you ask them to do so before Returning from the Sub.
At this point in your code, you know that something is selected in the active Inventor assembly. Now you will go ahead and do something to each of the selected components.
Dim selSet As SelectSet
selSet = asmDoc.SelectSet
Dim compOcc As ComponentOccurrence
Dim obj As Object
For Each obj In selSet
compOcc = obj
compOcc.Visible = False
Catch ex As Exception
MsgBox("Is the selected item a Component?")
Here you assign the SelectSet containing the selected entities from the active AssemblyDocument to the “selSet” variable. A Try Catch block is used for error checking: if a problem occurs while executing the code inside the Try block, the code in the Catch block gets executed, allowing you to provide further information to the user about the problem (in this case you ask them to make sure they have selected one or more components).
Within the Try block, you use a “For Next” loop to step through each of the entities in the SelectSet. If only one entity is selected then the code between the “For Each” and “Next” statements will only be processed once. If there are more entities selected, the code will be processed once for each entity. You know that the code will be executed at least once, as you would already have returned from the Sub if there were no entities in the SelectSet. The SelectSet could contain any type of entity that is selectable in Inventor: it’s for this reason you access its contents using the generic “Object” type (a type that can contain any kind of object). If the user has selected something other than a Component, an error will be generated when you attempt to assign it to your “compOcc” variable of type ComponentOccurrence. Assuming this assignment doesn’t cause an error, the next line will execute which uses Debug.Print to send the name of the ComponentOccurrence to the Immediate
window in Visual Basic Express. This window can be displayed in Visual Basic Express from the Debug
menu > Windows
). Using Debug.Print and the immediate window is a useful tool if a problem occurs and you need to work out what is wrong. Notice that the Immediate window is accessed from a different location then the Error List
which is accessed from View
> Other Windows
. After the Debug.Print statement, you reach the goal of this lesson’s code: to hide the selected components by setting their Visible property to False.
Well done! You have just written a more robust plug-in by hiding the selected components programmaticallyand anticipating the possibility of something unexpected happening with the use of your plug-in, which will, in turn, improve the user experience.