Notifications
Clear all

[Closed] Face intersection

Hi! I want to check, if 2 faces of different objects intersect with each other. There are plenty of functions for plane-plane intersection, but is there some function for finite plane? I could not find any

7 Replies

you can test to see if one of the edges of a tri (as a segment) intersects with a tri of the other object…

something like this may work

for all edges
create ray for edge
test ray against targ
if intersection
get distance from ray to intersection
if within edge/segment length
all tris sharing this edge intersect with targ tri

1 Reply
(@ryumaster)
Joined: 11 months ago

Posts: 0

But if I have two triangles like almost near eache other, almost parallel, but notintersecting,
the ray from one triangle edge will still intersect the other triangle during check.

Like, if I test ray against target, will it fail if they do not intersect? Probably not, then getting length later will not help, or I’ve missed something?

Ah, on seconds thought, I think there were formula to check if edge lies on some plane, maybe that will help after raycast, I just wonder if that is nice way to do it. Still will try to start from your suggestion plus that

if you test and get an intersection with the ray

get distance from ray start along the ray to intersection

if that lies within the segment (edge len) then you have what you are looking for.

fn getFaceIntersection objA objB =
(	
	cgrid = RayMeshGridIntersect();
	cgrid.initialize  10;
	cgrid.addNode objA;
	cgrid.buildGrid();

	objBfaces = #{};
	numfaces = objB.numfaces;
	for i = 1 to numfaces do
	(
		fverts = getface objB i;
		if cgrid.intersectSegment (getvert objB fverts.x) (getvert objB fverts.y) true > 0 then objBfaces[i] = true;
		if cgrid.intersectSegment (getvert objB fverts.y) (getvert objB fverts.z) true > 0 then objBfaces[i] = true;
		if cgrid.intersectSegment (getvert objB fverts.z) (getvert objB fverts.x) true > 0 then objBfaces[i] = true;

	)
	objB.selectedfaces = objBfaces;
	cgrid.free();
)	


(
	gs1 = geosphere radius:50 pos:[25,0,0]
	converttomesh gs1	
	gs2 = geosphere radius:50 pos:[-25,0,0]	
	converttomesh gs2
	
	getFaceIntersection gs1 gs2;
	getFaceIntersection gs2 gs1;
)

Thank you very much for the reply with this code! I was working entirely in different direction, but now I finally can do something productive by examining what solution you did came up with

it’s marginally quicker if you change the intersectSegment doubleside toggle to false with a grid size of 25.


  fn getFaceIntersection objA objB gridsize =
(	
	cgrid = RayMeshGridIntersect();
	cgrid.initialize  gridsize;
	cgrid.addNode objA;
	cgrid.buildGrid();

	intersectsegfn = cgrid.intersectSegment
	
	objBfaces = #{};
	numfaces = objB.numfaces;
	for i = 1 to numfaces do
	(
		fverts = getface objB i;
		a = getvert objB fverts.x;
		b = getvert objB fverts.y;
		c = getvert objB fverts.z;
		if intersectsegfn a b false > 0 then objBfaces[i] = true;
		if intersectsegfn b c false > 0 then objBfaces[i] = true;
		if intersectsegfn c a false > 0 then objBfaces[i] = true;
	)
	objB.selectedfaces = objBfaces;
	cgrid.free();
)	


(
	gs1 = geosphere radius:50 pos:[25,0,0] segs:8
	converttomesh gs1	
	gs2 = geosphere radius:50 pos:[-25,0,0]	segs:8
	converttomesh gs2
	
	start = timestamp()
	getFaceIntersection gs1 gs2 25;
	getFaceIntersection gs2 gs1 25;
	format "t:% 
" (timestamp() - start)
)

Yes, I have found that in docs already. Did not know such voxel grid method exists in 3ds max, so examining it carefully right now