well ⦠i looked into the file and its setup and requirements.
as i expected the straightforward position comparison is very slow because of pretty big meshes and pure algorithm
anyway here is the code:
fn getOpenEdgeVerts mesh =
(
ee = meshop.getopenedges mesh
meshop.getvertsusingedge mesh ee
)
fn isMeshCloseEnough source target threshold:10 open:off =
(
near = off
sv = if open then getOpenEdgeVerts source else source.verts as bitarray
tv = if open then getOpenEdgeVerts target else target.verts as bitarray
for s in sv while not near do
(
p = getvert source s
for t in tv while not near do
(
near = distance p (getvert target t) <= threshold
)
)
near
)
fn findMeshesCloseEnough sources: targets: threshold:10 open:on =
(
if sources == unsupplied do sources = selection as array
sources = for source in sources where iskindof source Editable_mesh collect source
if targets == unsupplied do targets = for target in geometry where iskindof target Editable_mesh collect target
targets = for target in targets where (finditem sources target == 0) collect target
format ">> s:% t:%\n" sources.count targets.count
_sources = deepcopy (sources as array)
for source in _sources do
(
format "% >>" (finditem sources source)
for i = targets.count to 1 by -1 while not keyboard.escpressed do
(
target = targets[i]
if (isMeshCloseEnough source target threshold:threshold open:open) do
(
append sources target
deleteitem targets i
)
)
format " s:% t:%\n" sources.count targets.count
)
sources
)
fn findAllMeshesCloseEnough sources: targets: threshold:10 open:on =
(
if sources == unsupplied do sources = selection as array
sources = for source in sources where iskindof source Editable_mesh collect source
if targets == unsupplied do targets = for target in geometry where iskindof target Editable_mesh collect target
targets = for target in targets where (finditem sources target == 0) collect target
format ">> s:% t:%\n" sources.count targets.count
data = [0,0]
curr = [sources.count, targets.count]
for source in sources while not keyboard.escpressed do
(
data = copy curr
format "% >>" (finditem sources source)
for i = targets.count to 1 by -1 while not keyboard.escpressed do
(
target = targets[i]
if (isMeshCloseEnough source target threshold:threshold open:open) do
(
append sources target
deleteitem targets i
)
)
format " s:% t:%\n" sources.count targets.count
curr = [sources.count, targets.count]
)
sources
)
you can select the first mesh and run (with a specified threshold):
all = findAllMeshesCloseEnough threshold:10
select all
this function recursively adds close enough meshes to the list and grows the search. it stops when no new target was added.
the function shows the trace (where you can see timing and algorithm working)
i found that most meshes are āconnectedā by open edges, so there is no reason to search all verts.
the function has an option <open: true/false>, which controls what set of verts to use (open or all). so, see the difference
the possible optimization could be:
#1 check meshes bounding box intersection before verts searching to ensure that the searching is needed at all
#2 of course itās better to use Kd-tree search algorithm ⦠but itās a subject of another topic
(with a smart Kd-tree full search takes about 0.1 sec on my machine)
good luck!