×
INTELLIGENT WORK FORUMS
FOR ENGINEERING PROFESSIONALS

Log In

Come Join Us!

Are you an
Engineering professional?
Join Eng-Tips Forums!
  • Talk With Other Members
  • Be Notified Of Responses
    To Your Posts
  • Keyword Search
  • One-Click Access To Your
    Favorite Forums
  • Automated Signatures
    On Your Posts
  • Best Of All, It's Free!
  • Students Click Here

*Eng-Tips's functionality depends on members receiving e-mail. By joining you are opting in to receive e-mail.

Posting Guidelines

Promoting, selling, recruiting, coursework and thesis posting is forbidden.

Students Click Here

Jobs

How to traverse assembly to check custom properties
2

How to traverse assembly to check custom properties

How to traverse assembly to check custom properties

(OP)
I'm new to Solidworks API, and I've checked the built-in API help, searched these forums, and Google'd the web for help but found nothing that suits my needs so far.

I'm looking for a code example that traverses an open assembly in SW and scans every component for it's custom properties. For example, if it finds the "Material" property to have a value of "20115", then it looks for Custom Properties "Volume" and "Thickness" to have valid values as well.

Can anyone help me with this?

RE: How to traverse assembly to check custom properties

You want to look up "Assembly- traverse" in the API help.  There are examples of code to get you started.  Getting and setting custom properties of files can be performed on each file during the traversal.  
  I'll look for a project I found on a German site that was very helpful, although you have to tranlate the cooments in the code.
 

RE: How to traverse assembly to check custom properties

(OP)
Thanks for all the replies. I realize I'm probably being naive, but I'm hoping for an example that is more bare-bones and just scans the whole assembly. I want something like that, where I have something simple to start with, and I can add the functionality as I learn and go along.

Gwubs, I've already looked up "Assembly - Traverse" in the SW API help, and I didn't understand why it was outputting components as (example) "AA00007-2-3/AB00007-1-1/AB00007-S1-1" instead of "AA0007-2-3" ?  I couldn't figure that out.
Also, Lenny's AssemblyBOM macro looks like it traverses the assembly the way I want to, but like I said - I am new to the SW API, and I need something SIMPLER to start with.  I have the same dilemna with TheTick's suggested example.
I'm not sure if there exists such a simplified example, but - I just want to traverse an assembly, opening each part one-by-one from the top down. If I could find an example that does just that (and nothing else) so I can understand the process, that would be PERFECT!  

Thank you guys for your help.  I really do appreciate it!

RE: How to traverse assembly to check custom properties

(OP)
I found an example, I think it's the closest thing to what I'm looking for.  Only problem is, when I run it I get an error:

Object variable or With block variable not set (Error 91)

This is the code:

Const swDocASSEMBLY = 2

Dim swApp As SldWorks.SldWorks
Dim ModelDoc As SldWorks.ModelDoc2
Dim childlevel As Integer
Dim strText As Variant

Sub Main()

    Dim swRootComp As SldWorks.Component2
    Dim swConf As SldWorks.Configuration
    Dim ModelLevel As Integer
    Set swApp = Application.SldWorks
    Set ModelDoc = swApp.ActiveDoc
    
    
    If Not ModelDoc Is Nothing Then
        If ModelDoc.GetType = swDocASSEMBLY Then
            Set swConf = ModelDoc.GetActiveConfiguration
            Set swRootComp = swConf.GetRootComponent
            'Traverse the assembly
            TraverseComponent swRootComp
        End If
    End If
    
    'ModelDoc.AddCustomInfo3 "", "Level", swCustomInfoText, ""
    'ModelLevel = (childlevel + 1)
    'ModelDoc.CustomInfo2("", "Level") = ModelLevel
    'MsgBox ("ASSEMBLY FILE NOT SKIPPED")
    
        
End Sub


