mirror of
https://github.com/BelfrySCAD/BOSL2.git
synced 2025-01-01 09:49:45 +00:00
add starts to threaded rod/nut
remove vnf_add_face(s) add vnf_from_polygon
This commit is contained in:
parent
787fe45798
commit
afe75d0e3f
3 changed files with 31 additions and 102 deletions
|
@ -1958,8 +1958,8 @@ function rounded_prism(bottom, top, joint_bot=0, joint_top=0, joint_sides=0, k_b
|
||||||
vnf = vnf_merge([ each subindex(top_samples,0),
|
vnf = vnf_merge([ each subindex(top_samples,0),
|
||||||
each subindex(bot_samples,0),
|
each subindex(bot_samples,0),
|
||||||
for(pts=edge_points) vnf_vertex_array(pts),
|
for(pts=edge_points) vnf_vertex_array(pts),
|
||||||
debug ? vnf_add_faces(EMPTY_VNF,faces)
|
debug ? vnf_from_polygons(faces)
|
||||||
: vnf_triangulate(vnf_add_faces(EMPTY_VNF,faces))
|
: vnf_triangulate(vnf_from_polygons(faces))
|
||||||
])
|
])
|
||||||
)
|
)
|
||||||
debug ? [concat(top_patch, bot_patch), vnf] : vnf;
|
debug ? [concat(top_patch, bot_patch), vnf] : vnf;
|
||||||
|
|
|
@ -24,6 +24,7 @@
|
||||||
// bevel = if true, bevel the thread ends. Default: false
|
// bevel = if true, bevel the thread ends. Default: false
|
||||||
// bevel1 = if true bevel the bottom end.
|
// bevel1 = if true bevel the bottom end.
|
||||||
// bevel2 = if true bevel the top end.
|
// bevel2 = if true bevel the top end.
|
||||||
|
// starts = The number of lead starts. Default: 1
|
||||||
// internal = If true, make this a mask for making internal threads.
|
// internal = If true, make this a mask for making internal threads.
|
||||||
// d1 = Bottom outside diameter of threads.
|
// d1 = Bottom outside diameter of threads.
|
||||||
// d2 = Top outside diameter of threads.
|
// d2 = Top outside diameter of threads.
|
||||||
|
@ -43,7 +44,7 @@
|
||||||
module threaded_rod(
|
module threaded_rod(
|
||||||
d, l, pitch,
|
d, l, pitch,
|
||||||
left_handed=false,
|
left_handed=false,
|
||||||
bevel,bevel1,bevel2,
|
bevel,bevel1,bevel2,starts=1,
|
||||||
internal=false,
|
internal=false,
|
||||||
d1, d2,
|
d1, d2,
|
||||||
higbee, higbee1, higbee2,
|
higbee, higbee1, higbee2,
|
||||||
|
@ -82,7 +83,7 @@ module threaded_rod(
|
||||||
generic_threaded_rod(
|
generic_threaded_rod(
|
||||||
d=basic ? d : d[2], d1=d1, d2=d2, l=l,
|
d=basic ? d : d[2], d1=d1, d2=d2, l=l,
|
||||||
pitch=pitch,
|
pitch=pitch,
|
||||||
profile=profile,
|
profile=profile,starts=starts,
|
||||||
left_handed=left_handed,
|
left_handed=left_handed,
|
||||||
bevel=bevel,bevel1=bevel1,bevel2=bevel2,
|
bevel=bevel,bevel1=bevel1,bevel2=bevel2,
|
||||||
internal=internal,
|
internal=internal,
|
||||||
|
@ -106,6 +107,7 @@ module threaded_rod(
|
||||||
// h = height/thickness of nut.
|
// h = height/thickness of nut.
|
||||||
// pitch = Length between threads.
|
// pitch = Length between threads.
|
||||||
// ---
|
// ---
|
||||||
|
// starts = The number of lead starts. Default: 1
|
||||||
// left_handed = if true, create left-handed threads. Default = false
|
// left_handed = if true, create left-handed threads. Default = false
|
||||||
// bevel = if true, bevel the thread ends. Default: false
|
// bevel = if true, bevel the thread ends. Default: false
|
||||||
// bevel1 = if true bevel the bottom end.
|
// bevel1 = if true bevel the bottom end.
|
||||||
|
@ -119,7 +121,7 @@ module threaded_rod(
|
||||||
// threaded_nut(od=16, id=8, h=8, pitch=1.25, left_handed=true, bevel=true, $slop=0.1, $fa=1, $fs=1);
|
// threaded_nut(od=16, id=8, h=8, pitch=1.25, left_handed=true, bevel=true, $slop=0.1, $fa=1, $fs=1);
|
||||||
module threaded_nut(
|
module threaded_nut(
|
||||||
od, id, h,
|
od, id, h,
|
||||||
pitch, left_handed=false, bevel, bevel1, bevel2,
|
pitch, starts=1, left_handed=false, bevel, bevel1, bevel2,
|
||||||
anchor, spin, orient
|
anchor, spin, orient
|
||||||
) {
|
) {
|
||||||
depth = pitch * cos(30) * 5/8;
|
depth = pitch * cos(30) * 5/8;
|
||||||
|
@ -134,7 +136,7 @@ module threaded_nut(
|
||||||
generic_threaded_nut(
|
generic_threaded_nut(
|
||||||
od=od, id=id, h=h,
|
od=od, id=id, h=h,
|
||||||
pitch=pitch,
|
pitch=pitch,
|
||||||
profile=profile,
|
profile=profile,starts=starts,
|
||||||
left_handed=left_handed,
|
left_handed=left_handed,
|
||||||
bevel=bevel,bevel1=bevel1,bevel2=bevel2,
|
bevel=bevel,bevel1=bevel1,bevel2=bevel2,
|
||||||
anchor=anchor, spin=spin,
|
anchor=anchor, spin=spin,
|
||||||
|
|
117
vnf.scad
117
vnf.scad
|
@ -328,59 +328,26 @@ function vnf_merge(vnfs, cleanup=false, eps=EPSILON) =
|
||||||
[nverts, nfaces];
|
[nverts, nfaces];
|
||||||
|
|
||||||
|
|
||||||
|
// Function: vnf_from_polygons()
|
||||||
// Function: vnf_add_face()
|
|
||||||
// Usage:
|
// Usage:
|
||||||
// vnf_add_face(vnf, pts);
|
// vnf = vnf_from_polygons(polygons);
|
||||||
// Description:
|
// Description:
|
||||||
// Given a VNF structure and a list of face vertex points, adds the face to the VNF structure.
|
// Given a list of 3d polygons, produces a VNF containing those polygons.
|
||||||
// Returns the modified VNF structure `[VERTICES, FACES]`. It is up to the caller to make
|
|
||||||
// sure that the points are in the correct order to make the face normal point outwards.
|
|
||||||
// Arguments:
|
|
||||||
// vnf = The VNF structure to add a face to.
|
|
||||||
// pts = The vertex points for the face.
|
|
||||||
function vnf_add_face(vnf=EMPTY_VNF, pts) =
|
|
||||||
assert(is_vnf(vnf))
|
|
||||||
assert(is_path(pts))
|
|
||||||
let(
|
|
||||||
res = set_union(vnf[0], pts, get_indices=true),
|
|
||||||
face = deduplicate(res[0], closed=true)
|
|
||||||
) [
|
|
||||||
res[1],
|
|
||||||
concat(vnf[1], len(face)>2? [face] : [])
|
|
||||||
];
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// Function: vnf_add_faces()
|
|
||||||
// Usage:
|
|
||||||
// vnf_add_faces(vnf, faces);
|
|
||||||
// Description:
|
|
||||||
// Given a VNF structure and a list of faces, where each face is given as a list of vertex points,
|
|
||||||
// adds the faces to the VNF structure. Returns the modified VNF structure `[VERTICES, FACES]`.
|
|
||||||
// It is up to the caller to make sure that the points are in the correct order to make the face
|
// It is up to the caller to make sure that the points are in the correct order to make the face
|
||||||
// normals point outwards.
|
// normals point outwards. No checking for duplicate vertices is done. If you want to
|
||||||
|
// remove duplicate vertices use vnf_merge with the cleanup option.
|
||||||
// Arguments:
|
// Arguments:
|
||||||
// vnf = The VNF structure to add a face to.
|
// polygons = The list of 3d polygons to turn into a VNF
|
||||||
// faces = The list of faces, where each face is given as a list of vertex points.
|
function vnf_from_polygons(polygons) =
|
||||||
function vnf_add_faces(vnf=EMPTY_VNF, faces) =
|
assert(is_list(polygons))
|
||||||
assert(is_vnf(vnf))
|
let(
|
||||||
assert(is_list(faces))
|
offs = cumsum([0, for(p=polygons) len(p)]),
|
||||||
let(
|
faces = [for(i=idx(polygons))
|
||||||
res = set_union(vnf[0], flatten(faces), get_indices=true),
|
[for (j=idx(polygons[i])) offs[i]+j]
|
||||||
idxs = res[0],
|
]
|
||||||
nverts = res[1],
|
)
|
||||||
offs = cumsum([0, for (face=faces) len(face)]),
|
[flatten(polygons), faces];
|
||||||
ifaces = [
|
|
||||||
for (i=idx(faces)) [
|
|
||||||
for (j=idx(faces[i]))
|
|
||||||
idxs[offs[i]+j]
|
|
||||||
]
|
|
||||||
]
|
|
||||||
) [
|
|
||||||
nverts,
|
|
||||||
concat(vnf[1],ifaces)
|
|
||||||
];
|
|
||||||
|
|
||||||
|
|
||||||
// Section: VNF Testing and Access
|
// Section: VNF Testing and Access
|
||||||
|
@ -702,7 +669,7 @@ function vnf_slice(vnf,dir,cuts) =
|
||||||
faces = [for(face=vnf[1]) select(vert,face)],
|
faces = [for(face=vnf[1]) select(vert,face)],
|
||||||
poly_list = _slice_3dpolygons(faces, dir, cuts)
|
poly_list = _slice_3dpolygons(faces, dir, cuts)
|
||||||
)
|
)
|
||||||
vnf_add_faces(faces=poly_list);
|
vnf_merge([vnf_from_polygons(poly_list)], cleanup=true);
|
||||||
|
|
||||||
|
|
||||||
function _split_polygon_at_x(poly, x) =
|
function _split_polygon_at_x(poly, x) =
|
||||||
|
@ -886,48 +853,9 @@ function _triangulate_planar_convex_polygons(polys) =
|
||||||
// vnf = apply(fwd(5)*yrot(30),cube([100,2,5],center=true));
|
// vnf = apply(fwd(5)*yrot(30),cube([100,2,5],center=true));
|
||||||
// bent = vnf_bend(vnf, axis="Z");
|
// bent = vnf_bend(vnf, axis="Z");
|
||||||
// vnf_polyhedron(bent);
|
// vnf_polyhedron(bent);
|
||||||
function old_vnf_bend(vnf,r,d,axis="Z") =
|
|
||||||
let(
|
|
||||||
chk_axis = assert(in_list(axis,["X","Y","Z"])),
|
|
||||||
vnf = vnf_triangulate(vnf),
|
|
||||||
verts = vnf[0],
|
|
||||||
bounds = pointlist_bounds(verts),
|
|
||||||
bmin = bounds[0],
|
|
||||||
bmax = bounds[1],
|
|
||||||
dflt = axis=="Z"?
|
|
||||||
max(abs(bmax.y), abs(bmin.y)) :
|
|
||||||
max(abs(bmax.z), abs(bmin.z)),
|
|
||||||
r = get_radius(r=r,d=d,dflt=dflt),
|
|
||||||
extent = axis=="X" ? [bmin.y, bmax.y] : [bmin.x, bmax.x]
|
|
||||||
)
|
|
||||||
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."),
|
|
||||||
steps = ceil(segs(r) * (extent[1]-extent[0])/(2*PI*r)),
|
|
||||||
step = (extent[1]-extent[0]) / steps,
|
|
||||||
bend_at = [for(i = [1:1:steps-1]) i*step+extent[0]],
|
|
||||||
facepolys = [for (face=vnf[1]) select(verts,face)],
|
|
||||||
slicedir = axis=="X"? "Y" : "X", // slice in y dir for X axis case, and x dir otherwise
|
|
||||||
splits = _slice_3dpolygons(facepolys, slicedir, bend_at),
|
|
||||||
newtris = _triangulate_planar_convex_polygons(splits),
|
|
||||||
bent_faces = [
|
|
||||||
for (tri = newtris) [
|
|
||||||
for (p = tri) let(
|
|
||||||
a = axis=="X"? 180*p.y/(r*PI) * sign(bmax.z) :
|
|
||||||
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);
|
|
||||||
function vnf_bend(vnf,r,d,axis="Z") =
|
function vnf_bend(vnf,r,d,axis="Z") =
|
||||||
let(
|
let(
|
||||||
chk_axis = assert(in_list(axis,["X","Y","Z"])),
|
chk_axis = assert(in_list(axis,["X","Y","Z"])),
|
||||||
//vnf = vnf_triangulate(vnf),
|
|
||||||
verts = vnf[0],
|
verts = vnf[0],
|
||||||
bounds = pointlist_bounds(verts),
|
bounds = pointlist_bounds(verts),
|
||||||
bmin = bounds[0],
|
bmin = bounds[0],
|
||||||
|
@ -954,7 +882,6 @@ function vnf_bend(vnf,r,d,axis="Z") =
|
||||||
axis=="Y"? [p.z*sin(a), p.y, 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]]
|
[p.y*sin(a), p.y*cos(a), p.z]]
|
||||||
|
|
||||||
// ) vnf_triangulate([new_vert,sliced[1]]);
|
|
||||||
) [new_vert,sliced[1]];
|
) [new_vert,sliced[1]];
|
||||||
|
|
||||||
|
|
||||||
|
@ -1134,7 +1061,7 @@ module vnf_debug(vnf, faces=true, vertices=true, opacity=0.5, size=1, convexity=
|
||||||
// c = [-50, 50, 50];
|
// c = [-50, 50, 50];
|
||||||
// d = [ 50, 50, 60];
|
// d = [ 50, 50, 60];
|
||||||
// e = [ 50,-50, 50];
|
// e = [ 50,-50, 50];
|
||||||
// vnf = vnf_add_faces(faces=[
|
// vnf = vnf_from_polygons([
|
||||||
// [a, b, e], [a, c, b], [a, d, c], [a, e, d], [b, c, d, e]
|
// [a, b, e], [a, c, b], [a, d, c], [a, e, d], [b, c, d, e]
|
||||||
// ]);
|
// ]);
|
||||||
// vnf_validate(vnf);
|
// vnf_validate(vnf);
|
||||||
|
@ -1146,26 +1073,26 @@ module vnf_debug(vnf, faces=true, vertices=true, opacity=0.5, size=1, convexity=
|
||||||
// path3d(square(100,center=true),0),
|
// path3d(square(100,center=true),0),
|
||||||
// path3d(square(100,center=true),100),
|
// path3d(square(100,center=true),100),
|
||||||
// ], slices=0, caps=false);
|
// ], slices=0, caps=false);
|
||||||
// vnf = vnf_add_faces(vnf=vnf1, faces=[
|
// vnf = vnf_merge([vnf1, vnf_from_polygons([
|
||||||
// [[-50,-50, 0], [ 50, 50, 0], [-50, 50, 0]],
|
// [[-50,-50, 0], [ 50, 50, 0], [-50, 50, 0]],
|
||||||
// [[-50,-50, 0], [ 50,-50, 0], [ 50, 50, 0]],
|
// [[-50,-50, 0], [ 50,-50, 0], [ 50, 50, 0]],
|
||||||
// [[-50,-50,100], [-50, 50,100], [ 50, 50,100]],
|
// [[-50,-50,100], [-50, 50,100], [ 50, 50,100]],
|
||||||
// [[-50,-50,100], [ 50,-50,100], [ 50, 50,100]],
|
// [[-50,-50,100], [ 50,-50,100], [ 50, 50,100]],
|
||||||
// ]);
|
// ])]);
|
||||||
// vnf_validate(vnf);
|
// vnf_validate(vnf);
|
||||||
// Example: T_JUNCTION Errors; Vertex is Mid-Edge on Another Face.
|
// Example: T_JUNCTION Errors; Vertex is Mid-Edge on Another Face.
|
||||||
// vnf1 = skin([
|
// vnf1 = skin([
|
||||||
// path3d(square(100,center=true),0),
|
// path3d(square(100,center=true),0),
|
||||||
// path3d(square(100,center=true),100),
|
// path3d(square(100,center=true),100),
|
||||||
// ], slices=0, caps=false);
|
// ], slices=0, caps=false);
|
||||||
// vnf = vnf_add_faces(vnf=vnf1, faces=[
|
// vnf = vnf_merge([vnf1, vnf_from_polygons([
|
||||||
// [[-50,-50,0], [50,50,0], [-50,50,0]],
|
// [[-50,-50,0], [50,50,0], [-50,50,0]],
|
||||||
// [[-50,-50,0], [50,-50,0], [50,50,0]],
|
// [[-50,-50,0], [50,-50,0], [50,50,0]],
|
||||||
// [[-50,-50,100], [-50,50,100], [0,50,100]],
|
// [[-50,-50,100], [-50,50,100], [0,50,100]],
|
||||||
// [[-50,-50,100], [0,50,100], [0,-50,100]],
|
// [[-50,-50,100], [0,50,100], [0,-50,100]],
|
||||||
// [[0,-50,100], [0,50,100], [50,50,100]],
|
// [[0,-50,100], [0,50,100], [50,50,100]],
|
||||||
// [[0,-50,100], [50,50,100], [50,-50,100]],
|
// [[0,-50,100], [50,50,100], [50,-50,100]],
|
||||||
// ]);
|
// ])]);
|
||||||
// vnf_validate(vnf);
|
// vnf_validate(vnf);
|
||||||
// Example: FACE_ISECT Errors; Faces Intersect
|
// Example: FACE_ISECT Errors; Faces Intersect
|
||||||
// vnf = vnf_merge([
|
// vnf = vnf_merge([
|
||||||
|
|
Loading…
Reference in a new issue