Skip to content

Commit

Permalink
Merge pull request #10 from jeroen94704/optimize_base_generation
Browse files Browse the repository at this point in the history
Optimized the bin base generation and moved it to a common module
  • Loading branch information
jeroen94704 authored Jun 14, 2024
2 parents 5a7d4e6 + c713cf0 commit c034ee9
Show file tree
Hide file tree
Showing 6 changed files with 96 additions and 147 deletions.
Empty file added generators/__init__.py
Empty file.
78 changes: 5 additions & 73 deletions generators/classicbin/classicbin_generator.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
from grid_constants import *
import logging

from generators.common.bin_base import bin_base

logger = logging.getLogger('CBG')

class Generator:
Expand All @@ -27,69 +29,6 @@ def precalculate(self):
self.compartmentSizeY = self.internalSizeY / self.settings.compartmentsY
self.compartmentSizeZ = (self.settings.sizeUnitsZ-1)*self.grid.HEIGHT_UNITSIZE_MM

def unit_base(self, basePlane):
"""Construct a 1x1 GridFinity unit base on the provided workplane"""

# The elements are constructed "centered" because that makes life easier.
baseBottom = basePlane.box(self.grid.BASE_BOTTOM_SIZE_X, self.grid.BASE_BOTTOM_SIZE_Y, self.grid.BASE_BOTTOM_THICKNESS, combine=False)
baseBottom = baseBottom.edges("|Z").fillet(self.grid.BASE_BOTTOM_FILLET_RADIUS)
baseBottom = baseBottom.faces("<Z").chamfer(self.grid.BASE_BOTTOM_CHAMFER_SIZE)

baseTop = baseBottom.faces(">Z").workplane()
baseTop = baseTop.box(self.grid.BRICK_UNIT_SIZE_X, self.grid.BRICK_UNIT_SIZE_Y, self.grid.BASE_TOP_THICKNESS, centered=(True, True, False), combine=False)
baseTop = baseTop.edges("|Z").fillet(self.grid.CORNER_FILLET_RADIUS)
baseTop = baseTop.faces("<Z").chamfer(self.grid.BASE_TOP_CHAMFER_SIZE)

result = baseTop | baseBottom

if self.settings.addMagnetHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y)])
result = result.hole(self.settings.magnetHoleDiameter, self.grid.DEFAULT_MAGNET_HOLE_DEPTH)

if self.settings.addRemovalHoles:
result = result.pushPoints([(self.grid.HOLE_OFFSET_X-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, self.grid.HOLE_OFFSET_Y-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-self.grid.HOLE_OFFSET_X+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, self.grid.HOLE_OFFSET_Y-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(self.grid.HOLE_OFFSET_X-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, -self.grid.HOLE_OFFSET_Y+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-self.grid.HOLE_OFFSET_X+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, -self.grid.HOLE_OFFSET_Y+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET)])
result = result.hole(self.grid.REMOVABLE_MAGNET_HOLE_DIAMETER, self.grid.DEFAULT_MAGNET_HOLE_DEPTH)

if self.settings.addScrewHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y)])
result = result.hole(self.grid.SCREW_HOLE_DIAMETER, self.grid.SCREW_HOLE_DEPTH)

# Translate the result because it is now centered around the origin, which is inconvenient for subsequent steps
result = result.translate((self.grid.BRICK_UNIT_SIZE_X/2, self.grid.BRICK_UNIT_SIZE_Y/2, self.grid.BASE_BOTTOM_THICKNESS/2))

return result

def grid_base(self, basePlane):
"""Construct a base of WidthxLength grid units"""

result = basePlane.workplane()

for x in range(self.settings.sizeUnitsX):
for y in range(self.settings.sizeUnitsY):
result.add(self.unit_base(basePlane).translate((x*self.grid.GRID_UNIT_SIZE_X_MM, y*self.grid.GRID_UNIT_SIZE_Y_MM, 0)))

return result

def brick_floor(self, basePlane):
"""Create a floor covering all unit bases"""

floor = basePlane.box(self.brickSizeX, self.brickSizeY, self.grid.FLOOR_THICKNESS, centered = False, combine = False)

floor = floor.edges("|Z").fillet(self.grid.CORNER_FILLET_RADIUS)

return floor

def outer_wall(self, basePlane):
"""Create the outer wall of the bin"""

Expand Down Expand Up @@ -209,18 +148,11 @@ def validate_settings(self):

def generate_model(self):
plane = cq.Workplane("XY")
result = plane.workplane()

# Add the base of Gridfinity profiles
result.add(self.grid_base(plane))

# Continue from the top of the base
plane = result.faces(">Z").workplane()

# Add the floor of the bin
result.add(self.brick_floor(plane))
# First create the base
result = bin_base(plane, self.settings, self.grid)

# Continue from the top of the floor
# Continue at the top of the base
plane = result.faces(">Z").workplane()

# Add the outer walls
Expand Down
Empty file added generators/common/__init__.py
Empty file.
85 changes: 85 additions & 0 deletions generators/common/bin_base.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
import cadquery as cq