Sub TraverseComponent(swComp As SldWorks.Component2)
    'this recursively traverses all of the components in an assembly
    Dim vChildComp                  As Variant
    Dim swChildComp                 As SldWorks.Component2
    Dim childlevel_temp             As String
    Dim ModDoc                      As Object   ' ModelDoc2 of child component
    Dim ModName                     As String
    

    vChildComp = swComp.GetChildren
    childlevel_temp = 0
    childlevel = 0
    For i = 0 To UBound(vChildComp)
        Set swChildComp = vChildComp(i)
        ModName = swChildComp.Name
        Set ModDoc = swChildComp.GetModelDoc()
        childlevel_temp = CInt(ModDoc.GetCustomInfoValue("", "Level"))
           If childlevel_temp > childlevel Then
              childlevel = childlevel_temp
           End If
    Next i
End Sub


I haven't figured out what is wrong... I've SET the ModDoc object - any ideas?

RE: How to traverse assembly to check custom properties

To traverse a tiered structure like an assembly, the "TraverseComponent" sub will have to call itself if there are components on the next level.  I don't see that in your code.

RE: How to traverse assembly to check custom properties

One possibility is that when you execute the macro it's not actually running "main" first.  Try assigning the macro to a button.  This allows you to specify which method the execution starts in.

A simpler method than traversing the assembly would be to traverse all open files.  That way you don't have to worry about levels of subassemblies.

When you open an assembly, SolidWorks actually opens all unsuppressed components of that assembly, whether parts or subassemblies, in memory.  These can be interacted with by the API code without giving them a visible window.  

What this means is that as long as you don't have any parts open that you don't want to check custom properties on you could use a bit simpler code.  If you're interested I can post some such code tomorrow.

RE: How to traverse assembly to check custom properties

Here's code that will traverse all open parts.  I forgot that I had posted it (well, something much like it) previously.  There may be some extra variables declared.  I cut this out of some longer code.

CODE

Sub AllOpenParts()
Dim swDoc As SldWorks.ModelDoc2
Dim swAllDocs As EnumDocuments2
Dim FirstDoc As SldWorks.ModelDoc2
Dim dummy As Boolean
Dim NumDocsReturned As Long
Dim DocCount As Long
Dim i As Long
Dim sMsg As String
Dim swApp As SldWorks.SldWorks

Set swApp = Application.SldWorks
Set swAllDocs = swApp.EnumDocuments2
Set FirstDoc = swApp.ActiveDoc

DocCount = 0
swAllDocs.Next 1, swDoc, NumDocsReturned
While NumDocsReturned <> 0
    'Replace these comment lines with
    'the custom property actions you wish to take.

    swAllDocs.Next 1, swDoc, NumDocsReturned
    DocCount = DocCount + 1
Wend

sMsg = DocCount & " Documents are open."
MsgBox sMsg

End Sub

RE: How to traverse assembly to check custom properties

(OP)
Thanks for your help everyone. I do appreciate the time you've taken.  With your help, I've figured out what I needed to do.
Now I have another question.  First, here's the code I've used so far to traverse an assembly and it's components:

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

Const swDocAssembly = 2

Option Explicit
Public docType As Integer
Public swApp As SldWorks.SldWorks
Public swModel As SldWorks.ModelDoc2
Dim returnOK As Boolean
Public Part As Object

Private Sub Main()

Dim swRootComp              As SldWorks.Component2
Dim swConf                  As SldWorks.Configuration


Set swApp = CreateObject("SldWorks.Application")
swApp.visible = True
Set swModel = swApp.ActiveDoc

If swModel Is Nothing Then
    Call MsgBox("A SolidWorks document needs to be loaded!", vbExclamation, "Custom Properties")  ' Display error message
    returnOK = False
    swApp.visible = True

    End                    ' If no model currently loaded, then exit
    Else
     docType = swModel.GetType
     If (docType = swDocAssembly) Then
        Set swConf = swModel.GetActiveConfiguration
        Set swRootComp = swConf.GetRootComponent
        
        Open "C:\BOM Export Files\Output.txt" For Output Access Write Lock Write As #1
        
        
        'Traverse assembly
        TraverseComponent swRootComp
        
        Close #1
        
        Else
        MsgBox ("File is not assembly")
        End 'Exit if file is not assembly
            'Code for parts and drawings to be added later
        
        
    End If
End If

End Sub

