From 70162bdfb2046c683a083273eeec4fa7671105c6 Mon Sep 17 00:00:00 2001 From: Florian Festi Date: Thu, 6 Apr 2023 21:06:28 +0200 Subject: [PATCH] Move Lid details and creation into own LidSettings class Add new ontop and overthetop lid styles Replace _ChestLid mixin class. Currently supported for UBox, UniversalBox and ABox Resolves: #356 --- boxes/__init__.py | 4 ++ boxes/generators/abox.py | 8 +-- boxes/generators/ubox.py | 11 ++-- boxes/generators/universalbox.py | 11 ++-- boxes/lids.py | 103 +++++++++++++++++++++++++------ 5 files changed, 98 insertions(+), 39 deletions(-) diff --git a/boxes/__init__.py b/boxes/__init__.py index 30ee6b5..fc4f31e 100755 --- a/boxes/__init__.py +++ b/boxes/__init__.py @@ -634,6 +634,10 @@ class Boxes: # HexHoles self.hexHolesSettings = HexHolesSettings(self.thickness, True, **self.edgesettings.get("HexHoles", {})) + # Lids + self.lidSettings = lids.LidSettings(self.thickness, True, + **self.edgesettings.get("Lid", {})) + self.lid = lids.Lid(self, self.lidSettings) # Nuts self.addPart(NutHole(self, None)) diff --git a/boxes/generators/abox.py b/boxes/generators/abox.py index cf984d3..dbcb9a1 100644 --- a/boxes/generators/abox.py +++ b/boxes/generators/abox.py @@ -15,6 +15,7 @@ # along with this program. If not, see . from boxes import * +from boxes.lids import LidSettings class ABox(Boxes): """A simple Box""" @@ -26,11 +27,8 @@ class ABox(Boxes): def __init__(self) -> None: Boxes.__init__(self) self.addSettingsArgs(edges.FingerJointSettings) + self.addSettingsArgs(LidSettings) self.buildArgParser("x", "y", "h", "outside", "bottom_edge") - #self.argparser.add_argument( - # "--lid", action="store", type=str, default="default (none)", - # choices=("default (none)", "chest", "flat"), - # help="additional lid (for straight top_edge only)") def render(self): x, y, h = self.x, self.y, self.h @@ -53,7 +51,7 @@ class ABox(Boxes): if self.bottom_edge != "e": self.rectangularWall(x, y, "ffff", move="up") - #self.drawAddOnLid(x, y, self.lid) + self.lid(x, y) self.rectangularWall(x, h, [b, sideedge, t3, sideedge], ignore_widths=[1, 6], move="right only") diff --git a/boxes/generators/ubox.py b/boxes/generators/ubox.py index 998ae36..e5017d2 100644 --- a/boxes/generators/ubox.py +++ b/boxes/generators/ubox.py @@ -15,10 +15,10 @@ # along with this program. If not, see . from boxes import * -from boxes.lids import _TopEdge, _ChestLid +from boxes.lids import _TopEdge, LidSettings -class UBox(_TopEdge, _ChestLid): +class UBox(_TopEdge): """Box various options for different stypes and lids""" ui_group = "FlexBox" @@ -27,14 +27,11 @@ class UBox(_TopEdge, _ChestLid): Boxes.__init__(self) self.addTopEdgeSettings() self.addSettingsArgs(edges.FlexSettings) + self.addSettingsArgs(LidSettings) self.buildArgParser("top_edge", "x", "y", "h") self.argparser.add_argument( "--radius", action="store", type=float, default=30.0, help="radius of bottom corners") - self.argparser.add_argument( - "--lid", action="store", type=str, default="default (none)", - choices=("default (none)", "chest", "flat"), - help="additional lid") self.angle = 0 def U(self, x, y, r, edge="e", move=None, label=""): @@ -102,6 +99,6 @@ class UBox(_TopEdge, _ChestLid): self.Uwall(x, y, h, r, [t2, t4], move="up", label=_("wall")) self.drawLid(x, h, self.top_edge) - self.drawAddOnLid(x, h, self.lid) + self.lid(x, h, self.top_edge) diff --git a/boxes/generators/universalbox.py b/boxes/generators/universalbox.py index 9091b4a..5cbad0f 100644 --- a/boxes/generators/universalbox.py +++ b/boxes/generators/universalbox.py @@ -16,9 +16,9 @@ from boxes import * from boxes.edges import Bolts -from boxes.lids import _TopEdge, _ChestLid +from boxes.lids import _TopEdge -class UniversalBox(_TopEdge, _ChestLid): +class UniversalBox(_TopEdge): """Box with various options for different styles and lids""" ui_group = "Box" @@ -28,6 +28,7 @@ class UniversalBox(_TopEdge, _ChestLid): self.addTopEdgeSettings(roundedtriangle={"outset" : 1}, hinge={"outset" : True}) self.addSettingsArgs(edges.FlexSettings) + self.addSettingsArgs(lids.LidSettings) self.buildArgParser("top_edge", "bottom_edge", "x", "y", "h", "outside") self.argparser.add_argument( @@ -35,10 +36,6 @@ class UniversalBox(_TopEdge, _ChestLid): default="finger joints", choices=("finger joints", "finger holes"), help="connections used for the vertical edges") - self.argparser.add_argument( - "--lid", action="store", type=str, default="default (none)", - choices=("default (none)", "chest", "flat"), - help="additional lid (for straight top_edge only)") def top_hole(self, x, y, top_edge): t = self.thickness @@ -93,7 +90,7 @@ class UniversalBox(_TopEdge, _ChestLid): lambda:self.top_hole(x, y, self.top_edge)], move="up", label="top hole") self.set_source_color(Color.BLACK) self.drawLid(x, y, self.top_edge, [d2, d3]) - self.drawAddOnLid(x, y, self.lid) + self.lid(x, y, self.top_edge) self.rectangularWall(x, h, [b, sideedge, tf, sideedge], ignore_widths=[1, 6], diff --git a/boxes/lids.py b/boxes/lids.py index ef770b3..4db7baa 100644 --- a/boxes/lids.py +++ b/boxes/lids.py @@ -13,25 +13,101 @@ # You should have received a copy of the GNU General Public License # along with this program. If not, see . -from boxes import * +from boxes import edges, Boxes -class _ChestLid(Boxes): +class LidSettings(edges.Settings): - def getR(self, x, angle=0): + """Settings for the Lid +Values: +*absolute + + * style : "none" : type of lid to create + +* relative (in multiples of thickness) + + * height : 4.0 : height of the brim (if any) + * play : 0.1 : play when sliding the lid on (if applicable) + """ + + absolute_params = { + "style" : ("none", "flat", "chest", "overthetop", "ontop"), + } + + relative_params = { + "height" : 4.0, + "play" : 0.1, + } + + +class Lid: + + def __init__(self, boxes, settings): + self.boxes = boxes + self.settings = settings + + def __getattr__(self, name): + """Hack for using unalter code form Boxes class""" + if hasattr(self.settings, name): + return getattr(self.settings, name) + return getattr(self.boxes, name) + + def handleCB(self, x, y): + def cb(): + pass + + return cb + + def __call__(self, x, y, edge=None): + t = self.thickness + style = self.settings.style + height = self.height + if style == "flat": + self.rectangularWall(x, y, "eeee", move="right", label="lid bottom") + self.rectangularWall(x, y, "EEEE", move="up", label="lid top") + elif style == "chest": + self.chestSide(x, move="right", label="lid right") + self.chestSide(x, move="up", label="lid left") + self.chestSide(x, move="left only", label="invisible") + self.chestTop(x, y, move="up", label="lid top") + elif style in ("overthetop", "ontop"): + x2 = x + y2 = y + if style == "overthetop": + x2 += 2*t + self.play + y2 += 2*t + self.play + self.rectangularWall(x2, y2, "ffff", move="up") + self.rectangularWall(x2, self.height, "eFFF", + ignore_widths=[1, 2, 5, 6], move="up") + self.rectangularWall(x2, self.height, "eFFF", + ignore_widths=[1, 2, 5, 6], move="up") + self.rectangularWall(y2, self.height, "efFf", + ignore_widths=[1, 2, 5, 6], move="up") + self.rectangularWall(y2, self.height, "efFf", + ignore_widths=[1, 2, 5, 6], move="up") + if style == "ontop": + self.rectangularWall(y - self.play, height + 2*t, "eeee", + move="up") + self.rectangularWall(y - self.play, height + 2*t, "eeee", + move="up") + else: + return False + return True + + def getChestR(self, x, angle=0): t = self.thickness d = x - 2*math.sin(math.radians(angle)) * (3*t) r = d / 2.0 / math.cos(math.radians(angle)) return r - def side(self, x, angle=0, move="", label=""): + def chestSide(self, x, angle=0, move="", label=""): if "a" not in self.edges: s = edges.FingerJointSettings(self.thickness, True, finger=1.0, space=1.0) s.edgeObjects(self, "aA.") t = self.thickness - r = self.getR(x, angle) + r = self.getChestR(x, angle) if self.move(x+2*t, 0.5*x+3*t, move, True, label=label): return @@ -45,14 +121,14 @@ class _ChestLid(Boxes): self.move(x+2*t, 0.5*x+3*t, move, False, label=label) - def top(self, x, y, angle=0, move=None, label=""): + def chestTop(self, x, y, angle=0, move=None, label=""): if "a" not in self.edges: s = edges.FingerJointSettings(self.thickness, True, finger=1.0, space=1.0) s.edgeObjects(self, "aA.") t = self.thickness - l = math.radians(180-2*angle) * self.getR(x, angle) + l = math.radians(180-2*angle) * self.getChestR(x, angle) tw = l + 6*t th = y+2*t @@ -75,19 +151,6 @@ class _ChestLid(Boxes): self.move(tw, th, move, label=label) - def drawAddOnLid(self, x, y, style): - if style == "flat": - self.rectangularWall(x, y, "eeee", move="right", label="lid bottom") - self.rectangularWall(x, y, "EEEE", move="up", label="lid top") - elif style == "chest": - self.side(x, move="right", label="lid right") - self.side(x, move="up", label="lid left") - self.side(x, move="left only", label="invisible") - self.top(x, y, move="up", label="lid top") - else: - return False - return True - class _TopEdge(Boxes): def addTopEdgeSettings(self, fingerjoint={}, stackable={}, hinge={},