Merge remote-tracking branch 'upstream/master'

This commit is contained in:
Adrian Mariano
2022-03-31 18:38:33 -04:00
2 changed files with 113 additions and 122 deletions

View File

@@ -159,9 +159,10 @@ function line_of(spacing, n, l, p1, p2) =
// Usage: // Usage:
// xcopies(spacing, [n], [sp]) children; // xcopies(spacing, [n], [sp]) children;
// xcopies(l, [n], [sp]) children; // xcopies(l, [n], [sp]) children;
// xcopies(LIST) children;
// //
// Arguments: // Arguments:
// spacing = spacing between copies. (Default: 1.0) // spacing = Given a scalar, specifies a uniform spacing between copies. Given a list of scalars, each one gives a specific position along the line. (Default: 1.0)
// n = Number of copies to spread out. (Default: 2) // n = Number of copies to spread out. (Default: 2)
// l = Length to spread copies over. // l = Length to spread copies over.
// sp = If given as a point, copies will be spread on a line to the right of starting position `sp`. If given as a scalar, copies will be spread on a line to the right of starting position `[sp,0,0]`. If not given, copies will be spread along a line that is centered at [0,0,0]. // sp = If given as a point, copies will be spread on a line to the right of starting position `sp`. If given as a scalar, copies will be spread on a line to the right of starting position `[sp,0,0]`. If not given, copies will be spread along a line that is centered at [0,0,0].
@@ -180,15 +181,26 @@ function line_of(spacing, n, l, p1, p2) =
// cube(size=[1,3,1],center=true); // cube(size=[1,3,1],center=true);
// cube(size=[3,1,1],center=true); // cube(size=[3,1,1],center=true);
// } // }
// Example:
// xcopies([1,2,3,5,7]) sphere(d=1);
module xcopies(spacing, n, l, sp) module xcopies(spacing, n, l, sp)
{ {
req_children($children); req_children($children);
sp = is_finite(sp)? [sp,0,0] : sp; dir = RIGHT;
line_of( sp = is_finite(sp)? (sp*dir) : sp;
l=u_mul(l,RIGHT), if (is_vector(spacing)) {
spacing=u_mul(spacing,RIGHT), translate(default(sp,[0,0,0])) {
n=n, p1=sp for (x = spacing) {
) children(); translate(x*dir) children();
}
}
} else {
line_of(
l=u_mul(l,dir),
spacing=u_mul(spacing,dir),
n=n, p1=sp
) children();
}
} }
@@ -200,9 +212,10 @@ module xcopies(spacing, n, l, sp)
// Usage: // Usage:
// ycopies(spacing, [n], [sp]) children; // ycopies(spacing, [n], [sp]) children;
// ycopies(l, [n], [sp]) children; // ycopies(l, [n], [sp]) children;
// ycopies(LIST) children;
// //
// Arguments: // Arguments:
// spacing = spacing between copies. (Default: 1.0) // spacing = Given a scalar, specifies a uniform spacing between copies. Given a list of scalars, each one gives a specific position along the line. (Default: 1.0)
// n = Number of copies to spread out. (Default: 2) // n = Number of copies to spread out. (Default: 2)
// l = Length to spread copies over. // l = Length to spread copies over.
// sp = If given as a point, copies will be spread on a line back from starting position `sp`. If given as a scalar, copies will be spread on a line back from starting position `[0,sp,0]`. If not given, copies will be spread along a line that is centered at [0,0,0]. // sp = If given as a point, copies will be spread on a line back from starting position `sp`. If given as a scalar, copies will be spread on a line back from starting position `[0,sp,0]`. If not given, copies will be spread along a line that is centered at [0,0,0].
@@ -221,15 +234,26 @@ module xcopies(spacing, n, l, sp)
// cube(size=[1,3,1],center=true); // cube(size=[1,3,1],center=true);
// cube(size=[3,1,1],center=true); // cube(size=[3,1,1],center=true);
// } // }
// Example:
// ycopies([1,2,3,5,7]) sphere(d=1);
module ycopies(spacing, n, l, sp) module ycopies(spacing, n, l, sp)
{ {
req_children($children); req_children($children);
sp = is_finite(sp)? [0,sp,0] : sp; dir = BACK;
line_of( sp = is_finite(sp)? (sp*dir) : sp;
l=u_mul(l,BACK), if (is_vector(spacing)) {
spacing=u_mul(spacing,BACK), translate(default(sp,[0,0,0])) {
n=n, p1=sp for (x = spacing) {
) children(); translate(x*dir) children();
}
}
} else {
line_of(
l=u_mul(l,dir),
spacing=u_mul(spacing,dir),
n=n, p1=sp
) children();
}
} }
@@ -241,9 +265,10 @@ module ycopies(spacing, n, l, sp)
// Usage: // Usage:
// zcopies(spacing, [n], [sp]) children; // zcopies(spacing, [n], [sp]) children;
// zcopies(l, [n], [sp]) children; // zcopies(l, [n], [sp]) children;
// zcopies(LIST) children;
// //
// Arguments: // Arguments:
// spacing = spacing between copies. (Default: 1.0) // spacing = Given a scalar, specifies a uniform spacing between copies. Given a list of scalars, each one gives a specific position along the line. (Default: 1.0)
// n = Number of copies to spread out. (Default: 2) // n = Number of copies to spread out. (Default: 2)
// l = Length to spread copies over. // l = Length to spread copies over.
// sp = If given as a point, copies will be spread on a line up from starting position `sp`. If given as a scalar, copies will be spread on a line up from starting position `[0,0,sp]`. If not given, copies will be spread along a line that is centered at [0,0,0]. // sp = If given as a point, copies will be spread on a line up from starting position `sp`. If given as a scalar, copies will be spread on a line up from starting position `[0,0,sp]`. If not given, copies will be spread along a line that is centered at [0,0,0].
@@ -276,15 +301,26 @@ module ycopies(spacing, n, l, sp)
// back(($idx%2)*xyr*cos(60)) // back(($idx%2)*xyr*cos(60))
// grid2d(s,n=[12,7],stagger=($idx%2)? "alt" : true) // grid2d(s,n=[12,7],stagger=($idx%2)? "alt" : true)
// sphere(d=s); // sphere(d=s);
// Example:
// zcopies([1,2,3,5,7]) sphere(d=1);
module zcopies(spacing, n, l, sp) module zcopies(spacing, n, l, sp)
{ {
req_children($children); req_children($children);
sp = is_finite(sp)? [0,0,sp] : sp; dir = UP;
line_of( sp = is_finite(sp)? (sp*dir) : sp;
l=u_mul(l,UP), if (is_vector(spacing)) {
spacing=u_mul(spacing,UP), translate(default(sp,[0,0,0])) {
n=n, p1=sp for (x = spacing) {
) children(); translate(x*dir) children();
}
}
} else {
line_of(
l=u_mul(l,dir),
spacing=u_mul(spacing,dir),
n=n, p1=sp
) children();
}
} }
@@ -422,64 +458,6 @@ module grid2d(spacing, n, size, stagger=false, inside=undef, nonzero)
} }
// Module: grid3d()
//
// Description:
// Makes a 3D grid of duplicate children.
//
// Usage:
// grid3d(spacing,n) children;
// grid3d(spacing=[dX,dY,dZ], n=[Xn,Yn,Zn]) children;
// grid3d([xa=], [ya=], [za=]) children;
//
// Arguments:
// spacing = spacing of copies per axis. Use with `n`.
// n = Optional number of copies to have per axis.
// xa = array or range of X-axis values to offset by. (Default: [0])
// ya = array or range of Y-axis values to offset by. (Default: [0])
// za = array or range of Z-axis values to offset by. (Default: [0])
//
// Side Effects:
// `$pos` is set to the relative centerpoint of each child copy, and can be used to modify each child individually.
// `$idx` is set to the [Xidx,Yidx,Zidx] index values of each child copy, when using `count` and `n`.
//
// Examples(FlatSpin,VPD=222):
// grid3d(xa=[0:25:50],ya=[0,40],za=[-20:40:20]) sphere(r=5);
// Examples(FlatSpin,VPD=800):
// grid3d(n=[3, 4, 2], spacing=[60, 50, 40]) sphere(r=10);
// Examples:
// grid3d(ya=[-60:40:60],za=[0,70]) sphere(r=10);
// grid3d(n=3, spacing=30) sphere(r=10);
// grid3d(n=[3, 1, 2], spacing=30) sphere(r=10);
// grid3d(n=[3, 4], spacing=[80, 60]) sphere(r=10);
// Examples:
// grid3d(n=[10, 10, 10], spacing=50) color($idx/9) cube(50, center=true);
module grid3d(spacing, n, xa=[0], ya=[0], za=[0])
{
req_children($children);
n = scalar_vec3(n, 1);
spacing = scalar_vec3(spacing, undef);
if (!is_undef(n) && !is_undef(spacing)) {
for (xi = [0:1:n.x-1]) {
for (yi = [0:1:n.y-1]) {
for (zi = [0:1:n.z-1]) {
$idx = [xi,yi,zi];
$pos = v_mul(spacing, $idx - (n-[1,1,1])/2);
translate($pos) children();
}
}
}
} else {
for (xoff = xa, yoff = ya, zoff = za) {
$pos = [xoff, yoff, zoff];
translate($pos) children();
}
}
}
////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////
// Section: Rotating copies of all children // Section: Rotating copies of all children
////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////