Sub TraverseComponent(swComp As SldWorks.Component2)
    'this recursively traverses all of the components in an assembly
    Dim vChildComp                  As Variant
    Dim swChildComp                 As SldWorks.Component2
    Dim ModName                     As String
    Dim i                           As Integer
    Dim vChildComp2                 As Variant
    Dim i2                          As Integer
    Dim swChildComp2                As SldWorks.Component2
    Dim vChildComp3                 As Variant
    Dim i3                          As Integer
    Dim swChildComp3                As SldWorks.Component2

    'Get the childrent of this component
    vChildComp = swComp.GetChildren

    'Get children on 1st level
    For i = 0 To UBound(vChildComp)
        Set swChildComp = vChildComp(i)
        ModName = swChildComp.Name
        'Set the Part object
        Set Part = swChildComp.GetModelDoc()
        If Not swChildComp.IsSuppressed() And Not swChildComp.ExcludeFromBOM Then
            Print #1, swChildComp.Name
        'Set the Child variant
        vChildComp2 = swChildComp.GetChildren
            'Get children on 2nd level
            For i2 = 0 To UBound(vChildComp2)
                Set swChildComp2 = vChildComp2(i2)
        
                Set Part = swChildComp2.GetModelDoc()

                If Not swChildComp2.IsSuppressed() And Not swChildComp2.ExcludeFromBOM Then
                Print #1, swChildComp2.Name
                'Set the Child variant
                vChildComp3 = swChildComp2.GetChildren
                    'Get childrent on 3rd level
                    For i3 = 0 To UBound(vChildComp3)
                    Set swChildComp3 = vChildComp3(i3)
                    
                    Set Part = swChildComp3.GetModelDoc()
                    
                    If Not Part.IsSuppressed And Not Part.ExcludeFromBOM Then
                    Print #1, swChildComp3.Name
                    End If
                    Next i3
                    
            End If
            Next i2
    End If
    Next i
End Sub

'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''

The problem I'm having is where I use If...Then statements to skip any SUPRESSED components and those with an "EXCLUDE FROM BOM" property defined.
I've set a watch to "trip" when either "suppressed" or "exclude" is TRUE. The problem is that (with my IF NOT and AND NOT statements) the statement is supposed to execute as long as the component is neither suppressed nor excluded from BOM, but it executes regardless of the returned value.
How can this be?  I've tried running the same code with different expressions (If Not 2 = 3 And Not 3 = 3 Then) and I get the same results...

Help!!

Thanks again :)

RE: How to traverse assembly to check custom properties

I have run into issues processing boolean operations in SW VBA.  They are spotty and intermittent and hard to pin down, though.  It's not nearly as elegant, but you may want to try a nested if with true comparisons, like:

CODE

If (false = swChildComp.IsSuppressed()) then
  If (false = swChildComp.ExcludeFromBOM) Then
  'do your stuff here
  end if
end if

RE: How to traverse assembly to check custom properties

Try adding some parentheses to ensure that VB is interpreting it as you intend.  For instance:

CODE

(Not swChildComp.IsSuppressed()) And (Not swChildComp.ExcludeFromBOM)

An alternative and logically equivalent form would be:

CODE

Not (swChildComp.IsSuppressed() Or swChildComp.ExcludeFromBOM)

Eric

RE: How to traverse assembly to check custom properties

(OP)
Thanks handleman, your suggestion worked nicely.
''''''''''''''''''''''
If (False = swChildComp.IsSuppressed) And _
(False = swChildComp.ExcludeFromBOM) Then

'some actions

End If
'''''''''''''''''''''''

For some reason, that changes the way the expressions are evaluated.  Could this have something to do with the way the VBA compiler handles "order of execution" or maybe "short-circuiting"?  I found some information that may shed some light on this anomaly, but I haven't had time to read it thoroughly.

http://vb.mvps.org/tips/truth.asp

For now, I've bookmarked the link so I can get back to work on this project.  Thanks for the help everyone!

Red Flag This Post

Please let us know here why this post is inappropriate. Reasons such as off-topic, duplicates, flames, illegal, vulgar, or students posting their homework.

Red Flag Submitted

Thank you for helping keep Eng-Tips Forums free from inappropriate posts.
The Eng-Tips staff will check this out and take appropriate action.

Reply To This Thread

Posting in the Eng-Tips forums is a member-only feature.

Click Here to join Eng-Tips and talk with other members!


Resources