Autor
|
Thema: Rekursives Makro zum Batch-Umbenennen (5234 mal gelesen)
|
cad_praktikant Mitglied
Beiträge: 6 Registriert: 05.07.2006 V5R18
|
erstellt am: 22. Sep. 2011 10:54 <-- editieren / zitieren --> Unities abgeben:
Moin Forum, habe folgendes Problem - habe zwar schon einige Beispiele zur Rekursion gefunden (etwa, wie war Instanznamen mit Dateinamen rekursiv synchronisiert - weiß aber nicht, wie ich folgende Lösung aufziehen soll: Ich habe eine Baugruppe mit einer großen Zahl Tnterbaugruppen und Teilen. Das ganze soll per Makro rekursiv durchlaufen werden, dabei: - jede Baugruppe/jedes Part mit einer neuen Teilenummer versehen werden - die Baugruppe/das Part mit der geänderten Teilenummer an einem anderen Ort (unter Beibehaltung der UUID) gespeichert werden. - die Teile/Baugruppen durch das neu abgespeicherte Teil/Baugruppe in der übergeordneten Baugruppe ersetzt werden.
Ist es halbwegs verständlich? Gibt es evtl. Codesnippets (gerne auch für einen Teilbereich, alles rette mir die Abschlussarbeit )
Viele Grüße, Moe Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
RSchulz Moderator² Head of CAD, Content & Collaboration / IT-Manager
Beiträge: 5541 Registriert: 12.04.2007 @Work Lenovo P510 Xeon E5-1630v4 64GB DDR4 Quadro P2000 256GB PCIe SSD 512GB SSD SmarTeam V5-6 R2016 Sp04 CATIA V5-6 R2016 Sp05 E3.Series V2019 Altium Designer/Concord 19 Win 10 Pro x64
|
erstellt am: 22. Sep. 2011 11:03 <-- editieren / zitieren --> Unities abgeben: Nur für cad_praktikant
Hallo Moe, ich nehme mal an, dass du etwas lernen möchtest, daher lasse ich es jetzt erstmal mit dem Code und würde dir nur meine Logik, die ich hätte, näher bringen. Du brauchst in jedem Fall einen unabhängigen Baustein, der eine Produktstruktur durchläuft und die Sachen evtl. an einen weiteren zur Verarbeitung weitergibt. Den Baustein für die Produktstruktur nenne ich jetzt mal Check_Product... Dieser hätte folgende Funktion: >>> Produkt wird übergeben > prüfe alle Items in diesem Produkt > wenn Item gleich Teil, dann Liste Unterteil > wenn Item gleich Produkt dann übergebe Item an Check_Product Die Funktionen einzuarbeiten, sollte dann weniger das Problem sein. ------------------ MFG Rick Schulz Nettiquette (CAD.de) - Was ist die Systeminfo? - Wie man Fragen richtig stellt. - Unities Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
meisterlumpi Mitglied
Beiträge: 118 Registriert: 15.04.2011 Intel Core2 Quad Q6600 2.40 GHz | 4 GB RAM | Win7x64
|
erstellt am: 22. Sep. 2011 11:31 <-- editieren / zitieren --> Unities abgeben: Nur für cad_praktikant
ich glaube über eine selektion läuft das makro ein bisschen schneller, und der code ist IMHO wesentlich einfacher. mit dem modul anbei kannst du namen und partnummern in deiner baugruppe von allen products und parts anpassen. die 2 funktionen "NewName" und "NewPartNumber" kann man benutzen um den namen und die nummer anzupassen. NewName = OldName würde beispielsweise den Namen nicht ändern, bzw. den alten namen als neuen namen benutzen.. Zitat: - die Baugruppe/das Part mit der geänderten Teilenummer an einem anderen Ort (unter Beibehaltung der UUID) gespeichert werden.
durch das umbenennen sollte sich die UUID ja nicht ändern. zum speichern würde ich dann nochmal durch die selektion "loopen" und die dokumente mit .SaveAs an den neuen Platz speichern. Code: Function NewName(OldName As String) As String NewName = "1-Name-" & OldName End FunctionFunction NewPartNumber(OldPartNumber As String) As String NewPartNumber = "2-PartNumber-" & OldPartNumber End Function Sub CATMain() Dim i As Integer On Error Resume Next Dim ActiveDocument1 As Document Set ActiveDocument1 = CATIA.ActiveDocument If Err.Number <> 0 Then ' in case no open document was found ' ... Err.Clear End If Dim selection1 As Selection Set selection1 = ActiveDocument1.Selection '### - select all products selection1.Clear selection1.Search "CATProductSearch.Product,all" '### ' check document type for active document Select Case TypeName(ActiveDocument1) Case Is = "ProductDocument" ' active document is a product For i = 1 To selection1.Count With selection1.Item(i) ' check selected element If TypeName(.Value) = "Product" Then Dim product1 As Product Set product1 = .Value If TypeName(product1.Parent.Parent) = "Application" Then ' if item is main document product1.PartNumber = NewPartNumber(product1.PartNumber) Else ' if item is a subproduct Dim Product1Parent As Product Set Product1Parent = product1.Parent.Parent.ReferenceProduct Dim product2 As Product Set product2 = Product1Parent.Products.Item(product1.Name) product2.PartNumber = NewPartNumber(product2.PartNumber) product2.Name = NewName(product2.Name) End If End If End With Next i Case Is = "PartDocument" ' active document is a part Dim partDocument3 As PartDocument Set partDocument3 = ActiveDocument1 Dim product3 As Product Set product3 = partDocument3.GetItem(ActiveDocument1.Part.Name) product3.PartNumber = NewPartNumber(product3.PartNumber) Case Else ' active document is neither product nor part Call MsgBox("Macro only works with product- or part documents.", vbInformation) End Select If Err.Number <> 0 Then ' in case there was an error ' ... Err.Clear End If End Sub
[Diese Nachricht wurde von meisterlumpi am 25. Sep. 2011 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
cad_praktikant Mitglied
Beiträge: 6 Registriert: 05.07.2006 V5R18
|
erstellt am: 22. Sep. 2011 11:31 <-- editieren / zitieren --> Unities abgeben:
Klingt schon mal gar nicht schlecht - ich hab in der V5automation auch schon die Eigenschaft Partnumber für ein Product gefunden. Mein Aufbau würde sein: - Starte das Makro aus der Hauptbaugruppe - Läuft komplette Struktur durch (rekursiv?) - Überprüfung, ob aktuelles Element im Baum Baugruppe oder Part ist - Bei Part: Editiere Teilenummer (nach Schmema), Properties - Bei Product: Editiere Baugruppennummer - Speichern unter (nicht als New Document) unter Dateiname=Neue Teilenumme Das Replacen in der übergeordneten Baugruppe wäre nice to have, kann ich aber auch per Hand machen...(hinterher) Würde sicherlich gerne was lernen! Im Forum hab ich folgendes Snippet gefunden:
Code:
Sub CATMain() Set oMainProduct = CATIA.ActiveDocument.product Dim oMainProducts As Products Set oMainproducts = oMainProduct.Products Umbenennen oMainProducts Msgbox "Fertig" End Sub Sub Umbenennen(oProducts As Products) Dim oNumber As String Dim oName As String Dim i As Long For x = 1 to oProducts.Count 'Teilenummer auslesen/ändern nach Schema 'Bei Parts properties dazu 'Datei an anderem Ort und Dateiname=Teilenummer speichern unter" i=0 Do
On Error Resume Next i = i+1 If i>5000 Then ' Zahl soll angepasst werden Exit Do End If oInstance.Name = oNumber & "." & i If Err.Number = 0 Then Umbenennen oProducts.Item(x).ReferenceProduct.Products Exit Do ElseIf Err.Number = -2147467259 Then Err.Clear Err.Number = 0 Else Exit Do End If Loop If oInstance.Products.Count > 0 Then Umbenennen oInstance.Products End If Next End Sub
Wenn ich oInstance.Partnumber = "xyz" vor die auskommentierten Stellen ergänze, ändert sich nix in meiner Testbaugruppe. Oder ist das Objekt für einzelne Parts im Skript anders als oInstance?
Nochmal danke für die Schnelle Antwort! Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
cad_praktikant Mitglied
Beiträge: 6 Registriert: 05.07.2006 V5R18
|
erstellt am: 22. Sep. 2011 11:38 <-- editieren / zitieren --> Unities abgeben:
Zitat: Original erstellt von meisterlumpi: ich glaube über eine selektion läuft das makro ein bisschen schneller, und der code ist IMHO wesentlich einfacher.
Wieso bin ich da nicht selber draufgekommen? Wenn ich das richtig verstehe: Eine Selection für Products erstellen und dann per Schleife durchlaufen und dann prüfen, ob die einzelnen Selection-Elemente Product, Subproduct oder Part sind? Ein bisserl OT: hab neulich von einem (Maschinenbau-)Informatiker gehört, dass Selections in Catia schlecht, weil langsam sind. Aber immernoch schneller als eine Rekursion? Cool, wie schnell man hier gute Anregungen kriegt!
Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
meisterlumpi Mitglied
Beiträge: 118 Registriert: 15.04.2011 Intel Core2 Quad Q6600 2.40 GHz | 4 GB RAM | Win7x64
|
erstellt am: 22. Sep. 2011 12:39 <-- editieren / zitieren --> Unities abgeben: Nur für cad_praktikant
Zitat: Wenn ich das richtig verstehe: Eine Selection für Products erstellen und dann per Schleife durchlaufen und dann prüfen, ob die einzelnen Selection-Elemente Product, Subproduct oder Part sind?
genau, das macht das skript im prinzip schon. anbei das verbesserte skript, hier werden die teile auch im ordner 'SaveDirectory' gespeichert, den Ordner ("C:\temp\" im beispiel) muss es natürlich auch geben und der "\" am Ende ist wichtig! Code: Const SaveDirectory As String = "C:\temp\"Function NewName(OldName As String) As String NewName = "1-Name-" & OldName End Function Function NewPartNumber(OldPartNumber As String) As String NewPartNumber = "2-PartNumber-" & OldPartNumber End Function Sub CATMain() Dim i As Integer On Error Resume Next Dim ActiveDocument1 As Document Set ActiveDocument1 = CATIA.ActiveDocument If Err.Number <> 0 Then ' in case no open document was found ' ... Err.Clear End If Dim selection1 As Selection Set selection1 = ActiveDocument1.Selection '### - select all products selection1.Clear selection1.Search "CATProductSearch.Product,all" '### CATIA.DisplayFileAlerts = False ' check document type for active document Select Case TypeName(ActiveDocument1) Case Is = "ProductDocument" ' active document is a product For i = 1 To selection1.Count With selection1.Item(i) ' check selected element If TypeName(.Value) = "Product" Then Dim product1 As Product Set product1 = .Value If TypeName(product1.Parent.Parent) = "Application" Then ' if item is main document product1.PartNumber = NewPartNumber(product1.PartNumber) Else ' if item is a subproduct Dim Product1Parent As Product Set Product1Parent = product1.Parent.Parent.ReferenceProduct Dim product2 As Product Set product2 = Product1Parent.Products.Item(product1.Name) product1.PartNumber = NewPartNumber(product2.PartNumber) product2.Name = NewName(product2.Name) End If 'save the products in the new folder If TypeName(product1.ReferenceProduct.Parent) = "ProductDocument" Then Dim ProductDocument1 As ProductDocument Set ProductDocument1 = product1.ReferenceProduct.Parent Call ProductDocument1.SaveAs(SaveDirectory & product1.PartNumber & ".CATProduct") ElseIf TypeName(product1.ReferenceProduct.Parent) = "PartDocument" Then Dim PartDocument1 As PartDocument Set PartDocument1 = product1.ReferenceProduct.Parent Call PartDocument1.SaveAs(SaveDirectory & product1.PartNumber & ".CATPart") End If End If End With Next i Case Is = "PartDocument" ' active document is a part Dim partDocument3 As PartDocument Set partDocument3 = ActiveDocument1 Dim product3 As Product Set product3 = partDocument3.GetItem(ActiveDocument1.Part.Name) product3.PartNumber = NewPartNumber(product3.PartNumber) ' save the part document in the new folder Call partDocument3.SaveAs(SaveDirectory & product3.PartNumber) Case Else ' active document is neither product nor part Call MsgBox("Macro only works with product- or part documents.", vbInformation) End Select If Err.Number <> 0 Then ' in case there was an error ' ... Err.Clear End If End Sub
[Diese Nachricht wurde von meisterlumpi am 25. Sep. 2011 editiert.] Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
cad_praktikant Mitglied
Beiträge: 6 Registriert: 05.07.2006 V5R18
|
erstellt am: 23. Sep. 2011 13:57 <-- editieren / zitieren --> Unities abgeben:
Wow, das funktioniert super! Hab allerdings noch nen kleinen Bug gefunden - es muss heißen: Code: product1.PartNumber = NewPartNumber(product2.PartNumber) product2.Name = NewName(product2.Name)
Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |
meisterlumpi Mitglied
Beiträge: 118 Registriert: 15.04.2011 Intel Core2 Quad Q6600 2.40 GHz | 4 GB RAM | Win7x64
|
erstellt am: 25. Sep. 2011 19:09 <-- editieren / zitieren --> Unities abgeben: Nur für cad_praktikant
Zitat: Hab allerdings noch nen kleinen Bug gefunden..
super, vielen dank. daher kam auch der komische fehler.. deine korrektur war die richtige :-) hab den code in meinen beiträgen entsprechend geändert.. Eine Antwort auf diesen Beitrag verfassen (mit Zitat/Zitat des Beitrags) IP |