From b678c360cfa11223576147312ce87364386c3d64 Mon Sep 17 00:00:00 2001 From: "Zheng, Lei" Date: Mon, 6 Aug 2018 00:39:00 +0800 Subject: [PATCH] assembly: auto reload partial document on unfreeze --- assembly.py | 54 ++++++++++++++++++++++++++++++++++++----------------- 1 file changed, 37 insertions(+), 17 deletions(-) diff --git a/assembly.py b/assembly.py index bf3222c..14a4dc5 100644 --- a/assembly.py +++ b/assembly.py @@ -1,5 +1,5 @@ import os -from collections import namedtuple +from collections import namedtuple,defaultdict import FreeCAD, FreeCADGui, Part from PySide import QtCore, QtGui from . import utils, gui @@ -285,8 +285,10 @@ def showParts(self): return vobj.ChildViewProvider = 'PartGui::ViewProviderPartExt' cvp = vobj.ChildViewProvider - cvp.MapTransparency = True - cvp.MapFaceColor = True + if not cvp.MapTransparency: + cvp.MapTransparency = True + if not cvp.MapFaceColor: + cvp.MapFaceColor = True cvp.ForceMapColors = True vobj.DefaultMode = mode @@ -2308,6 +2310,7 @@ class Assembly(AsmGroup): _PartArrayMap = {} # maps array part to assembly _ScheduleTimer = QtCore.QTimer() _PendingRemove = [] + _PendingReload = defaultdict(set) def __init__(self): self.parts = set() @@ -2446,6 +2449,15 @@ def scheduleDelete(cls,doc,names): pass return cls._PendingRemove.append((doc,names)) + cls.schedule() + + @classmethod + def scheduleReload(cls,obj): + cls._PendingReload[obj.Document.Name].add(obj.Name) + cls.schedule() + + @classmethod + def schedule(cls): if not cls._ScheduleTimer.isSingleShot(): cls._ScheduleTimer.setSingleShot(True) cls._ScheduleTimer.timeout.connect(Assembly.onSchedule) @@ -2454,12 +2466,22 @@ def scheduleDelete(cls,doc,names): @classmethod def onSchedule(cls): - pending = [] + for doc in FreeCAD.listDocuments().values(): + if doc.Recomputing: + cls._ScheduleTimer.start(50) + return + for name,onames in cls._PendingReload.items(): + doc = FreeCADGui.reload(name) + if not doc: + break + for oname in onames: + obj = doc.getObject(oname) + if getattr(obj,'Freeze',None): + obj.Freeze = False + cls._PendingReload.clear() + for doc,names in cls._PendingRemove: try: - if doc.Recomputing: - pending.append((doc,names)) - continue for name in names: try: doc.removeObject(name) @@ -2467,9 +2489,7 @@ def onSchedule(cls): pass except Exception: pass - cls._PendingRemove = pending - if pending: - cls._ScheduleTimer.start(50) + cls._PendingRemove = [] def onSolverChanged(self): for obj in self.getConstraintGroup().Group: @@ -2566,11 +2586,8 @@ def buildShape(self): if not shapes: raise RuntimeError('No shape found in parts') if len(shapes) == 1: - shape = shapes[0] - # make sure the 'shape' has identity transform to prevent it from - # messing up with assembly's or partGroup's Placement - if not shape.Placement.isIdentity(): - shape = Part.makeCompound(shape) + # hide shape placement, and get element mapping + shape = Part.makeCompound(shapes) elif obj.BuildShape == BuildShapeFuse: shape = shapes[0].fuse(shapes[1:]) elif obj.BuildShape == BuildShapeCut: @@ -2582,13 +2599,12 @@ def buildShape(self): if hasattr(partGroup,'Shape'): if obj.Freeze or obj.BuildShape!=BuildShapeCompound: - shape.Tag = partGroup.ID partGroup.Shape = shape + shape.Tag = partGroup.ID else: partGroup.Shape = Part.Shape() shape.Placement = obj.Placement - shape.Tag = obj.ID obj.Shape = shape def attach(self, obj): @@ -2607,6 +2623,7 @@ def linkSetup(self,obj): obj.configLinkProperty('ColoredElements') if not hasattr(obj,'Freeze'): obj.addProperty('App::PropertyBool','Freeze','Base','') + obj.setPropertyStatus('Freeze','PartialTrigger') super(Assembly,self).linkSetup(obj) obj.setPropertyStatus('Group','Output') System.attach(obj) @@ -2639,6 +2656,9 @@ def onChanged(self, obj, prop): if prop == 'Freeze': if obj.Freeze == self.frozen: return + if obj.Document.Partial: + Assembly.scheduleReload(obj) + return self.upgrade() if obj.BuildShape==BuildShapeNone: self.buildShape()