mirror of
https://github.com/BelfrySCAD/BOSL2.git
synced 2025-01-01 09:49:45 +00:00
vnf_bend_around_y_axis() to vnf_bend(), with support for X, Y, and Z axes.
This commit is contained in:
parent
b1ae85e65c
commit
476967db6d
2 changed files with 64 additions and 17 deletions
|
@ -8,7 +8,7 @@
|
||||||
//////////////////////////////////////////////////////////////////////
|
//////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
|
||||||
BOSL_VERSION = [2,0,305];
|
BOSL_VERSION = [2,0,306];
|
||||||
|
|
||||||
|
|
||||||
// Section: BOSL Library Version Functions
|
// Section: BOSL Library Version Functions
|
||||||
|
|
79
vnf.scad
79
vnf.scad
|
@ -409,9 +409,9 @@ function _triangulate_planar_convex_polygons(polys) =
|
||||||
) outtris;
|
) outtris;
|
||||||
|
|
||||||
|
|
||||||
// Function: vnf_bend_around_y_axis()
|
// Function: vnf_bend()
|
||||||
// Usage:
|
// Usage:
|
||||||
// bentvnf = vnf_bend_around_y_axis(vnf);
|
// bentvnf = vnf_bend(vnf);
|
||||||
// Description:
|
// Description:
|
||||||
// Given a VNF that is entirely above, or entirely below the Z=0 plane, bends the VNF around the
|
// Given a VNF that is entirely above, or entirely below the Z=0 plane, bends the VNF around the
|
||||||
// Y axis, splitting up faces as necessary. Returns the bent VNF. Will error out if the VNF
|
// Y axis, splitting up faces as necessary. Returns the bent VNF. Will error out if the VNF
|
||||||
|
@ -425,55 +425,102 @@ function _triangulate_planar_convex_polygons(polys) =
|
||||||
// vnf = The original VNF to bend.
|
// vnf = The original VNF to bend.
|
||||||
// r = If given, the radius where the size of the original shape is the same as in the original.
|
// r = If given, the radius where the size of the original shape is the same as in the original.
|
||||||
// d = If given, the diameter where the size of the original shape is the same as in the original.
|
// d = If given, the diameter where the size of the original shape is the same as in the original.
|
||||||
|
// axis = The axis to wrap around. "X", "Y", or "Z". Default: "Z"
|
||||||
// Example(3D):
|
// Example(3D):
|
||||||
// vnf0 = cube([100,40,10], center=true);
|
// vnf0 = cube([100,40,10], center=true);
|
||||||
// vnf1 = up(35, p=vnf0);
|
// vnf1 = up(35, p=vnf0);
|
||||||
// vnf2 = down(50, p=vnf0);
|
// vnf2 = down(50, p=vnf0);
|
||||||
// bent1 = vnf_bend_around_y_axis(vnf1);
|
// bent1 = vnf_bend(vnf1);
|
||||||
// bent2 = vnf_bend_around_y_axis(vnf2);
|
// bent2 = vnf_bend(vnf2);
|
||||||
// vnf_polyhedron([bent1,bent2]);
|
// vnf_polyhedron([bent1,bent2]);
|
||||||
// Example(3D):
|
// Example(3D):
|
||||||
// vnf0 = linear_sweep(star(n=5,step=2,d=100), height=10);
|
// vnf0 = linear_sweep(star(n=5,step=2,d=100), height=10);
|
||||||
// vnf1 = up(35, p=vnf0);
|
// vnf1 = up(35, p=vnf0);
|
||||||
// vnf2 = down(50, p=vnf0);
|
// vnf2 = down(50, p=vnf0);
|
||||||
// bent1 = vnf_bend_around_y_axis(vnf1);
|
// bent1 = vnf_bend(vnf1);
|
||||||
// bent2 = vnf_bend_around_y_axis(vnf2);
|
// bent2 = vnf_bend(vnf2);
|
||||||
// vnf_polyhedron([bent1,bent2]);
|
// vnf_polyhedron([bent1,bent2]);
|
||||||
// Example(3D):
|
// Example(3D):
|
||||||
// rgn = union(rect([100,20],center=true), rect([20,100],center=true));
|
// rgn = union(rect([100,20],center=true), rect([20,100],center=true));
|
||||||
// vnf0 = linear_sweep(zrot(45,p=rgn), height=10);
|
// vnf0 = linear_sweep(zrot(45,p=rgn), height=10);
|
||||||
// vnf1 = up(35, p=vnf0);
|
// vnf1 = up(35, p=vnf0);
|
||||||
// vnf2 = down(50, p=vnf0);
|
// vnf2 = down(50, p=vnf0);
|
||||||
// bent1 = vnf_bend_around_y_axis(vnf1);
|
// bent1 = vnf_bend(vnf1);
|
||||||
// bent2 = vnf_bend_around_y_axis(vnf2);
|
// bent2 = vnf_bend(vnf2);
|
||||||
// vnf_polyhedron([bent1,bent2]);
|
// vnf_polyhedron([bent1,bent2]);
|
||||||
function vnf_bend_around_y_axis(vnf,r,d) =
|
// Example(3D): Bending Around X Axis.
|
||||||
|
// rgnr = union(
|
||||||
|
// rect([20,100],center=true),
|
||||||
|
// back(50, p=trapezoid(w1=40, w2=0, h=20, anchor=FRONT))
|
||||||
|
// );
|
||||||
|
// vnf0 = xrot(00,p=linear_sweep(rgnr, height=10));
|
||||||
|
// vnf1 = up(50, p=vnf0);
|
||||||
|
// #vnf_polyhedron(vnf1);
|
||||||
|
// bent1 = vnf_bend(vnf1, axis="X");
|
||||||
|
// vnf_polyhedron([bent1]);
|
||||||
|
// Example(3D): Bending Around Y Axis.
|
||||||
|
// rgn = union(
|
||||||
|
// rect([20,100],center=true),
|
||||||
|
// back(50, p=trapezoid(w1=40, w2=0, h=20, anchor=FRONT))
|
||||||
|
// );
|
||||||
|
// rgnr = zrot(-90, p=rgn);
|
||||||
|
// vnf0 = xrot(00,p=linear_sweep(rgnr, height=10));
|
||||||
|
// vnf1 = up(50, p=vnf0);
|
||||||
|
// #vnf_polyhedron(vnf1);
|
||||||
|
// bent1 = vnf_bend(vnf1, axis="Y");
|
||||||
|
// vnf_polyhedron([bent1]);
|
||||||
|
// Example(3D): Bending Around Z Axis.
|
||||||
|
// rgn = union(
|
||||||
|
// rect([20,100],center=true),
|
||||||
|
// back(50, p=trapezoid(w1=40, w2=0, h=20, anchor=FRONT))
|
||||||
|
// );
|
||||||
|
// rgnr = zrot(90, p=rgn);
|
||||||
|
// vnf0 = xrot(90,p=linear_sweep(rgnr, height=10));
|
||||||
|
// vnf1 = fwd(50, p=vnf0);
|
||||||
|
// #vnf_polyhedron(vnf1);
|
||||||
|
// bent1 = vnf_bend(vnf1, axis="Z");
|
||||||
|
// vnf_polyhedron([bent1]);
|
||||||
|
function vnf_bend(vnf,r,d,axis="Z") =
|
||||||
let(
|
let(
|
||||||
|
chk_axis = assert(in_list(axis,["X","Y","Z"])),
|
||||||
vnf = vnf_triangulate(vnf),
|
vnf = vnf_triangulate(vnf),
|
||||||
verts = vnf[0],
|
verts = vnf[0],
|
||||||
bounds = pointlist_bounds(verts),
|
bounds = pointlist_bounds(verts),
|
||||||
bmin = bounds[0],
|
bmin = bounds[0],
|
||||||
bmax = bounds[1],
|
bmax = bounds[1],
|
||||||
r = get_radius(r=r,d=d,dflt=max(abs(bmax.z), abs(bmin.z))),
|
dflt = axis=="Z"?
|
||||||
width = bmax.x - bmin.x
|
max(abs(bmax.y), abs(bmin.y)) :
|
||||||
|
max(abs(bmax.z), abs(bmin.z)),
|
||||||
|
r = get_radius(r=r,d=d,dflt=dflt),
|
||||||
|
width = axis=="X"? (bmax.y-bmin.y) : (bmax.x - bmin.x)
|
||||||
)
|
)
|
||||||
assert(bmin.z > 0 || bmax.z < 0, "Entire shape MUST be completely above or below z=0.")
|
|
||||||
assert(width <= 2*PI*r, "Shape would wrap more than completely around the cylinder.")
|
assert(width <= 2*PI*r, "Shape would wrap more than completely around the cylinder.")
|
||||||
let(
|
let(
|
||||||
|
span_chk = axis=="Z"?
|
||||||
|
assert(bmin.y > 0 || bmax.y < 0, "Entire shape MUST be completely in front of or behind y=0.") :
|
||||||
|
assert(bmin.z > 0 || bmax.z < 0, "Entire shape MUST be completely above or below z=0."),
|
||||||
min_ang = 180 * bmin.x / (PI * r),
|
min_ang = 180 * bmin.x / (PI * r),
|
||||||
max_ang = 180 * bmax.x / (PI * r),
|
max_ang = 180 * bmax.x / (PI * r),
|
||||||
ang_span = max_ang-min_ang,
|
ang_span = max_ang-min_ang,
|
||||||
steps = ceil(segs(r) * ang_span/360),
|
steps = ceil(segs(r) * ang_span/360),
|
||||||
step = width / steps,
|
step = width / steps,
|
||||||
bend_at = [for(i = [1:1:steps-1]) i*step+bmin.x],
|
bend_at = axis=="X"? [for(i = [1:1:steps-1]) i*step+bmin.y] :
|
||||||
|
[for(i = [1:1:steps-1]) i*step+bmin.x],
|
||||||
facepolys = [for (face=vnf[1]) select(verts,face)],
|
facepolys = [for (face=vnf[1]) select(verts,face)],
|
||||||
splits = split_polygons_at_each_x(facepolys, bend_at),
|
splits = axis=="X"?
|
||||||
|
split_polygons_at_each_y(facepolys, bend_at) :
|
||||||
|
split_polygons_at_each_x(facepolys, bend_at),
|
||||||
newtris = _triangulate_planar_convex_polygons(splits),
|
newtris = _triangulate_planar_convex_polygons(splits),
|
||||||
bent_faces = [
|
bent_faces = [
|
||||||
for (tri = newtris) [
|
for (tri = newtris) [
|
||||||
for (p = tri) let(
|
for (p = tri) let(
|
||||||
a = 180*p.x/(r*PI) * sign(bmax.z)
|
a = axis=="X"? 180*p.y/(r*PI) * sign(bmax.z) :
|
||||||
) [p.z*sin(a), p.y, p.z*cos(a)]
|
axis=="Y"? 180*p.x/(r*PI) * sign(bmax.z) :
|
||||||
|
180*p.x/(r*PI) * sign(bmax.y)
|
||||||
|
)
|
||||||
|
axis=="X"? [p.x, p.z*sin(a), p.z*cos(a)] :
|
||||||
|
axis=="Y"? [p.z*sin(a), p.y, p.z*cos(a)] :
|
||||||
|
[p.y*sin(a), p.y*cos(a), p.z]
|
||||||
]
|
]
|
||||||
]
|
]
|
||||||
) vnf_add_faces(faces=bent_faces);
|
) vnf_add_faces(faces=bent_faces);
|
||||||
|
|
Loading…
Reference in a new issue