View File

@@ -215,43 +215,48 @@ module cuboid(
cnt = sum(e); cnt = sum(e);
r = first_defined([chamfer, rounding]); r = first_defined([chamfer, rounding]);
dummy=assert(is_finite(r) && !approx(r,0)); dummy=assert(is_finite(r) && !approx(r,0));
c = [min(r,size.x/2), min(r,size.y/2), min(r,size.z/2)]; c = [r,r,r];
m = 0.01;
c2 = v_mul(corner,c/2); c2 = v_mul(corner,c/2);
c3 = v_mul(corner,c-[1,1,1]*m/2);
$fn = is_finite(chamfer)? 4 : quantup(segs(r),4); $fn = is_finite(chamfer)? 4 : quantup(segs(r),4);
translate(v_mul(corner, size/2-c)) { translate(v_mul(corner, size/2-c)) {
if (cnt == 0 || approx(r,0)) { intersection() {
translate(c2) cube(c, center=true); if (cnt == 0 || approx(r,0)) {
} else if (cnt == 1) { translate(c3) cube(m, center=true);
if (e.x) right(c2.x) xtcyl(l=c.x, r=r); } else if (cnt == 1) {
if (e.y) back (c2.y) ytcyl(l=c.y, r=r); if (e.x) right(c3.x) xtcyl(l=m, r=r);
if (e.z) up (c2.z) zcyl(l=c.z, r=r); if (e.y) back (c3.y) ytcyl(l=m, r=r);
} else if (cnt == 2) { if (e.z) up (c3.z) zcyl(l=m, r=r);
if (!e.x) { } else if (cnt == 2) {
intersection() { if (!e.x) {
ytcyl(l=c.y*2, r=r); intersection() {
zcyl(l=c.z*2, r=r); ytcyl(l=c.y*2, r=r);
} zcyl(l=c.z*2, r=r);
} else if (!e.y) { }
intersection() { } else if (!e.y) {
xtcyl(l=c.x*2, r=r); intersection() {
zcyl(l=c.z*2, r=r); xtcyl(l=c.x*2, r=r);
zcyl(l=c.z*2, r=r);
}
} else {
intersection() {
xtcyl(l=c.x*2, r=r);
ytcyl(l=c.y*2, r=r);
}
} }
} else { } else {
intersection() { if (trimcorners) {
xtcyl(l=c.x*2, r=r); tsphere(r=r);
ytcyl(l=c.y*2, r=r); } else {
} intersection() {
} xtcyl(l=c.x*2, r=r);
} else { ytcyl(l=c.y*2, r=r);
if (trimcorners) { zcyl(l=c.z*2, r=r);
tsphere(r=r); }
} else {
intersection() {
xtcyl(l=c.x*2, r=r);
ytcyl(l=c.y*2, r=r);
zcyl(l=c.z*2, r=r);
} }
} }
translate(c2) cube(c, center=true); // Trim to just the octant.
} }
} }
} }
@@ -281,15 +286,22 @@ module cuboid(
} }
} }
} else { } else {
if (is_finite(chamfer)) { rr = max(default(chamfer,0), default(rounding,0));
if (any(edges[0])) assert(chamfer <= size.y/2 && chamfer <=size.z/2, "chamfer must be smaller than half the cube length or height."); if (rr>0) {
if (any(edges[1])) assert(chamfer <= size.x/2 && chamfer <=size.z/2, "chamfer must be smaller than half the cube width or height."); rv = [for (i=[0:2])
if (any(edges[2])) assert(chamfer <= size.x/2 && chamfer <=size.y/2, "chamfer must be smaller than half the cube width or length."); [for (j=[0:3])
} (edges[i][j]>0?rr:0) * v_abs(EDGE_OFFSETS[i][j])
if (is_finite(rounding)) { ]
if (any(edges[0])) assert(rounding <= size.y/2 && rounding<=size.z/2, "rounding radius must be smaller than half the cube length or height."); ];
if (any(edges[1])) assert(rounding <= size.x/2 && rounding<=size.z/2, "rounding radius must be smaller than half the cube width or height."); grays = pair([0,1,3,2],wrap=true); // gray code ordering.
if (any(edges[2])) assert(rounding <= size.x/2 && rounding<=size.y/2, "rounding radius must be smaller than half the cube width or length."); minx = max([for (i=[1,2], j=grays) rv[i][j[0]].x + rv[i][j[1]].x]);
miny = max([for (i=[0,2], j=grays) rv[i][j[0]].y + rv[i][j[1]].y]);
minz = max([for (i=[0,1], j=grays) rv[i][j[0]].z + rv[i][j[1]].z]);
check =
assert(minx <= size.x, "Rounding or chamfering too large for cuboid size in the X axis.")
assert(miny <= size.y, "Rounding or chamfering too large for cuboid size in the Y axis.")
assert(minz <= size.z, "Rounding or chamfering too large for cuboid size in the Z axis.")
;
} }
majrots = [[0,90,0], [90,0,0], [0,0,0]]; majrots = [[0,90,0], [90,0,0], [0,0,0]];
attachable(anchor,spin,orient, size=size) { attachable(anchor,spin,orient, size=size) {
@@ -1500,7 +1512,7 @@ module zcyl(
// --- // ---
// od = Outer diameter of tube. // od = Outer diameter of tube.
// id = Inner diameter of tube. // id = Inner diameter of tube.
// wall = horizontal thickness of tube wall. Default 0.5 // wall = horizontal thickness of tube wall. Default 1
// or1 = Outer radius of bottom of tube. Default: value of r) // or1 = Outer radius of bottom of tube. Default: value of r)
// or2 = Outer radius of top of tube. Default: value of r) // or2 = Outer radius of top of tube. Default: value of r)
// od1 = Outer diameter of bottom of tube. // od1 = Outer diameter of bottom of tube.
@@ -1540,14 +1552,16 @@ module tube(
orr2 = get_radius(r1=or2, r=or, d1=od2, d=od, dflt=undef); orr2 = get_radius(r1=or2, r=or, d1=od2, d=od, dflt=undef);
irr1 = get_radius(r1=ir1, r=ir, d1=id1, d=id, dflt=undef); irr1 = get_radius(r1=ir1, r=ir, d1=id1, d=id, dflt=undef);
irr2 = get_radius(r1=ir2, r=ir, d1=id2, d=id, dflt=undef); irr2 = get_radius(r1=ir2, r=ir, d1=id2, d=id, dflt=undef);
wall = default(wall, 1);
r1 = default(orr1, u_add(irr1,wall)); r1 = default(orr1, u_add(irr1,wall));
r2 = default(orr2, u_add(irr2,wall)); r2 = default(orr2, u_add(irr2,wall));
ir1 = default(irr1, u_sub(orr1,wall)); ir1 = default(irr1, u_sub(orr1,wall));
ir2 = default(irr2, u_sub(orr2,wall)); ir2 = default(irr2, u_sub(orr2,wall));
assert(all_defined([r1, r2, ir1, ir2]), "Must specify two of inner radius/diam, outer radius/diam, and wall width.");
assert(ir1 <= r1, "Inner radius is larger than outer radius."); assert(ir1 <= r1, "Inner radius is larger than outer radius.");
assert(ir2 <= r2, "Inner radius is larger than outer radius."); assert(ir2 <= r2, "Inner radius is larger than outer radius.");
sides = segs(max(r1,r2)); sides = segs(max(r1,r2));
anchor = get_anchor(anchor, center, BOT, BOT); anchor = get_anchor(anchor, center, BOT, CENTER);
attachable(anchor,spin,orient, r1=r1, r2=r2, l=h) { attachable(anchor,spin,orient, r1=r1, r2=r2, l=h) {
zrot(realign? 180/sides : 0) { zrot(realign? 180/sides : 0) {
difference() { difference() {
@@ -2247,7 +2261,7 @@ function torus(
// Example: Standard Conical Connectors // Example: Standard Conical Connectors
// teardrop(d1=20, d2=30, h=20, cap_h1=11, cap_h2=16) // teardrop(d1=20, d2=30, h=20, cap_h1=11, cap_h2=16)
// show_anchors(custom=false); // show_anchors(custom=false);
// Example(Spin,VPD=275): Named Conical Connectors // Example(Spin,VPD=150,Med): Named Conical Connectors
// teardrop(d1=20, d2=30, h=20, cap_h1=11, cap_h2=16) // teardrop(d1=20, d2=30, h=20, cap_h1=11, cap_h2=16)
// show_anchors(std=false); // show_anchors(std=false);
module teardrop(h, r, ang=45, cap_h, r1, r2, d, d1, d2, cap_h1, cap_h2, l, anchor=CENTER, spin=0, orient=UP) module teardrop(h, r, ang=45, cap_h, r1, r2, d, d1, d2, cap_h1, cap_h2, l, anchor=CENTER, spin=0, orient=UP)
@@ -2310,7 +2324,6 @@ function teardrop(h, r, ang=45, cap_h, r1, r2, d, d1, d2, cap_h1, cap_h2, l, anc
profile2 = teardrop2d(r=r2, ang=ang, cap_h=cap_h2, $fn=sides), profile2 = teardrop2d(r=r2, ang=ang, cap_h=cap_h2, $fn=sides),
tip_y1 = max(column(profile1,1)), tip_y1 = max(column(profile1,1)),
tip_y2 = max(column(profile2,1)), tip_y2 = max(column(profile2,1)),
feef=echo(tip_y1=tip_y1, tip_y2=tip_y2),
_cap_h1 = min(default(cap_h1, tip_y1), tip_y1), _cap_h1 = min(default(cap_h1, tip_y1), tip_y1),
_cap_h2 = min(default(cap_h2, tip_y2), tip_y2), _cap_h2 = min(default(cap_h2, tip_y2), tip_y2),
capvec = unit([0, _cap_h1-_cap_h2, l]), capvec = unit([0, _cap_h1-_cap_h2, l]),