from grid_constants import *

def unit_base(basePlane, settings, grid):
"""Construct a 1x1 GridFinity unit base on the provided workplane"""

# The elements are constructed "centered" because that makes life easier.
baseBottom = basePlane.box(grid.BASE_BOTTOM_SIZE_X, grid.BASE_BOTTOM_SIZE_Y, grid.BASE_BOTTOM_THICKNESS, combine=False)
baseBottom = baseBottom.edges("|Z").fillet(grid.BASE_BOTTOM_FILLET_RADIUS)
baseBottom = baseBottom.faces("<Z").chamfer(grid.BASE_BOTTOM_CHAMFER_SIZE)

baseTop = baseBottom.faces(">Z").workplane()
baseTop = baseTop.box(grid.BRICK_UNIT_SIZE_X, grid.BRICK_UNIT_SIZE_Y, grid.BASE_TOP_THICKNESS, centered=(True, True, False), combine=False)
baseTop = baseTop.edges("|Z").fillet(grid.CORNER_FILLET_RADIUS)
baseTop = baseTop.faces("<Z").chamfer(grid.BASE_TOP_CHAMFER_SIZE)

result = baseTop | baseBottom

if settings.addMagnetHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(grid.HOLE_OFFSET_X, grid.HOLE_OFFSET_Y),
(-grid.HOLE_OFFSET_X, grid.HOLE_OFFSET_Y),
(grid.HOLE_OFFSET_X, -grid.HOLE_OFFSET_Y),
(-grid.HOLE_OFFSET_X, -grid.HOLE_OFFSET_Y)])
result = result.hole(settings.magnetHoleDiameter, grid.DEFAULT_MAGNET_HOLE_DEPTH)

if settings.addRemovalHoles:
result = result.pushPoints([(grid.HOLE_OFFSET_X-grid.REMOVABLE_MAGNET_HOLE_OFFSET, grid.HOLE_OFFSET_Y-grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-grid.HOLE_OFFSET_X+grid.REMOVABLE_MAGNET_HOLE_OFFSET, grid.HOLE_OFFSET_Y-grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(grid.HOLE_OFFSET_X-grid.REMOVABLE_MAGNET_HOLE_OFFSET, -grid.HOLE_OFFSET_Y+grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-grid.HOLE_OFFSET_X+grid.REMOVABLE_MAGNET_HOLE_OFFSET, -grid.HOLE_OFFSET_Y+grid.REMOVABLE_MAGNET_HOLE_OFFSET)])
result = result.hole(grid.REMOVABLE_MAGNET_HOLE_DIAMETER, grid.DEFAULT_MAGNET_HOLE_DEPTH)

if settings.addScrewHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(grid.HOLE_OFFSET_X, grid.HOLE_OFFSET_Y),
(-grid.HOLE_OFFSET_X, grid.HOLE_OFFSET_Y),
(grid.HOLE_OFFSET_X, -grid.HOLE_OFFSET_Y),
(-grid.HOLE_OFFSET_X, -grid.HOLE_OFFSET_Y)])
result = result.hole(grid.SCREW_HOLE_DIAMETER, grid.SCREW_HOLE_DEPTH)

# Translate the result because it is now centered around the origin, which is inconvenient for subsequent steps
result = result.translate((grid.BRICK_UNIT_SIZE_X/2, grid.BRICK_UNIT_SIZE_Y/2, grid.BASE_BOTTOM_THICKNESS/2))

return result

def grid_base(basePlane, settings, grid):
"""Construct a base of WidthxLength grid units"""

result = basePlane.workplane()

base_unit = unit_base(basePlane, settings, grid)

for x in range(settings.sizeUnitsX):
for y in range(settings.sizeUnitsY):
result.add(base_unit.translate((x*grid.GRID_UNIT_SIZE_X_MM, y*grid.GRID_UNIT_SIZE_Y_MM, 0)))

return result

def brick_floor(basePlane, settings, grid):
"""Create a floor covering all unit bases"""

brickSizeX = settings.sizeUnitsX * grid.GRID_UNIT_SIZE_X_MM - grid.BRICK_SIZE_TOLERANCE_MM
brickSizeY = settings.sizeUnitsY * grid.GRID_UNIT_SIZE_Y_MM - grid.BRICK_SIZE_TOLERANCE_MM

floor = basePlane.box(brickSizeX, brickSizeY, grid.FLOOR_THICKNESS, centered = False, combine = False)

floor = floor.edges("|Z").fillet(grid.CORNER_FILLET_RADIUS)

return floor

def bin_base(basePlane, settings, grid):

result = grid_base(basePlane, settings, grid)

# Continue from the top of the base
plane = result.faces(">Z").workplane()

# Add the floor of the bin
result.add(brick_floor(plane, settings, grid))

result = result.combine(clean=True)

return result
78 changes: 5 additions & 73 deletions generators/solidbin/solidbin_generator.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
from cadquery import exporters
from grid_constants import *

