[Closed] Find similar vertex position in 2 objects
Hey everybody
As title say I like to find the similar vertices in 2 objects by their position, but in this example I can’t use the “distance” function, it just find one because of vertices order!
How to find the 2 similar vertices in these 2 objects:
wire1 = splineShape name:"wire1" wire1color:blue vertexTicks:on
addnewSpline wire1
addKnot wire1 1 #corner #line [30,30,0]
addKnot wire1 1 #corner #line [30,-30,0]
addKnot wire1 1 #corner #line [-30,-30,0]
addKnot wire1 1 #corner #line [-30,30,0]
close wire1 1
convertToPoly wire1
update wire1
wire2 = splineShape name:"wire2" wire1color:blue vertexTicks:on
addnewSpline wire2
addKnot wire2 1 #corner #line [60,0,0]
addKnot wire2 1 #corner #line [30,30,0]
addKnot wire2 1 #corner #line [30,-30,0]
close wire2 1
convertToPoly wire2
update wire2
Similar is a very broad term. But you could start from using GetHashValue of their knot positions
First time to hear ” GetHashValue” I’m on max 2016.
The objects are editable poly .
to show the vertex order i used spline then converted to edit poly.
If i try to find the distance between the vertcies of 2 objects, one of them has 3 vert and other has 4
and in this example I can just find one of them which is the vert numer “3”
For anybody else with the same problem searching in the future you should post the answer you found.
Frankly & honestly
When i think that denis & othres guru guys can see my crazy solution
I’m really shy to share the codes
But when you say that
Tha is OK.
Here is my approach for the scene above
fn ColectVerPos obj VertAr=
(
nVerts = obj.numverts
for i=1 to nVerts do (append VertAr (polyop.getvert obj i ) )
)
--test1
select wire1
selectmore wire2
--test2
select wire2
selectmore wire1
--collect the vertices
obj1 = selection[1]
obj1VertAr=#()
ColectVerPos obj1 obj1VertAr
obj2 = selection[2]
obj2VertAr=#()
ColectVerPos obj2 obj2VertAr
here was my mistake
The2VertAr =#()
for i = 1 to obj1VertAr.count do
(
for k in obj1VertAr do --(print k)
(
if (distance k obj2VertAr[i] < 0.01) do (append The2VertAr k)
)
)
above code if you select the bigger poly (wire1) in vertices first , you face a problem.
and if you select lesser ploy in vert (wire2) first, you can just find one same vert .
and this is the better one
The2VertAr=#()
for k in obj2VertAr do
(
for i=1 to obj1VertAr.count do
(
if (distance k obj1VertAr[i] < 0.01) do (append The2VertAr obj1VertAr[i])
)
)
point pos:The2VertAr[1] wirecolor:red
point pos:The2VertAr[2] wirecolor:Yellow
First of all, when you talk about “similar” floats (or any few floats — point2, point3, point4, color, matrix3, etc.), you should indicate how close they should be.
therefore, two floats (or doubles) in real life can simply be “close enough”. in other words, the “distance” between them is less than the specified tolerance.
“hash value” can only be used to search for exactly the same values.
Thanks denis for your participation
Frankly I didn’t understand what you’ve said
Would you give an example that my will not work and needs “hash value” .
Thanks. I should have mention that.
Here’s the example:
delete objects
shp1 = convertToSplineShape (Rectangle width:100 length:100)
shp2 = convertToSplineShape (Rectangle width:100 length:100 pos:[100,0,0])
move #( shp1, shp2 ) [ 1.654, 2.6465, 3.5641 ]
/*
-- uncomment to see how hash value comparison fails when position of first vert changes even slightly
p1 = getKnotPoint shp1 1 1
setKnotPoint shp1 1 1 (p1 + [ 0.005, 0, 0 ] )
updateShape shp1
*/
for i=1 to numKnots shp1 do
(
pt1 = getKnotPoint shp1 1 i
hash_value_1 = getHashValue pt1 0
for j = 1 to numKnots shp2 do
(
pt2 = getKnotPoint shp2 1 j
hash_value_2 = getHashValue pt2 0
format "knot:% hash:% knot:% hash:%\n" i hash_value_1 j hash_value_2
if distance pt1 pt2 < 0.01 then
(
format " Close verts: [ %, % ] Hashes match: %\n" i j (hash_value_1 == hash_value_2)
)
format "\n"
)
)
your naive algorithm checks all verts of one mesh against all verts of another which is slow and inefficient
to make it faster you’ll have to use some accelerating structure
little interactive example:
struct Lookup2DGrid
(
_minx = 1e6,
_miny = 1e6,
_maxx = -1e6,
_maxy = -1e6,
_min = [0,0,0],
_max = [0,0,0],
width,
height,
step,
size = [0,0],
points,
lookup2D,
fn init pts gridsize =
(
for p in pts where p != undefined do
(
if p.x < _minx then _minx = p.x else (if p.x > _maxx do _maxx = p.x)
if p.y < _miny then _miny = p.y else (if p.y > _maxy do _maxy = p.y)
)
_min = [ _minx, _miny, 0 ]
_max = [ _maxx, _maxy, 0 ]
points = pts
width = _maxx - _minx
height = _maxy - _miny
step = gridsize
size = [ceil (width / step) , ceil (height / step)]
lookup2D = for i=1 to size.x collect (for j=1 to size.y collect #())
for i=1 to pts.count where pts[i] != undefined do
(
index_x = 1 + int((pts[i].x - _minx)/step)
index_y = 1 + int((pts[i].y - _miny)/step)
append lookup2D[ index_x ][ index_y ] i
)
),
fn getNearestNeighbors pt offset:1 =
(
index_x = 1 + (floor((pt.x - _minx)/step))
index_y = 1 + (floor((pt.y - _miny)/step))
indexes = #()
for x = amax 1 (index_x-offset) to amin (index_x + offset) size.x do
(
for y = amax 1 (index_y-offset) to amin (index_y + offset) size.y do join indexes lookup2D[ x ][ y ]
)
indexes
),
fn getNearestIndex pt =
(
mind = 1e6
index = -1
for i in getNearestNeighbors pt where (d = distance pt points[i]) < mind do (mind = d; index = i)
index
),
fn getMinDistance pt =
(
mind = 1e6
indexes = getNearestNeighbors pt
if indexes.count == 0 do return -1
for i in indexes where (d = distance pt points[i]) < mind do mind = d
mind
)
)
delete objects
gc light:true
actionMan.executeAction 0 "551"
p = plane widthsegments:12 lengthsegments:12 wirecolor:black
convertToPoly p
rotate p (EulerAngles 0 0 23.5)
lg = Lookup2DGrid()
lg.init (for i=1 to polyop.getNumVerts p collect polyop.getVert p i) 2.0
move_me = point centermarker:on cross:off wirecolor:yellow isSelected:true
h2 = point wirecolor:red
deleteAllChangeHandlers id:#xxx
when transform move_me change id:#xxx val do
(
nearest_index = lg.getNearestIndex val.pos
if nearest_index > 0 do
(
h2.pos = lg.points[ nearest_index ]
)
)
btw. What’s the best way to find closest grid cell to arbitrary point in space?