Arch: Fixed recursion loop in windows
This commit is contained in:
@@ -965,24 +965,22 @@ class _Window(ArchComponent.Component):
|
||||
ArchComponent.Component.onDocumentRestored(self,obj)
|
||||
self.setProperties(obj)
|
||||
|
||||
def onBeforeChange(self,obj,prop):
|
||||
|
||||
if prop in ["Base","WindowParts","Placement","HoleDepth","Height","Width","Hosts"]:
|
||||
setattr(self,prop,getattr(obj,prop))
|
||||
|
||||
def onChanged(self,obj,prop):
|
||||
|
||||
self.hideSubobjects(obj,prop)
|
||||
if not "Restore" in obj.State:
|
||||
if prop in ["Base","WindowParts","Placement","HoleDepth","Height","Width","Hosts"]:
|
||||
# anti-recursive loops, bc the base sketch will touch the Placement all the time
|
||||
ok = True
|
||||
if prop == "Placement":
|
||||
if hasattr(self,"Placement"):
|
||||
if self.Placement == obj.Placement:
|
||||
ok = False
|
||||
self.Placement = FreeCAD.Placement(obj.Placement)
|
||||
elif prop == "Hosts":
|
||||
if hasattr(self,"Hosts"):
|
||||
if self.Hosts == obj.Hosts:
|
||||
ok = False
|
||||
self.Hosts = obj.Hosts
|
||||
if ok and hasattr(obj,"Hosts"):
|
||||
touchhosts = False
|
||||
if hasattr(self,prop):
|
||||
if getattr(self,prop) != getattr(obj,prop):
|
||||
touchhosts = True
|
||||
if touchhosts and hasattr(obj,"Hosts"):
|
||||
for host in obj.Hosts:
|
||||
# mark host to recompute so it can detect this object
|
||||
host.touch()
|
||||
@@ -1007,12 +1005,206 @@ class _Window(ArchComponent.Component):
|
||||
ArchComponent.Component.onChanged(self,obj,prop)
|
||||
|
||||
|
||||
def buildShapes(self,obj):
|
||||
|
||||
import Part,DraftGeomUtils,math
|
||||
self.sshapes = []
|
||||
self.vshapes = []
|
||||
shapes = []
|
||||
rotdata = None
|
||||
for i in range(int(len(obj.WindowParts)/5)):
|
||||
wires = []
|
||||
hinge = None
|
||||
omode = None
|
||||
ssymbols = []
|
||||
vsymbols = []
|
||||
wstr = obj.WindowParts[(i*5)+2].split(',')
|
||||
for s in wstr:
|
||||
if "Wire" in s:
|
||||
j = int(s[4:])
|
||||
if obj.Base.Shape.Wires:
|
||||
if len(obj.Base.Shape.Wires) >= j:
|
||||
wires.append(obj.Base.Shape.Wires[j])
|
||||
elif "Edge" in s:
|
||||
hinge = int(s[4:])-1
|
||||
elif "Mode" in s:
|
||||
omode = int(s[-1])
|
||||
if wires:
|
||||
max_length = 0
|
||||
for w in wires:
|
||||
if w.BoundBox.DiagonalLength > max_length:
|
||||
max_length = w.BoundBox.DiagonalLength
|
||||
ext = w
|
||||
wires.remove(ext)
|
||||
shape = Part.Face(ext)
|
||||
norm = shape.normalAt(0,0)
|
||||
if hasattr(obj,"Normal"):
|
||||
if obj.Normal:
|
||||
if not DraftVecUtils.isNull(obj.Normal):
|
||||
norm = obj.Normal
|
||||
if hinge and omode:
|
||||
opening = None
|
||||
if hasattr(obj,"Opening"):
|
||||
if obj.Opening:
|
||||
opening = obj.Opening/100.0
|
||||
e = obj.Base.Shape.Edges[hinge]
|
||||
ev1 = e.Vertexes[0].Point
|
||||
ev2 = e.Vertexes[-1].Point
|
||||
if (ev2.z - ev1.z) < 0.1**Draft.precision():
|
||||
if ev2.y < ev1.y:
|
||||
ev1,ev2 = ev2,ev1
|
||||
elif ev2.z < ev1.z:
|
||||
ev1,ev2 = ev2,ev1
|
||||
p = None
|
||||
d = 0
|
||||
for v in shape.Vertexes:
|
||||
dist = v.Point.distanceToLine(ev1,ev2.sub(ev1))
|
||||
if dist > d:
|
||||
d = dist
|
||||
p = v.Point
|
||||
if p:
|
||||
chord = p.sub(ev1)
|
||||
enorm = ev2.sub(ev1)
|
||||
proj = DraftVecUtils.project(chord,enorm)
|
||||
v1 = ev1
|
||||
if proj.Length > 0:
|
||||
chord = p.sub(ev1.add(proj))
|
||||
p = v1.add(chord)
|
||||
v4 = p.add(DraftVecUtils.scale(enorm,0.5))
|
||||
if omode == 1: # Arc 90
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/4,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),90*opening]
|
||||
elif omode == 2: # Arc -90
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/4,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-90*opening]
|
||||
elif omode == 3: # Arc 45
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/8,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi/4,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),45*opening]
|
||||
elif omode == 4: # Arc -45
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/8,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi/4,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-45*opening]
|
||||
elif omode == 5: # Arc 180
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),180*opening]
|
||||
elif omode == 6: # Arc -180
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [ev1,ev2.sub(ev1),-180*opening]
|
||||
elif omode == 7: # tri
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
ssymbols.append(Part.LineSegment(p,v2).toShape())
|
||||
ssymbols.append(Part.LineSegment(v2,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),90*opening]
|
||||
elif omode == 8: # -tri
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
ssymbols.append(Part.LineSegment(p,v2).toShape())
|
||||
ssymbols.append(Part.LineSegment(v2,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-90*opening]
|
||||
elif omode == 9: # sliding
|
||||
pass
|
||||
elif omode == 10: # -sliding
|
||||
pass
|
||||
V = 0
|
||||
thk = obj.WindowParts[(i*5)+3]
|
||||
if "+V" in thk:
|
||||
thk = thk[:-2]
|
||||
V = obj.Frame.Value
|
||||
thk = float(thk) + V
|
||||
if thk:
|
||||
exv = DraftVecUtils.scaleTo(norm,thk)
|
||||
shape = shape.extrude(exv)
|
||||
for w in wires:
|
||||
f = Part.Face(w)
|
||||
f = f.extrude(exv)
|
||||
shape = shape.cut(f)
|
||||
if obj.WindowParts[(i*5)+4]:
|
||||
V = 0
|
||||
zof = obj.WindowParts[(i*5)+4]
|
||||
if "+V" in zof:
|
||||
zof = zof[:-2]
|
||||
V = obj.Offset.Value
|
||||
zof = float(zof) + V
|
||||
if zof:
|
||||
zov = DraftVecUtils.scaleTo(norm,zof)
|
||||
shape.translate(zov)
|
||||
for symb in ssymbols:
|
||||
symb.translate(zov)
|
||||
for symb in vsymbols:
|
||||
symb.translate(zov)
|
||||
if rotdata and hinge and omode:
|
||||
rotdata[0] = rotdata[0].add(zov)
|
||||
if obj.WindowParts[(i*5)+1] == "Louvre":
|
||||
if hasattr(obj,"LouvreWidth"):
|
||||
if obj.LouvreWidth and obj.LouvreSpacing:
|
||||
bb = shape.BoundBox
|
||||
bb.enlarge(10)
|
||||
step = obj.LouvreWidth.Value+obj.LouvreSpacing.Value
|
||||
if step < bb.ZLength:
|
||||
box = Part.makeBox(bb.XLength,bb.YLength,obj.LouvreWidth.Value)
|
||||
boxes = []
|
||||
for i in range(int(bb.ZLength/step)+1):
|
||||
b = box.copy()
|
||||
b.translate(FreeCAD.Vector(bb.XMin,bb.YMin,bb.ZMin+i*step))
|
||||
boxes.append(b)
|
||||
self.boxes = Part.makeCompound(boxes)
|
||||
#rot = obj.Base.Placement.Rotation
|
||||
#self.boxes.rotate(self.boxes.BoundBox.Center,rot.Axis,math.degrees(rot.Angle))
|
||||
self.boxes.translate(shape.BoundBox.Center.sub(self.boxes.BoundBox.Center))
|
||||
shape = shape.cut(self.boxes)
|
||||
if rotdata:
|
||||
shape.rotate(rotdata[0],rotdata[1],rotdata[2])
|
||||
shapes.append(shape)
|
||||
self.sshapes.extend(ssymbols)
|
||||
self.vshapes.extend(vsymbols)
|
||||
return shapes
|
||||
|
||||
def execute(self,obj):
|
||||
|
||||
if self.clone(obj):
|
||||
clonedProxy = obj.CloneOf.Proxy
|
||||
if not (hasattr(clonedProxy, "sshapes") and hasattr(clonedProxy, "vshapes")):
|
||||
clonedProxy.execute(obj.CloneOf)
|
||||
clonedProxy.buildShapes(obj.CloneOf)
|
||||
self.sshapes = clonedProxy.sshapes
|
||||
self.vshapes = clonedProxy.vshapes
|
||||
if hasattr(clonedProxy, "boxes"):
|
||||
@@ -1028,193 +1220,7 @@ class _Window(ArchComponent.Component):
|
||||
if obj.Base.isDerivedFrom("Part::Feature"):
|
||||
if hasattr(obj,"WindowParts"):
|
||||
if obj.WindowParts and (len(obj.WindowParts)%5 == 0):
|
||||
shapes = []
|
||||
rotdata = None
|
||||
for i in range(int(len(obj.WindowParts)/5)):
|
||||
wires = []
|
||||
hinge = None
|
||||
omode = None
|
||||
ssymbols = []
|
||||
vsymbols = []
|
||||
wstr = obj.WindowParts[(i*5)+2].split(',')
|
||||
for s in wstr:
|
||||
if "Wire" in s:
|
||||
j = int(s[4:])
|
||||
if obj.Base.Shape.Wires:
|
||||
if len(obj.Base.Shape.Wires) >= j:
|
||||
wires.append(obj.Base.Shape.Wires[j])
|
||||
elif "Edge" in s:
|
||||
hinge = int(s[4:])-1
|
||||
elif "Mode" in s:
|
||||
omode = int(s[-1])
|
||||
if wires:
|
||||
max_length = 0
|
||||
for w in wires:
|
||||
if w.BoundBox.DiagonalLength > max_length:
|
||||
max_length = w.BoundBox.DiagonalLength
|
||||
ext = w
|
||||
wires.remove(ext)
|
||||
shape = Part.Face(ext)
|
||||
norm = shape.normalAt(0,0)
|
||||
if hasattr(obj,"Normal"):
|
||||
if obj.Normal:
|
||||
if not DraftVecUtils.isNull(obj.Normal):
|
||||
norm = obj.Normal
|
||||
if hinge and omode:
|
||||
opening = None
|
||||
if hasattr(obj,"Opening"):
|
||||
if obj.Opening:
|
||||
opening = obj.Opening/100.0
|
||||
e = obj.Base.Shape.Edges[hinge]
|
||||
ev1 = e.Vertexes[0].Point
|
||||
ev2 = e.Vertexes[-1].Point
|
||||
if (ev2.z - ev1.z) < 0.1**Draft.precision():
|
||||
if ev2.y < ev1.y:
|
||||
ev1,ev2 = ev2,ev1
|
||||
elif ev2.z < ev1.z:
|
||||
ev1,ev2 = ev2,ev1
|
||||
p = None
|
||||
d = 0
|
||||
for v in shape.Vertexes:
|
||||
dist = v.Point.distanceToLine(ev1,ev2.sub(ev1))
|
||||
if dist > d:
|
||||
d = dist
|
||||
p = v.Point
|
||||
if p:
|
||||
chord = p.sub(ev1)
|
||||
enorm = ev2.sub(ev1)
|
||||
proj = DraftVecUtils.project(chord,enorm)
|
||||
v1 = ev1
|
||||
if proj.Length > 0:
|
||||
chord = p.sub(ev1.add(proj))
|
||||
p = v1.add(chord)
|
||||
v4 = p.add(DraftVecUtils.scale(enorm,0.5))
|
||||
if omode == 1: # Arc 90
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/4,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),90*opening]
|
||||
elif omode == 2: # Arc -90
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/4,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-90*opening]
|
||||
elif omode == 3: # Arc 45
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/8,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi/4,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),45*opening]
|
||||
elif omode == 4: # Arc -45
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/8,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi/4,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-45*opening]
|
||||
elif omode == 5: # Arc 180
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,math.pi,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),180*opening]
|
||||
elif omode == 6: # Arc -180
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
v3 = v1.add(DraftVecUtils.rotate(chord,-math.pi,enorm))
|
||||
ssymbols.append(Part.Arc(p,v2,v3).toShape())
|
||||
ssymbols.append(Part.LineSegment(v3,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [ev1,ev2.sub(ev1),-180*opening]
|
||||
elif omode == 7: # tri
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,math.pi/2,enorm))
|
||||
ssymbols.append(Part.LineSegment(p,v2).toShape())
|
||||
ssymbols.append(Part.LineSegment(v2,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),90*opening]
|
||||
elif omode == 8: # -tri
|
||||
v2 = v1.add(DraftVecUtils.rotate(chord,-math.pi/2,enorm))
|
||||
ssymbols.append(Part.LineSegment(p,v2).toShape())
|
||||
ssymbols.append(Part.LineSegment(v2,v1).toShape())
|
||||
vsymbols.append(Part.LineSegment(v1,v4).toShape())
|
||||
vsymbols.append(Part.LineSegment(v4,ev2).toShape())
|
||||
if opening:
|
||||
rotdata = [v1,ev2.sub(ev1),-90*opening]
|
||||
elif omode == 9: # sliding
|
||||
pass
|
||||
elif omode == 10: # -sliding
|
||||
pass
|
||||
V = 0
|
||||
thk = obj.WindowParts[(i*5)+3]
|
||||
if "+V" in thk:
|
||||
thk = thk[:-2]
|
||||
V = obj.Frame.Value
|
||||
thk = float(thk) + V
|
||||
if thk:
|
||||
exv = DraftVecUtils.scaleTo(norm,thk)
|
||||
shape = shape.extrude(exv)
|
||||
for w in wires:
|
||||
f = Part.Face(w)
|
||||
f = f.extrude(exv)
|
||||
shape = shape.cut(f)
|
||||
if obj.WindowParts[(i*5)+4]:
|
||||
V = 0
|
||||
zof = obj.WindowParts[(i*5)+4]
|
||||
if "+V" in zof:
|
||||
zof = zof[:-2]
|
||||
V = obj.Offset.Value
|
||||
zof = float(zof) + V
|
||||
if zof:
|
||||
zov = DraftVecUtils.scaleTo(norm,zof)
|
||||
shape.translate(zov)
|
||||
for symb in ssymbols:
|
||||
symb.translate(zov)
|
||||
for symb in vsymbols:
|
||||
symb.translate(zov)
|
||||
if rotdata and hinge and omode:
|
||||
rotdata[0] = rotdata[0].add(zov)
|
||||
if obj.WindowParts[(i*5)+1] == "Louvre":
|
||||
if hasattr(obj,"LouvreWidth"):
|
||||
if obj.LouvreWidth and obj.LouvreSpacing:
|
||||
bb = shape.BoundBox
|
||||
bb.enlarge(10)
|
||||
step = obj.LouvreWidth.Value+obj.LouvreSpacing.Value
|
||||
if step < bb.ZLength:
|
||||
box = Part.makeBox(bb.XLength,bb.YLength,obj.LouvreWidth.Value)
|
||||
boxes = []
|
||||
for i in range(int(bb.ZLength/step)+1):
|
||||
b = box.copy()
|
||||
b.translate(FreeCAD.Vector(bb.XMin,bb.YMin,bb.ZMin+i*step))
|
||||
boxes.append(b)
|
||||
self.boxes = Part.makeCompound(boxes)
|
||||
#rot = obj.Base.Placement.Rotation
|
||||
#self.boxes.rotate(self.boxes.BoundBox.Center,rot.Axis,math.degrees(rot.Angle))
|
||||
self.boxes.translate(shape.BoundBox.Center.sub(self.boxes.BoundBox.Center))
|
||||
shape = shape.cut(self.boxes)
|
||||
if rotdata:
|
||||
shape.rotate(rotdata[0],rotdata[1],rotdata[2])
|
||||
shapes.append(shape)
|
||||
self.sshapes.extend(ssymbols)
|
||||
self.vshapes.extend(vsymbols)
|
||||
shapes = self.buildShapes(obj)
|
||||
if shapes:
|
||||
base = Part.makeCompound(shapes)
|
||||
elif not obj.WindowParts:
|
||||
|
||||
Reference in New Issue
Block a user