from generators.common.bin_base import bin_base

class Generator:
def __init__(self, settings, grid) -> None:
self.settings = settings
Expand All @@ -20,71 +22,10 @@ def precalculate(self):
self.internalSizeY = self.brickSizeY-2*self.grid.WALL_THICKNESS
self.compartmentSizeZ = (self.settings.sizeUnitsZ-1)*self.grid.HEIGHT_UNITSIZE_MM

def unit_base(self, basePlane):
"""Construct a 1x1 GridFinity unit base on the provided workplane"""

# The elements are constructed "centered" because that makes life easier.
baseBottom = basePlane.box(self.grid.BASE_BOTTOM_SIZE_X, self.grid.BASE_BOTTOM_SIZE_Y, self.grid.BASE_BOTTOM_THICKNESS, combine=False)
baseBottom = baseBottom.edges("|Z").fillet(self.grid.BASE_BOTTOM_FILLET_RADIUS)
baseBottom = baseBottom.faces("<Z").chamfer(self.grid.BASE_BOTTOM_CHAMFER_SIZE)

baseTop = baseBottom.faces(">Z").workplane()
baseTop = baseTop.box(self.grid.BRICK_UNIT_SIZE_X, self.grid.BRICK_UNIT_SIZE_Y, self.grid.BASE_TOP_THICKNESS, centered=(True, True, False), combine=False)
baseTop = baseTop.edges("|Z").fillet(self.grid.CORNER_FILLET_RADIUS)
baseTop = baseTop.faces("<Z").chamfer(self.grid.BASE_TOP_CHAMFER_SIZE)

result = baseTop | baseBottom

if self.settings.addMagnetHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y)])
result = result.hole(self.grid.DEFAULT_MAGNET_HOLE_DIAMETER, self.grid.DEFAULT_MAGNET_HOLE_DEPTH)
if self.settings.addRemovalHoles:
result = result.pushPoints([(self.grid.HOLE_OFFSET_X-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, self.grid.HOLE_OFFSET_Y-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-self.grid.HOLE_OFFSET_X+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, self.grid.HOLE_OFFSET_Y-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(self.grid.HOLE_OFFSET_X-self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, -self.grid.HOLE_OFFSET_Y+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET),
(-self.grid.HOLE_OFFSET_X+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET, -self.grid.HOLE_OFFSET_Y+self.grid.REMOVABLE_MAGNET_HOLE_OFFSET)])
result = result.hole(self.grid.REMOVABLE_MAGNET_HOLE_DIAMETER, self.grid.DEFAULT_MAGNET_HOLE_DEPTH)

if self.settings.addScrewHoles:
result = result.faces("<Z").workplane()
result = result.pushPoints([(self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, self.grid.HOLE_OFFSET_Y),
(self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y),
(-self.grid.HOLE_OFFSET_X, -self.grid.HOLE_OFFSET_Y)])
result = result.hole(self.grid.SCREW_HOLE_DIAMETER, self.grid.SCREW_HOLE_DEPTH)

# Translate the result because it is now centered around the origin, which is inconvenient for subsequent steps
result = result.translate((self.grid.BRICK_UNIT_SIZE_X/2, self.grid.BRICK_UNIT_SIZE_Y/2, self.grid.BASE_BOTTOM_THICKNESS/2))

return result

def grid_base(self, basePlane):
"""Construct a base of WidthxLength grid units"""

result = basePlane.workplane()

for x in range(self.settings.sizeUnitsX):
for y in range(self.settings.sizeUnitsY):
result.add(self.unit_base(basePlane).translate((x*self.grid.GRID_UNIT_SIZE_X_MM, y*self.grid.GRID_UNIT_SIZE_Y_MM, 0)))

return result

def brick_floor(self, basePlane):
"""Create a floor covering all unit bases"""

floor = basePlane.box(self.brickSizeX, self.brickSizeY, self.grid.FLOOR_THICKNESS, centered = False, combine = False)

floor = floor.edges("|Z").fillet(self.grid.CORNER_FILLET_RADIUS)

return floor

def outer_wall(self, basePlane):
"""Create the outer wall of the bin"""

# Allow creation of a 1-unit height bin (just the base)
if self.compartmentSizeZ == 0:
return

Expand Down Expand Up @@ -127,18 +68,9 @@ def validate_settings(self):

def generate_model(self):
plane = cq.Workplane("XY")
result = plane.workplane()

# Add the base of Gridfinity profiles
result.add(self.grid_base(plane))

# Continue from the top of the base
plane = result.faces(">Z").workplane()

# Add the floor of the bin
result.add(self.brick_floor(plane))

result = bin_base(plane, self.settings, self.grid)

# Continue from the top of the floor
plane = result.faces(">Z").workplane()

# Add the outer wall
Expand Down
2 changes: 1 addition & 1 deletion version.py
Original file line number Diff line number Diff line change
@@ -1 +1 @@
__version__ = "0.3.1"
__version__ = "0.3.2"

0 comments on commit c034ee9

Please sign in to comment.