1
0
mirror of https://github.com/JustinSDK/dotSCAD.git synced 2025-08-21 05:52:16 +02:00

pass function

This commit is contained in:
Justin Lin
2021-05-07 08:00:30 +08:00
parent d4dbbc7952
commit a42f758f35
2 changed files with 50 additions and 41 deletions

View File

@@ -8,8 +8,6 @@ use <../../util/some.scad>;
use <../../util/has.scad>; use <../../util/has.scad>;
use <../../util/find_index.scad>; use <../../util/find_index.scad>;
_indices_hash = function(indices) indices[0] * 961 + indices[1] * 31 + indices[2];
function _tri_circumcircle(shape_pts) = function _tri_circumcircle(shape_pts) =
let( let(
p0 = shape_pts[0], p0 = shape_pts[0],
@@ -34,7 +32,7 @@ function _tri_circumcircle(shape_pts) =
function cc_center(cc) = cc[0]; function cc_center(cc) = cc[0];
function cc_rr(cc) = cc[1]; function cc_rr(cc) = cc[1];
function delaunay_init(center, width, height, leng_points) = function delaunay_init(center, width, height, leng_points, _indices_hash) =
let( let(
halfW = width * 0.5, halfW = width * 0.5,
halfH = height * 0.5, halfH = height * 0.5,
@@ -64,13 +62,13 @@ function delaunay_init(center, width, height, leng_points) =
) )
[coords, triangles, circles]; [coords, triangles, circles];
function delaunay_addpoint(d, p) = function delaunay_addpoint(d, p, _indices_hash) =
let( let(
idx = len(delaunay_coords(d)), idx = len(delaunay_coords(d)),
ndelaunay = delaunayAddCoords(d, p), ndelaunay = delaunayAddCoords(d, p),
badTriangles = delaunayBadTriangles(ndelaunay, p), badTriangles = delaunayBadTriangles(ndelaunay, p, _indices_hash),
boundaries = delaunayBoundaries(ndelaunay, badTriangles), boundaries = delaunayBoundaries(ndelaunay, badTriangles, _indices_hash),
ndelaunay2 = delBadTriangles(ndelaunay, badTriangles), ndelaunay2 = delBadTriangles(ndelaunay, badTriangles, _indices_hash),
newTriangles = [ newTriangles = [
for(b = boundaries) [ for(b = boundaries) [
[idx, b[0][0], b[0][1]], // t [idx, b[0][0], b[0][1]], // t
@@ -79,9 +77,9 @@ function delaunay_addpoint(d, p) =
] ]
] ]
) )
adjustNeighbors(ndelaunay2, newTriangles); adjustNeighbors(ndelaunay2, newTriangles, _indices_hash);
function adjustNeighbors(d, newTriangles) = function adjustNeighbors(d, newTriangles, _indices_hash) =
let( let(
coords = delaunay_coords(d), coords = delaunay_coords(d),
nts = [ nts = [
@@ -94,22 +92,22 @@ function adjustNeighbors(d, newTriangles) =
], ],
nd = [ nd = [
coords, coords,
hashmap_puts(delaunay_triangles(d), nts), hashmap_puts(delaunay_triangles(d), nts, _indices_hash),
hashmap_puts(delaunay_circles(d), ncs), hashmap_puts(delaunay_circles(d), ncs, _indices_hash),
], ],
leng = len(newTriangles), leng = len(newTriangles),
aDtrid = _adjustNeighborsDtri(nd, newTriangles, leng) aDtrid = _adjustNeighborsDtri(nd, newTriangles, leng, _indices_hash)
) )
_adjustNeighborsOtri(aDtrid, newTriangles, leng); _adjustNeighborsOtri(aDtrid, newTriangles, leng, _indices_hash);
function hashmap_puts(m, kv_lt) = _hashmap_puts(m, kv_lt, len(kv_lt)); function hashmap_puts(m, kv_lt, _indices_hash) = _hashmap_puts(m, kv_lt, len(kv_lt), _indices_hash);
function _hashmap_puts(m, kv_lt, leng, i = 0) = function _hashmap_puts(m, kv_lt, leng, _indices_hash, i = 0) =
i == leng ? m : i == leng ? m :
let(kv = kv_lt[i]) let(kv = kv_lt[i])
_hashmap_puts(hashmap_put(m, kv[0], kv[1], hash = _indices_hash), kv_lt, leng, i + 1); _hashmap_puts(hashmap_put(m, kv[0], kv[1], hash = _indices_hash), kv_lt, leng, _indices_hash, i + 1);
function _adjustNeighborsOtri(d, newTriangles, leng, i = 0) = function _adjustNeighborsOtri(d, newTriangles, leng, _indices_hash, i = 0) =
i == leng ? d : i == leng ? d :
let( let(
t = newTriangles[i][0], t = newTriangles[i][0],
@@ -120,9 +118,9 @@ function _adjustNeighborsOtri(d, newTriangles, leng, i = 0) =
nTriangles = hashmap_put(hashmap_del(triangles, t, hash = _indices_hash), t, [v[0], nbr1, nbr2], hash = _indices_hash), nTriangles = hashmap_put(hashmap_del(triangles, t, hash = _indices_hash), t, [v[0], nbr1, nbr2], hash = _indices_hash),
nd = [delaunay_coords(d), nTriangles, delaunay_circles(d)] nd = [delaunay_coords(d), nTriangles, delaunay_circles(d)]
) )
_adjustNeighborsOtri(nd, newTriangles, leng, i + 1); _adjustNeighborsOtri(nd, newTriangles, leng, _indices_hash, i + 1);
function _adjustNeighborsDtri(d, newTriangles, leng, i = 0) = function _adjustNeighborsDtri(d, newTriangles, leng, _indices_hash, i = 0) =
i == leng ? d : i == leng ? d :
let( let(
t = newTriangles[i][0], t = newTriangles[i][0],
@@ -137,17 +135,20 @@ function _adjustNeighborsDtri(d, newTriangles, leng, i = 0) =
nd = nbri == -1 ? d : updateNbrs(d, delaunayTri, [ nd = nbri == -1 ? d : updateNbrs(d, delaunayTri, [
for(j = 0; j < leng_nbrs; j = j + 1) for(j = 0; j < leng_nbrs; j = j + 1)
j == nbri ? t : neighbors[j] j == nbri ? t : neighbors[j]
]) ], _indices_hash)
) )
_adjustNeighborsDtri(nd, newTriangles, leng, i + 1) : _adjustNeighborsDtri(nd, newTriangles, leng, _indices_hash, i + 1) :
_adjustNeighborsDtri(d, newTriangles, leng, i + 1); _adjustNeighborsDtri(d, newTriangles, leng, _indices_hash, i + 1);
function updateNbrs(d, delaunayTri, neighbors) = function updateNbrs(d, delaunayTri, neighbors, _indices_hash) =
let( let(
coords = delaunay_coords(d), coords = delaunay_coords(d),
triangles = delaunay_triangles(d), triangles = delaunay_triangles(d),
circles = delaunay_circles(d), circles = delaunay_circles(d),
nTriangles = hashmap_put(hashmap_del(triangles, delaunayTri, hash = _indices_hash), delaunayTri, neighbors, hash = _indices_hash) nTriangles = hashmap_put(
hashmap_del(triangles, delaunayTri, hash = _indices_hash),
delaunayTri, neighbors, hash = _indices_hash
)
) )
[coords, nTriangles, circles]; [coords, nTriangles, circles];
@@ -158,14 +159,14 @@ function delaunayAddCoords(d, p) =
delaunay_circles(d) delaunay_circles(d)
]; ];
function delaunayBadTriangles(d, p) = function delaunayBadTriangles(d, p, _indices_hash) =
let( let(
triangles = delaunay_triangles(d), triangles = delaunay_triangles(d),
circles = delaunay_circles(d) circles = delaunay_circles(d)
) )
[ [
for(t = hashmap_keys(triangles)) for(t = hashmap_keys(triangles))
if(inCircumcircle(t, p, circles)) if(inCircumcircle(t, p, circles, _indices_hash))
t t
]; ];
@@ -174,7 +175,7 @@ function delaunayBadTriangles(d, p) =
t: triangle indices t: triangle indices
circles: a hashmap circles: a hashmap
*/ */
function inCircumcircle(t, p, circles) = function inCircumcircle(t, p, circles, _indices_hash) =
let( let(
c = hashmap_get(circles, t, hash = _indices_hash), c = hashmap_get(circles, t, hash = _indices_hash),
v = cc_center(c) - p, v = cc_center(c) - p,
@@ -182,15 +183,15 @@ function inCircumcircle(t, p, circles) =
) )
rr <= cc_rr(c); rr <= cc_rr(c);
function delaunayBoundaries(d, badTriangles) = function delaunayBoundaries(d, badTriangles, _indices_hash) =
let( let(
boundaries = [], boundaries = [],
t = badTriangles[0], t = badTriangles[0],
vi = 0 vi = 0
) )
_delaunayBoundaries(d, badTriangles, boundaries, t, vi); _delaunayBoundaries(d, badTriangles, boundaries, t, vi, _indices_hash);
function _delaunayBoundaries(d, badTriangles, boundaries, t, vi) = function _delaunayBoundaries(d, badTriangles, boundaries, t, vi, _indices_hash) =
let( let(
triangles = delaunay_triangles(d), triangles = delaunay_triangles(d),
opTri = hashmap_get(triangles, t, hash = _indices_hash)[vi] opTri = hashmap_get(triangles, t, hash = _indices_hash)[vi]
@@ -201,7 +202,7 @@ function _delaunayBoundaries(d, badTriangles, boundaries, t, vi) =
nvi = (i + 1) % 3, nvi = (i + 1) % 3,
nt = opTri nt = opTri
) )
_delaunayBoundaries(d, badTriangles, boundaries, nt, nvi) : _delaunayBoundaries(d, badTriangles, boundaries, nt, nvi, _indices_hash) :
let( let(
nboundaries = concat(boundaries, [[ nboundaries = concat(boundaries, [[
[t[(vi + 1) % 3], t[vi > 0 ? vi - 1 : (vi + 2)]], // edge [t[(vi + 1) % 3], t[vi > 0 ? vi - 1 : (vi + 2)]], // edge
@@ -211,21 +212,23 @@ function _delaunayBoundaries(d, badTriangles, boundaries, t, vi) =
v1 = nboundaries[0][0][0], v1 = nboundaries[0][0][0],
v2 = nboundaries[len(nboundaries) - 1][0][1] v2 = nboundaries[len(nboundaries) - 1][0][1]
) )
v1 == v2 ? nboundaries : _delaunayBoundaries(d, badTriangles, nboundaries, t, nvi); v1 == v2 ? nboundaries : _delaunayBoundaries(d, badTriangles, nboundaries, t, nvi, _indices_hash);
function delBadTriangles(d, badTriangles) = function delBadTriangles(d, badTriangles, _indices_hash) =
[ [
delaunay_coords(d), delaunay_coords(d),
hashmap_dels(delaunay_triangles(d), badTriangles), hashmap_dels(delaunay_triangles(d), badTriangles, _indices_hash),
hashmap_dels(delaunay_circles(d), badTriangles) hashmap_dels(delaunay_circles(d), badTriangles, _indices_hash)
]; ];
function hashmap_dels(m, keys) = _hashmap_dels(m, keys, len(keys)); function hashmap_dels(m, keys, _indices_hash) = _hashmap_dels(m, keys, len(keys), _indices_hash);
function _hashmap_dels(m, keys, leng, i = 0) = function _hashmap_dels(m, keys, leng, _indices_hash, i = 0) =
i == leng ? m : i == leng ? m :
_hashmap_dels(hashmap_del(m, keys[i], hash = _indices_hash), keys, leng, i + 1); _hashmap_dels(hashmap_del(m, keys[i], hash = _indices_hash), keys, leng, _indices_hash, i + 1);
function _tri_delaunay(d, points, leng, i = 0) = function _tri_delaunay(d, points, leng, _indices_hash, i = 0) =
i == leng ? d : i == leng ? d :
_tri_delaunay(delaunay_addpoint(d, points[i]), points, leng, i + 1); _tri_delaunay(
delaunay_addpoint(d, points[i], _indices_hash),
points, leng, _indices_hash, i + 1);

View File

@@ -6,6 +6,7 @@ use <tri_delaunay_voronoi.scad>;
// ret: "TRI_SHAPES", "TRI_INDICES", "VORONOI_CELLS", "DELAUNAY" // ret: "TRI_SHAPES", "TRI_INDICES", "VORONOI_CELLS", "DELAUNAY"
function tri_delaunay(points, ret = "TRI_INDICES") = function tri_delaunay(points, ret = "TRI_INDICES") =
let( let(
_indices_hash = function(indices) indices[0] * 961 + indices[1] * 31 + indices[2],
xs = [for(p = points) p[0]], xs = [for(p = points) p[0]],
ys = [for(p = points) p[1]], ys = [for(p = points) p[1]],
max_x = max(xs), max_x = max(xs),
@@ -16,7 +17,12 @@ function tri_delaunay(points, ret = "TRI_INDICES") =
width = abs(max_x - center[0]) * 4, width = abs(max_x - center[0]) * 4,
height = abs(max_y - center[1]) * 4, height = abs(max_y - center[1]) * 4,
leng_pts = len(points), leng_pts = len(points),
d = _tri_delaunay(delaunay_init(center, width, height, leng_pts), points, leng_pts) d = _tri_delaunay(
delaunay_init(center, width, height, leng_pts, _indices_hash),
points,
leng_pts,
_indices_hash
)
) )
ret == "TRI_INDICES" ? tri_delaunay_indices(d) : ret == "TRI_INDICES" ? tri_delaunay_indices(d) :
ret == "TRI_SHAPES" ? tri_delaunay_shapes(d) : ret == "TRI_SHAPES" ? tri_delaunay_shapes(d) :