scad/voussoir/dovetails.scad

77 lines
1.9 KiB
OpenSCAD

ZFIGHT = 0.001;
module dovetails(dovetail_width, dovetail_height, count, clearance)
{
centering = ((count-1) * dovetail_width / 2);
for (index=[0:count-1])
{
x_off = (index * dovetail_width) - centering;
translate([x_off, 0])
intersection()
{
trapezoid(
upper_width=(dovetail_width * 2 / 3 - clearance),
lower_width=(dovetail_width * 1 / 3 - clearance),
height=dovetail_height
);
// Masks off the clearance from the top side.
translate([0, -clearance/2])
square([dovetail_width, dovetail_height - clearance], center=true);
}
}
}
module dovetail_block(block_width, block_height, dovetail_width, dovetail_height, clearance=0)
{
module mask()
{
square([block_width, block_height], center=true);
}
module main_block()
{
w = block_width;
h = block_height - (2 * dovetail_height);
square([w, h], center=true);
}
module upper_dovetails()
{
count = ceil(block_width / dovetail_width);
y = (block_height - dovetail_height) / 2;
translate([0, y - ZFIGHT])
dovetails(dovetail_width, dovetail_height, count, clearance);
}
module lower_dovetails()
{
count = ceil(block_width / dovetail_width) + 1;
y = (block_height - dovetail_height) / 2;
translate([0, -(y - ZFIGHT)])
mirror([0, 1])
dovetails(dovetail_width, dovetail_height, count, clearance);
}
intersection()
{
union()
{
main_block();
upper_dovetails();
lower_dovetails();
}
mask();
}
}
module trapezoid(upper_width, lower_width, height)
{
x1 = upper_width / 2;
x2 = lower_width / 2;
y1 = height / 2;
polygon([
[-x1, y1],
[x1, y1],
[x2, -y1],
[-x2, -y1]
]);
}