Macro to colorize SOLIDWORKS sheet metal and weldment cut-list items
This VBA macro allows to assign a unique color for each group of cut-list items (sheet metal or weldment) based on the value of the custom property.
The most common use of this macro will be to differentiate different type of weldment items based on the profile size.
Macro will automatically assign random color to the specific group. It is possible to specify the constant colors to use for the specific group instead of random colors.
Configuration
In order to specify the name of the custom property to read the value from and group cut-list items, change the value of the PRP_NAME constant
Const PRP_NAME As String = "Description" 'Change the value of Description to select different custom property
In order to specify colors it is required to modify the values within the InitColors method.
Sub InitColors(Optional dummy As Variant = Empty) ColorsMap.Add "SB BEAM 80 X 6", RGB(255, 0, 0) ColorsMap.Add "TUBE, RECTANGULAR 50 X 30 X 2.60", RGB(0, 255, 0) End Sub
To add new color to the map add the following line
ColorsMap.Add "[PROPERTY VALUE]", RGB([Red], [Green], [Blue])
For example to add the blue (RGB = 0, 0, 255) color to the weldment profile "50 X 50", it is required to add the following line
ColorsMap.Add "50 X 50", RGB(0, 0, 255)
Const PRP_NAME As String = "Description" Dim swApp As SldWorks.SldWorks Dim ColorsMap As Object Sub main() try_: On Error GoTo catch_ Set ColorsMap = CreateObject("Scripting.Dictionary") ColorsMap.CompareMode = vbTextCompare InitColors Set swApp = Application.SldWorks Dim swModel As SldWorks.ModelDoc2 Set swModel = swApp.ActiveDoc If Not swModel Is Nothing Then If swModel.GetType() = swDocumentTypes_e.swDocPART Then Dim vCutLists As Variant vCutLists = GetCutLists(swModel) ColorizeCutLists vCutLists swModel.GraphicsRedraw2 Else Err.Raise vbError, "", "Only part document is supported" End If Else Err.Raise vbError, "", "Open part document" End If GoTo finally_ catch_: MsgBox Err.Description, vbCritical finally_: End Sub Sub InitColors(Optional dummy As Variant = Empty) ColorsMap.Add "SB BEAM 80 X 6", RGB(255, 0, 0) ColorsMap.Add "TUBE, RECTANGULAR 50 X 30 X 2.60", RGB(0, 255, 0) End Sub Sub ColorizeCutLists(vCutLists As Variant) Dim i As Integer For i = 0 To UBound(vCutLists) Dim swCutList As SldWorks.Feature Set swCutList = vCutLists(i) Dim swBodyFolder As SldWorks.BodyFolder Set swBodyFolder = swCutList.GetSpecificFeature2 If swBodyFolder.GetBodyCount() > 0 Then Dim swCustPrpsMgr As SldWorks.CustomPropertyManager Set swCustPrpsMgr = swCutList.CustomPropertyManager Dim prpVal As String swCustPrpsMgr.Get5 PRP_NAME, True, "", prpVal, False Dim color As Long If ColorsMap.Exists(prpVal) Then color = ColorsMap(prpVal) Else color = RGB(Int(255 * Rnd), Int(255 * Rnd), Int(255 * Rnd)) ColorsMap.Add prpVal, color End If Dim j As Integer Dim vBodies As Variant vBodies = swBodyFolder.GetBodies For j = 0 To UBound(vBodies) Dim swBody As SldWorks.Body2 Set swBody = vBodies(j) Dim RGBHex As String RGBHex = Right("000000" & Hex(color), 6) Dim dMatPrps(8) As Double dMatPrps(0) = CInt("&H" & Mid(RGBHex, 5, 2)) / 255 dMatPrps(1) = CInt("&H" & Mid(RGBHex, 3, 2)) / 255 dMatPrps(2) = CInt("&H" & Mid(RGBHex, 1, 2)) / 255 dMatPrps(3) = 1 dMatPrps(4) = 1 dMatPrps(5) = 0.5 dMatPrps(6) = 0.3125 dMatPrps(7) = 0 dMatPrps(8) = 0 swBody.MaterialPropertyValues2 = dMatPrps Next End If Next End Sub Function GetCutLists(model As SldWorks.ModelDoc2) As Variant Dim swFeat As SldWorks.Feature Dim swCutLists() As SldWorks.Feature Set swFeat = model.FirstFeature While Not swFeat Is Nothing If swFeat.GetTypeName2 <> "HistoryFolder" Then ProcessFeature swFeat, swCutLists TraverseSubFeatures swFeat, swCutLists End If Set swFeat = swFeat.GetNextFeature Wend GetCutLists = swCutLists End Function Sub TraverseSubFeatures(parentFeat As SldWorks.Feature, cutLists() As SldWorks.Feature) Dim swChildFeat As SldWorks.Feature Set swChildFeat = parentFeat.GetFirstSubFeature While Not swChildFeat Is Nothing ProcessFeature swChildFeat, cutLists Set swChildFeat = swChildFeat.GetNextSubFeature() Wend End Sub Sub ProcessFeature(feat As SldWorks.Feature, cutLists() As SldWorks.Feature) If feat.GetTypeName2() = "SolidBodyFolder" Then Dim swBodyFolder As SldWorks.BodyFolder Set swBodyFolder = feat.GetSpecificFeature2 swBodyFolder.UpdateCutList ElseIf feat.GetTypeName2() = "CutListFolder" Then If Not Contains(cutLists, feat) Then If (Not cutLists) = -1 Then ReDim cutLists(0) Else ReDim Preserve cutLists(UBound(cutLists) + 1) End If Set cutLists(UBound(cutLists)) = feat End If End If End Sub Function Contains(arr As Variant, item As Object) As Boolean Dim i As Integer For i = 0 To UBound(arr) If arr(i) Is item Then Contains = True Exit Function End If Next Contains = False End Function