From d76d693a3337a10eb26196c50370e0e340604b64 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Wed, 17 Jan 2024 19:34:07 -0500 Subject: [PATCH 01/17] support threaded teardrop holes (passthrough to new teardrop support in threaded rod) --- screws.scad | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/screws.scad b/screws.scad index 8c92b0e..7dfa703 100644 --- a/screws.scad +++ b/screws.scad @@ -588,8 +588,7 @@ module screw(spec, head, drive, thread, drive_size, assert(is_finite(length) && length>0, "Must specify positive screw length") assert(is_finite(_shoulder_len) && _shoulder_len>=0, "Must specify a nonegative shoulder length") assert(is_finite(_shoulder_diam) && _shoulder_diam>=0, "Must specify nonnegative shoulder diameter") - assert(is_undef(user_thread_len) || (is_finite(user_thread_len) && user_thread_len>=0), "Must specify nonnegative thread length") - assert(!_teardrop || pitch==0); + assert(is_undef(user_thread_len) || (is_finite(user_thread_len) && user_thread_len>=0), "Must specify nonnegative thread length"); sides = max(pitch==0 ? 3 : 12, segs(nominal_diam/2)); head_height = headless || flathead ? 0 : counterbore==true || is_undef(counterbore) || counterbore==0 ? struct_val(spec, "head_height") @@ -716,7 +715,7 @@ module screw(spec, head, drive, thread, drive_size, pitch = struct_val(threadspec, "pitch"), l=thread_len+eps_thread, left_handed=false, internal=_internal, bevel1=bevel1, - bevel2=bevel2, + bevel2=bevel2,teardrop=_teardrop, blunt_start=blunt_start, blunt_start1=blunt_start1, blunt_start2=blunt_start2, $fn=sides, anchor=TOP); } @@ -774,7 +773,7 @@ module screw(spec, head, drive, thread, drive_size, // head = head type. See [screw heads](#subsection-screw-heads) Default: none // --- // thread = thread type or specification for threaded masks, true to make a threaded mask with the standard threads, or false to make an unthreaded mask. See [screw pitch](#subsection-standard-screw-pitch). Default: false -// teardrop = if true produce teardrop hole. Only compatible with clearance holes, not threaded. Default: false +// teardrop = if true produce teardrop hole. Default: false // oversize = amount to increase diameter of the screw hole (hole and countersink). A scalar or length 2 vector. Default: use computed tolerance // hole_oversize = amount to increase diameter of the hole. Overrides the use of tolerance and replaces any settings given in the screw specification. // head_oversize = amount to increase diameter of head. Overrides the user of tolerance and replaces any settings given in the screw specification. @@ -852,7 +851,6 @@ module screw_hole(spec, head, thread, oversize, hole_oversize, head_oversize, counterbore = default(counterbore, default_counterbore); dummy = _validate_screw_spec(screwspec); threaded = thread==true || (is_finite(thread) && thread>0) || (is_undef(thread) && struct_val(screwspec,"pitch")>0); - dummy2 = assert(!threaded || !teardrop, "Cannot make threaded teardrop holes"); oversize = force_list(oversize,2); hole_oversize = first_defined([hole_oversize, oversize[0],struct_val(screwspec,"shaft_oversize")]); head_oversize = first_defined([head_oversize, oversize[1],struct_val(screwspec,"head_oversize")]); From 4308fa3b18c30fe757ced27af5651cc6cc9d4b97 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Wed, 17 Jan 2024 19:34:48 -0500 Subject: [PATCH 02/17] de-triangulate VNF textures --- skin.scad | 104 +++++++++++++++++++++++++----------------------------- 1 file changed, 49 insertions(+), 55 deletions(-) diff --git a/skin.scad b/skin.scad index 6263b33..636c677 100644 --- a/skin.scad +++ b/skin.scad @@ -3155,10 +3155,10 @@ function texture(tex, n, border, gap, roughness, inset) = assert(is_undef(n), str(tex,__vnf_no_n_mesg)) let( border = default(border,1/4)*2, - gap = default(gap,1/4) + gap = default(gap,1/4), + f=echo(gap, border, gap+border, gap+2*border) ) assert(all_nonnegative([border,gap]), "trunc_ribs_vnf texture requires gap>=0 and border>=0") - assert(gap+border > 0, "trunc_ribs_vnf texture requires that gap+border>0") assert(gap+border <= 1, "trunc_ribs_vnf texture requires that gap+2*border<=1") [ [ @@ -3166,9 +3166,9 @@ function texture(tex, n, border, gap, roughness, inset) = each move([0.5,0.5], p=path3d(rect([1-gap-border,1]),1)), each path3d(square(1)), ], [ - [1,2,6], [1,6,5], [0,4,3], [3,4,7], - if (gap+border < 1-EPSILON) each [[4,5,6], [4,6,7]], - if (gap > EPSILON) each [[1,9,10], [1,10,2], [0,3,8], [3,11,8]], + [4,7,3,0], [1,2,6,5], + if (gap+border < 1-EPSILON) [4,5,6,7], + if (gap > EPSILON) each [[1,9,10,2], [0,3,11,8]], ] ] : tex=="wave_ribs"? @@ -3249,11 +3249,9 @@ function texture(tex, n, border, gap, roughness, inset) = each path3d(square(1)), each move([1/2,1/2,1], p=path3d(rect(1-2*border))), ], [ - for (i=[0:3]) each [ - [i, (i+1)%4, i+4], - [(i+1)%4, (i+1)%4+4, i+4], - ], - [4,5,6], [4,6,7], + for (i=[0:3]) + [i, (i+1)%4, (i+1)%4+4,i+4], + [4,5,6,7] ] ] : tex=="hills"? @@ -3300,15 +3298,9 @@ function texture(tex, n, border, gap, roughness, inset) = each move([0.5+gap/2, 0.5+gap/2, 0], p=path3d(square([0.5-gap/2, 0.5-gap]))), each move([0.5+gap/2+border/2, 0.5+gap/2+border/2, 1], p=path3d(square([0.5-gap/2-border/2, 0.5-gap-border]))), ], [ - [ 8, 9,10], [ 8,10,11], [16,17,18], [16,18,19], [24,25,26], - [24,26,27], [ 0, 1, 5], [ 0, 5, 4], [ 1,13, 6], [ 1, 6, 5], - [ 6,13,12], [ 6,12,21], [ 7,21,20], [ 6,21, 7], [ 0, 4, 7], - [ 0, 7,20], [21,12,15], [21,15,22], [ 3,23,22], [ 3,22,15], - [ 2,15,14], [ 2, 3,15], [23,27,26], [23,26,22], [21,22,26], - [21,26,25], [21,25,24], [21,24,20], [12,16,19], [12,19,15], - [14,15,19], [14,19,18], [13,17,16], [13,16,12], [ 6,10, 9], - [ 6, 9, 5], [ 5, 9, 8], [ 5, 8, 4], [ 4, 8,11], [ 4,11, 7], - [ 7,11,10], [ 7,10, 6], + [0,4,7,20], [4,8,11,7], [9,8,4,5], [4,0,1,5], [10,9,5,6], + [20,7,6,13,12,21] ,[2,3,23,22,15,14], [15,19,18,14], [22,23,27,26], [16,19,15,12],[13,6,5,1], + [26,25,21,22], [8,9,10,11],[7,11,10,6],[17,16,12,13],[22,21,12,15],[16,17,18,19],[24,25,26,27],[25,24,20,21] ] ] : tex=="checkers"? @@ -3329,15 +3321,11 @@ function texture(tex, n, border, gap, roughness, inset) = [1,1/2,0], [1,1-border,0], [1,1,1], [1/2-border/2,1-border/2,1/2], [1-border/2,1-border/2,1/2], [1-border/2,1/2-border/2,1/2], ], [ - for (i=[0:4:12]) each [[i,i+1,i+2], [i, i+2, i+3]], - [10,13,11], [13,12,11], [2,5,4], [4,3,2], - [0,3,10], [10,9,0], [4,7,14], [4,14,13], - [4,13,16], [10,16,13], [10,3,16], [3,4,16], - [7,6,17], [7,17,18], [14,19,20], [14,20,15], - [8,11,22], [8,22,21], [12,15,24], [12,24,23], - [7,18,26], [7,26,14], [14,26,19], [18,19,26], - [15,20,27], [20,25,27], [24,27,25], [15,27,24], - [11,12,28], [12,23,28], [11,28,22], [23,22,28], + for (i=[0:4:12]) each [[i,i+1,i+2,i+3]], + [10,16,13,12,28,11],[9,0,3,16,10], [11,28,22,21,8], + [4,7,26,14,13,16], [7,6,17,18,26], [5,4,16,3,2], + [19,20,27,15,14,26], [20,25,27], [19,26,18], + [23,28,12,15,27,24], [23,22,28], [24,27,25] ] ] : tex=="cones"? @@ -3352,11 +3340,13 @@ function texture(tex, n, border, gap, roughness, inset) = [ each move([1/2,1/2], p=path3d(circle(d=1-2*border,$fn=n))), [1/2,1/2,1], - each path3d(square(1)), + each border>0 ? path3d(subdivide_path(square(1),refine=2,closed=true)) + : path3d(square(1)) ], [ for (i=[0:1:n-1]) [i, (i+1)%n, n], - for (i=[0:1:3], j=[0:1:n/4-1]) [n+1+i, (i*n/4+j+1)%n, i*n/4+j], - if (border > 0) for (i = [0:1:3]) [i+n+1, (i+1)%4+n+1, ((i+1)*n/4)%n], + if (border>0) for (i=[0:3]) [for(j=[(i+1)*n/4:-1:i*n/4]) j%n, + (2*i+7)%8+n+1,(2*i)%8+n+1, (2*i+1)%8+n+1], + if (border==0) for (i=[0:3]) [for(j=[(i+1)*n/4:-1:i*n/4]) j%n, i+n+1] ] ] : tex=="cubes"? @@ -3387,10 +3377,10 @@ function texture(tex, n, border, gap, roughness, inset) = for (a=[0:90:359]) each move([1/2,1/2], p=zrot(-a, p=[[1/2,border,1], [border,1/2,1], [1/2,1/2,1]])) ], [ for (i=[0:3]) each let(j=i*3+8) [ - [i,(i+1)%4,(i+1)%4+4], [i,(i+1)%4+4,i+4], - [j,j+1,j+2], [i, (i+3)%4, j], [(i+3)%4, j+1, j], + [i,(i+1)%4,(i+1)%4+4,i+4], + [j,j+1,j+2], [i, (i+3)%4,j+1, j], ], - [4,5,6], [4,6,7], + [4,5,6,7], ] ] : tex=="dimples" || tex=="dots" ? @@ -3408,23 +3398,25 @@ function texture(tex, n, border, gap, roughness, inset) = cp = [1/2, 1/2, r*sin(45)*(dots?-1:1)], sc = 1 / (r - abs(cp.z)), uverts = [ - each path3d(square(1)), for (p=[0:1:rows-1], t=[0:360/n:359.999]) cp + ( dots? spherical_to_xyz(r, -t, 45-45*p/rows) : spherical_to_xyz(r, -t, 135+45*p/rows) ), cp + r * (dots?UP:DOWN), + each border>0 ? path3d(subdivide_path(square(1),refine=2,closed=true)) + : path3d(square(1)), + ], verts = zscale(sc, p=uverts), faces = [ - for (i=[0:1:3], j=[0:1:n/4-1]) [i, 4+(i*n/4+j+1)%n, 4+i*n/4+j], for (i=[0:1:rows-2], j=[0:1:n-1]) each [ - [4+i*n+j, 4+(i+1)*n+(j+1)%n, 4+(i+1)*n+j], - [4+i*n+j, 4+i*n+(j+1)%n, 4+(i+1)*n+(j+1)%n], + [i*n+j, i*n+(j+1)%n, (i+1)*n+(j+1)%n,(i+1)*n+j], ], - for (i=[0:1:n-1]) [4+(rows-1)*n+i, 4+(rows-1)*n+(i+1)%n, 4+rows*n], - if (border>0) for (i=[0:3]) [i, (i+1)%4, 4+(i+1)%4*n/4] + for (i=[0:1:n-1]) [(rows-1)*n+i, (rows-1)*n+(i+1)%n, rows*n], + if (border>0) for (i=[0:3]) [for(j=[(i+1)*n/4:-1:i*n/4]) j%n, + (2*i+7)%8+rows*n+1,(2*i)%8+rows*n+1, (2*i+1)%8+rows*n+1], + if (border==0) for (i=[0:3]) [for(j=[(i+1)*n/4:-1:i*n/4]) j%n, i+rows*n+1] ] ) [verts, faces] : tex=="tri_grid"? @@ -3457,13 +3449,15 @@ function texture(tex, n, border, gap, roughness, inset) = [adj,y6,1], [1-adj,y6,1], [0,1,0], [1,1,0], ], [ - [0,2,3], [0,3,1], [2,6,3], [0,12,2], [2,12,6], [3,6,12], [3,12,1], - [0,4,8], [0,8,12], [4,7,8], [7,11,12], [7,12,8], - [1,12,9], [1,9,5], [5,9,10], [9,12,13], [9,13,10], - [11,14,15], [11,15,12], [19,15,14], [19,23,12], [19,12,15], - [12,16,13], [16,17,13], [16,20,17], [12,24,20], [12,20,16], - [21,22,18], [21,23,24], [21,24,22], [12,23,21], [12,21,18], - [12,18,22], [12,22,24], + [0,2,3,1], + [21,23,24,22], + [2,6,3], [0,12,6,2], [1,3,6,12], + [0,4,8,12], [4,7,8], [8,7,11,12], + [1,12,9,5], [5,9,10], [10,9,12,13], + [11,14,15,12], [19,15,14], [19,23,12,15], + [16,17,13,12], [16,20,17], [12,24,20,16], + [21,22,18], [12,23,21,18], + [12,18,22,24], ] ] : tex=="hex_grid"? @@ -3492,14 +3486,14 @@ function texture(tex, n, border, gap, roughness, inset) = hex[5]+[0,diag*sc,1], [0,1,1], [0.5-border,1,1], [0.5,1,0], [0.5+border,1,1], [1,1,1], ], [ - for (i=[0:2:5]) let(b=6) [b+i, b+(i+1)%6, b+(i+2)%6], [6,8,10], - for (i=[0:1:5]) each [ [i, (i+1)%6, (i+1)%6+6], [i, (i+1)%6+6, i+6] ], - [19,13,12], [19,12,20], [17,16,15], [17,15,14], - [21,25,26], [21,26,22], [23,28,29], [23,29,24], - [0,12,13], [0,13,1], [1,14,15], [1,15,2], - [3,21,22], [3,22,4], [4,23,24], [4,24,5], - [1,13,19], [1,19,18], [1,18,17], [1,17,14], - [4,22,26], [4,26,27], [4,27,28], [4,28,23], + count(6,s=6), + for (i=[0:1:5]) [i,(i+1)%6, (i+1)%6+6, i+6], + [20,19,13,12], [17,16,15,14], + [21,25,26,22], [23,28,29,24], + [0,12,13,1], [1,14,15,2], + [3,21,22,4], [4,23,24,5], + [1,13,19,18], [1,18,17,14], + [4,22,26,27], [4,27,28,23], ] ] : tex=="rough"? From 85fec74abc5bf333e73a109e676a6424e7df34b6 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Wed, 17 Jan 2024 19:55:59 -0500 Subject: [PATCH 03/17] add remark on triangulation of vnfs --- skin.scad | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/skin.scad b/skin.scad index 636c677..edf5d91 100644 --- a/skin.scad +++ b/skin.scad @@ -2876,6 +2876,16 @@ function associate_vertices(polygons, split, curpoly=0) = // cyl(d=10/PI, h=5, chamfer=0, // texture=texture("bricks_vnf"), tex_samples=8, tex_reps=[6,3], tex_depth=.2); // } +// Continues: +// Note that when the VNF is sliced, +// extra points can be introduced in the interior of faces leading to unexpected irregularities in the textures, which appear +// as extra triangles. These artifacts can be minimized by making the VNF texture's faces as large as possible rather than using +// a triangulated VNF, but depending on the specific VNF texture, it may be impossible to entirely eliminate them. +// Figure(3D,Big,NoAxes,VPR=[140.9,0,345.7],VPT=[9.48289,-0.88709,5.7837],VPD=39.5401): The left shows a normal bricks_vnf texture. The right shows a texture that was first passed through {{vnf_triangulate()}}. Note the extra triangle artifacts visible across the brick faces. +// tex = texture("bricks_vnf"); +// cyl(d=10,h=15,texture=tex, tex_reps=[4,2],tex_samples=5); +// up(7)fwd(-3)right(15)cyl(d=10,h=15,texture=vnf_triangulate(tex), tex_reps=[4,2],tex_samples=5); + // Function: texture() // Topics: Textures, Knurling From 20c5a4241d6ba9a6fc8c8e73d601ccc578b3b8c0 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Thu, 18 Jan 2024 00:56:27 +0000 Subject: [PATCH 04/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index c978b20..a613448 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,691]; +BOSL_VERSION = [2,0,692]; From f1a466c19dad30aa1a8bd15f82f72ee5da7b7022 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Fri, 19 Jan 2024 23:11:23 -0500 Subject: [PATCH 05/17] add vnf_unify_faces() --- vnf.scad | 129 ++++++++++++++++++++++++++++++++++++++++++++----------- 1 file changed, 104 insertions(+), 25 deletions(-) diff --git a/vnf.scad b/vnf.scad index 60a8061..378dc96 100644 --- a/vnf.scad +++ b/vnf.scad @@ -682,7 +682,7 @@ function vnf_faces(vnf) = vnf[1]; // Synopsis: Reverses the faces of a VNF. // SynTags: VNF // Topics: VNF Manipulation -// See Also: vnf_quantize(), vnf_merge_points(), vnf_drop_unused_points(), vnf_triangulate(), vnf_slice() +// See Also: vnf_quantize(), vnf_merge_points(), vnf_drop_unused_points(), vnf_triangulate(), vnf_slice(), vnf_unify_faces() // Usage: // rvnf = vnf_reverse_faces(vnf); // Description: @@ -712,7 +712,7 @@ function vnf_quantize(vnf,q=pow(2,-12)) = // Synopsis: Consolidates duplicate vertices of a VNF. // SynTags: VNF // Topics: VNF Manipulation -// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_drop_unused_points(), vnf_triangulate(), vnf_slice() +// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_drop_unused_points(), vnf_triangulate(), vnf_slice(), vnf_unify_faces() // Usage: // new_vnf = vnf_merge_points(vnf, [eps]); // Description: @@ -748,7 +748,7 @@ function vnf_merge_points(vnf,eps=EPSILON) = // Synopsis: Removes unreferenced vertices from a VNF. // SynTags: VNF // Topics: VNF Manipulation -// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_triangulate(), vnf_slice() +// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_triangulate(), vnf_slice(), vnf_unify_faces() // Usage: // clean_vnf = vnf_drop_unused_points(vnf); // Description: @@ -780,7 +780,7 @@ function _link_indicator(l,imin,imax) = // Synopsis: Triangulates the faces of a VNF. // SynTags: VNF // Topics: VNF Manipulation -// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_drop_unused_points(), vnf_slice() +// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_drop_unused_points(), vnf_slice(), vnf_unify_faces() // Usage: // vnf2 = vnf_triangulate(vnf); // Description: @@ -806,6 +806,84 @@ function vnf_triangulate(vnf) = +// Function vnf_unify_faces() +// Synposis: Remove triangulation from VNF, returning a copy with full faces +// SynTags: VNF +// Topics: VNF Manipulation +// See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_triangulate(), vnf_slice() +// Usage: +// newvnf = vnf_unify_faces(vnf); +// Description: +// When a VNF has been triangulated, the polygons that form the true faces have been chopped up into +// triangles. This can create problems for algorithms that operate on the VNF itself, where you might +// want to be able to identify the true faces. This function merges together the triangles that +// form those true faces, turning a VNF where each true face is represented by a single entry +// in the faces list of the VNF. This function requires that the true faces have no internal vertices. +// This will always be true for a triangulated VNF, but might fail for a VNF with some other +// face partition. If internal vertices are present, the output will include backtracking paths from +// the boundary to all of those vertices. +// Arguments: +// vnf = vnf whose faces you want to unify +// Example(3D): Original prism on the left is triangulated. On the right, the result of unifying the faces. +// $fn=16; +// poly = linear_sweep(hexagon(side=10),h=35); +// vnf = vnf_unify_faces(poly); +// color([0,1,1,.5])vnf_polyhedron(poly); +// vnf_wireframe(poly); +// right(25){ +// color([0,1,1,.5])vnf_polyhedron(vnf); +// vnf_wireframe(vnf); +// } + +function vnf_unify_faces(vnf) = + let( + faces = vnf[1], + edges = [for(i=idx(faces), edge=pair(faces[i],wrap=true)) + [[min(edge),max(edge)],i]], + normals = [for(face=faces) polygon_normal(select(vnf[0],face))], + facelist = count(faces), //[for(i=[1:1:len(faces)-1]) i], + newfaces = _detri_combine_faces(edges,faces,normals,facelist,0) + ) + [vnf[0],newfaces]; + + +function _detri_combine_faces(edgelist,faces,normals,facelist,curface) = + curface==len(faces)? select(faces,facelist) + : !in_list(curface,facelist) ? _detri_combine_faces(edgelist,faces,normals,facelist,curface+1) + : + let( + thisface=faces[curface], + neighbors = [for(i=idx(thisface)) + let( + edgepair = search([sort(select(thisface,i,i+1))],edgelist,0)[0], + choices = select(edgelist,edgepair), + good_choice=[for(choice=choices) + if (choice[1]!=curface && in_list(choice[1],facelist) && normals[choice[1]]*normals[curface]>1-EPSILON) + choice], + d=assert(len(good_choice)<=1), + ) + len(good_choice)==1 ? good_choice[0][1] : -1 + ], + // Check for duplicates in the neighbor list so we don't add them twice + dups = search([for(n=neighbors) if (n>=0) n], neighbors,0), + goodind = column(dups,0), + newface = [for(i=idx(thisface)) + each + !in_list(i,goodind) ? [thisface[i]] + : + let( + ind = search(select(thisface,i,i+1), faces[neighbors[i]]) + ) + select(faces[neighbors[i]],ind[0],ind[1]-1) + ], + usedfaces = [for(n=neighbors) if (n>=0) n], + faces = list_set(faces,curface,newface), + facelist = list_remove_values(facelist,usedfaces) + ) + _detri_combine_faces(edgelist,faces,normals,facelist,len(usedfaces)==0?curface+1:curface); + + + function _vnf_sort_vertices(vnf, idx=[2,1,0]) = let( verts = vnf[0], @@ -843,7 +921,8 @@ function _vnf_sort_vertices(vnf, idx=[2,1,0]) = // color("red")vnf_wireframe(sliced,width=.3); function vnf_slice(vnf,dir,cuts) = let( - cuts = [for (cut=cuts) _shift_cut_plane(vnf,dir,cut)], + // Code below seems to be unnecessary + //cuts = [for (cut=cuts) _shift_cut_plane(vnf,dir,cut)], vert = vnf[0], faces = [for(face=vnf[1]) select(vert,face)], poly_list = _slice_3dpolygons(faces, dir, cuts) @@ -920,26 +999,26 @@ function _slice_3dpolygons(polys, dir, cuts) = ) flatten([ for (poly = polys) - let( plane = plane_from_polygon(poly)) - assert(plane,"Found non-coplanar face.") - let( - normal = point3d(plane), - pnormal = normal - (normal*I[dir_ind])*I[dir_ind] - ) - approx(pnormal,[0,0,0]) ? [poly] : - let ( - pind = max_index(v_abs(pnormal)), // project along this direction - otherind = 3-pind-dir_ind, // keep dir_ind and this direction - keep = [I[dir_ind], I[otherind]], // dir ind becomes the x dir - poly2d = poly*transpose(keep), // project to 2d, putting selected direction in the X position - poly_list = [for(p=_split_2dpolygons_at_each_x([poly2d], cuts)) - let( - a = p*keep, // unproject, but pind dimension data is missing - ofs = outer_product((repeat(plane[3], len(a))-a*normal)/plane[pind],I[pind]) - ) - a+ofs] // ofs computes the missing pind dimension data and adds it back in - ) - poly_list + let( plane = plane_from_polygon(poly)) + assert(plane,"Found non-coplanar face.") + let( + normal = point3d(plane), + pnormal = normal - (normal*I[dir_ind])*I[dir_ind] + ) + approx(pnormal,[0,0,0]) ? [poly] // Polygons parallel to cut plane just pass through + : let( + pind = max_index(v_abs(pnormal)), // project along this direction + otherind = 3-pind-dir_ind, // keep dir_ind and this direction + keep = [I[dir_ind], I[otherind]], // dir ind becomes the x dir + poly2d = poly*transpose(keep), // project to 2d, putting selected direction in the X position + poly_list = [for(p=_split_2dpolygons_at_each_x([poly2d], cuts)) + let( + a = p*keep, // unproject, but pind dimension data is missing + ofs = outer_product((repeat(plane[3], len(a))-a*normal)/plane[pind],I[pind]) + ) + a+ofs] // ofs computes the missing pind dimension data and adds it back in + ) + poly_list ]); From 8451f6af2be5d0ede17723a1052b62181a322f36 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 04:11:58 +0000 Subject: [PATCH 06/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index a613448..583057d 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,692]; +BOSL_VERSION = [2,0,693]; From 5f8378ada6d89b632f0021ca2fb6a074b6fb8399 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Fri, 19 Jan 2024 23:14:58 -0500 Subject: [PATCH 07/17] diagram improvement --- vnf.scad | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/vnf.scad b/vnf.scad index 378dc96..7175ac9 100644 --- a/vnf.scad +++ b/vnf.scad @@ -824,15 +824,15 @@ function vnf_triangulate(vnf) = // the boundary to all of those vertices. // Arguments: // vnf = vnf whose faces you want to unify -// Example(3D): Original prism on the left is triangulated. On the right, the result of unifying the faces. +// Example(3D,Med,NoAxes): Original prism on the left is triangulated. On the right, the result of unifying the faces. // $fn=16; // poly = linear_sweep(hexagon(side=10),h=35); // vnf = vnf_unify_faces(poly); -// color([0,1,1,.5])vnf_polyhedron(poly); // vnf_wireframe(poly); +// color([0,1,1,.70])vnf_polyhedron(poly); // right(25){ -// color([0,1,1,.5])vnf_polyhedron(vnf); // vnf_wireframe(vnf); +// color([0,1,1,.70])vnf_polyhedron(vnf); // } function vnf_unify_faces(vnf) = From 0e8dd2c1c1df943387218a7f89002a0d391aa8a9 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 04:15:18 +0000 Subject: [PATCH 08/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index 583057d..cda7fce 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,693]; +BOSL_VERSION = [2,0,694]; From 8f8f6a2861d893d4aa4725c67add0025f242e311 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 04:44:55 +0000 Subject: [PATCH 09/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index 4edf1d1..06d8568 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,694]; +BOSL_VERSION = [2,0,695]; From b65c8076913e25ee72048eaa0f88e122202e94e1 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Fri, 19 Jan 2024 23:46:16 -0500 Subject: [PATCH 10/17] remove comma for old version --- vnf.scad | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/vnf.scad b/vnf.scad index 7175ac9..d0f7a56 100644 --- a/vnf.scad +++ b/vnf.scad @@ -825,15 +825,15 @@ function vnf_triangulate(vnf) = // Arguments: // vnf = vnf whose faces you want to unify // Example(3D,Med,NoAxes): Original prism on the left is triangulated. On the right, the result of unifying the faces. -// $fn=16; -// poly = linear_sweep(hexagon(side=10),h=35); -// vnf = vnf_unify_faces(poly); -// vnf_wireframe(poly); -// color([0,1,1,.70])vnf_polyhedron(poly); -// right(25){ -// vnf_wireframe(vnf); -// color([0,1,1,.70])vnf_polyhedron(vnf); -// } + $fn=16; + poly = linear_sweep(hexagon(side=10),h=35); + vnf = vnf_unify_faces(poly); + vnf_wireframe(poly); + color([0,1,1,.70])vnf_polyhedron(poly); + right(25){ + vnf_wireframe(vnf); + color([0,1,1,.70])vnf_polyhedron(vnf); + } function vnf_unify_faces(vnf) = let( @@ -860,7 +860,7 @@ function _detri_combine_faces(edgelist,faces,normals,facelist,curface) = good_choice=[for(choice=choices) if (choice[1]!=curface && in_list(choice[1],facelist) && normals[choice[1]]*normals[curface]>1-EPSILON) choice], - d=assert(len(good_choice)<=1), + d=assert(len(good_choice)<=1) ) len(good_choice)==1 ? good_choice[0][1] : -1 ], From 1d43fe8c8025552534dfe7072c586fbb56a5168f Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 04:46:38 +0000 Subject: [PATCH 11/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index 06d8568..58f5d18 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,695]; +BOSL_VERSION = [2,0,696]; From d39cd5adbb15608f388a1bb9c38b2f811be8d2ba Mon Sep 17 00:00:00 2001 From: revarbat Date: Sat, 20 Jan 2024 04:50:40 +0000 Subject: [PATCH 12/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index 9042888..77aad53 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,696]; +BOSL_VERSION = [2,0,697]; // Section: BOSL Library Version Functions From f6ac8509ed9b466398d4ff1dbafcf294e00712ee Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Fri, 19 Jan 2024 23:57:51 -0500 Subject: [PATCH 13/17] comment out example --- vnf.scad | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/vnf.scad b/vnf.scad index d0f7a56..9c2a239 100644 --- a/vnf.scad +++ b/vnf.scad @@ -825,15 +825,15 @@ function vnf_triangulate(vnf) = // Arguments: // vnf = vnf whose faces you want to unify // Example(3D,Med,NoAxes): Original prism on the left is triangulated. On the right, the result of unifying the faces. - $fn=16; - poly = linear_sweep(hexagon(side=10),h=35); - vnf = vnf_unify_faces(poly); - vnf_wireframe(poly); - color([0,1,1,.70])vnf_polyhedron(poly); - right(25){ - vnf_wireframe(vnf); - color([0,1,1,.70])vnf_polyhedron(vnf); - } +// $fn=16; +// poly = linear_sweep(hexagon(side=10),h=35); +// vnf = vnf_unify_faces(poly); +// vnf_wireframe(poly); +// color([0,1,1,.70])vnf_polyhedron(poly); +// right(25){ +// vnf_wireframe(vnf); +// color([0,1,1,.70])vnf_polyhedron(vnf); +// } function vnf_unify_faces(vnf) = let( From 41369e844b471e1fba1617d85f07242f0262f7a3 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 04:58:12 +0000 Subject: [PATCH 14/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index 77aad53..c24b60d 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,697]; +BOSL_VERSION = [2,0,698]; // Section: BOSL Library Version Functions From d17f72cffdd16fc007e0893b8d8a8261c7b60b39 Mon Sep 17 00:00:00 2001 From: Adrian Mariano Date: Sat, 20 Jan 2024 14:12:18 -0500 Subject: [PATCH 15/17] skip zero area polygons in vnf_slice --- vnf.scad | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/vnf.scad b/vnf.scad index 9c2a239..06ecff4 100644 --- a/vnf.scad +++ b/vnf.scad @@ -806,8 +806,8 @@ function vnf_triangulate(vnf) = -// Function vnf_unify_faces() -// Synposis: Remove triangulation from VNF, returning a copy with full faces +// Function: vnf_unify_faces() +// Synopsis: Remove triangulation from VNF, returning a copy with full faces // SynTags: VNF // Topics: VNF Manipulation // See Also: vnf_reverse_faces(), vnf_quantize(), vnf_merge_points(), vnf_triangulate(), vnf_slice() @@ -999,7 +999,9 @@ function _slice_3dpolygons(polys, dir, cuts) = ) flatten([ for (poly = polys) - let( plane = plane_from_polygon(poly)) + if (polygon_area(poly)>EPSILON) // Discard zero area polygons + let( + plane = plane_from_polygon(poly,1e-4)) assert(plane,"Found non-coplanar face.") let( normal = point3d(plane), From 0d9d5d8e6d680c92b14dea498f76f46f84c4ede0 Mon Sep 17 00:00:00 2001 From: adrianVmariano Date: Sat, 20 Jan 2024 19:12:40 +0000 Subject: [PATCH 16/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index c24b60d..f1863ed 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,698]; +BOSL_VERSION = [2,0,699]; // Section: BOSL Library Version Functions From 460cd884c3ad4a7006b1b59b57feaf54ecb5b624 Mon Sep 17 00:00:00 2001 From: revarbat Date: Thu, 25 Jan 2024 08:31:12 +0000 Subject: [PATCH 17/17] Version Bump --- version.scad | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.scad b/version.scad index f1863ed..5605ae8 100644 --- a/version.scad +++ b/version.scad @@ -9,7 +9,7 @@ ////////////////////////////////////////////////////////////////////// -BOSL_VERSION = [2,0,699]; +BOSL_VERSION = [2,0,700]; // Section: BOSL Library Version Functions