[Closed] Testing for intersection of objects
Hi,
I’m trying to create a test script for use with PFlow to qualify particles that intersect with another object.
The solution I tried was using the “boolObj” class to intersact two objects and then test if I get a legal result, but MaxScript allowes you to intersect objects even when they dont intersect.
Thanks
Eran
One way might be to test for the intersection of the bounding spheres of your two objects, something like:
pPos = particle position
oPos = obj.center
oRad = distance obj.max obj.center
if (distance oPos pPos) > oRad then intersect = false else intersect = true
[font=Arial][font=Verdana]Hi Moosley,
That’s a good and simple solution, but I’m trying to get an exact intersection (not just a sphere) .
Another possiable solution would be to start and use the “Ray” class & calculations, but that’s getting a bit too complicated.
I think a more elegant way would be to use the boolObj existing functionality. The question is just, how ??
Thanks
Eran
[/font][/font]
I remember me another solution proposed by BOBO. That isn’t specifically for particles but that will give you an idea.
You create a boolean operation between the 2 objects (union).
If there are points then there is an intersection.
Sorry but I can’t found the threath…
Hey Eran,
I had to do something like this recently… testing if particles were within a certain threshold distance from some specific geometry. I used rays shot from the particle position, and if a collision was within the spherical threshold, pass true, else pass false. Here is a sample script that will generate vectors from a central point (the particle):
(
fn makeCones vectorArray =
for x in vectorArray do
(
theCyl = cylinder heightsegs:1 sides:3 height:1 radius:.02
theCyl.rotation.controller = lookat_constraint()
theCyl.rotation.controller.appendtarget x 100
theCyl.rotation.controller.target_axis = 2
theCyl.rotation.controller.upnode_axis = 1
theCyl.rotation.controller.StoUP_axis = 1
theCyl.rotation.controller.lookat_vector_length = 0
theCyl.wirecolor = white
x.radius *= 2
theCyl.material = x.material = meditmaterials[2]
)
local iterations = 5 --2 to 10 spinner range
local segLength = 360 / (iterations * 2)
local origLength = segLength
local theVectors = #()
local theColor = [0,0,0]
/*
This method of ray distribution first creates a cylindrical array of vectors,
and translates them into a spherical array surrounding a point (the particle) with the radius
equaling the unit length. It provides more ray detection horizontally than
vertically.
In the function below, spheres are appended to theVectors array, which is
obviously unnecessary in practice. You will want to adapt this script to
only append the vectors derived from the function. This script is for
visualization purposes only.
*/
local polN = sphere pos:[0,0,1] radius:.025 wirecolor:red
local polS = sphere pos:[0,0,-1] radius:.025 wirecolor:red
append theVectors polN
append theVectors polS
for i = 1 to iterations do
(
for x = 1 to (iterations * 2) do
(
offset = [0,0,(((i - .5) / iterations) - .5) * 2]
theVector = [(cos segLength),(sin segLength),offset.z]
sphereDist = (distance theVector offset) - (sqrt (1 - (pow offset.z 2)))
local theSphere = sphere pos:(((normalize (theVector - offset)) * sphereDist) - theVector) radius:.025 wirecolor:theColor
segLength += origLength
append theVectors theSphere
)
theColor = [(random 1 255),(random 1 255),(random 1 255)]
)
makeCones theVectors
)
There’s a small article about it on my website. The ray distribution method above casts more rays laterally than at the poles. Like you said, this method gets a bit hairy if you need very high samples, and is something that MXS isn’t cut out to perform very optimally at. If you can get the kind of intersection you need another way, I’d recommend that, but if you can’t, this is one method to cast rays spherically.
arketip,
The boolean operation was the initial idea. Can you be more specific about the points idea.
I tried to see if there’s a difference in the objects properties (pivot, widtg, etc) before and after the boolean intersection, but no luck.
d3coy,
I’m leaving all this ray stuff as a last resort since I’m totally new to Maxscript (not to cooding in general) so I’m still trying to find a simple solution.
Here is the concept:
(
local theObject = box width:100 height:100 length:100
local theParticule = sphere pos:[50,0,0] radius:10.0 segs:8
local nVertsBefore = theParticule.mesh.numVerts
local nVertsAfter = (theParticule-theObject).numverts
max views redraw
if nVertsBefore!=nVertsAfter
then messageBox ("There is an Intersection")
else messageBox ("NO Intersection")
)
You have just to create a geometry for your particle. A sphere seems the best idea but I am not familiar with particles. There is maybe a means to obtain the geometry (?).
In theory, there is a possibility that the number of points stays the same after the operation.
This approach may have some problems during rendering. At render time you are not allowed to generate new objects – it is asking for a crash to happen.
Thanks,
Oleg B.
Thanks arketip,
This solution works great with Primitives, but I can’t make it work with an extruded editable Spile even when I convert it to editable mesh.
Any ideas ?
Your extruded spline don’t have any volume, isn’t ?
Then a boolean operation is not appropriate in this situation. Specially the boolean of 3dsmax because that doesn’t work very well with many flat shapes.
I suppose you want a collision that does work with volumes AND with flat shapes… Not easy.
You will have to detect the colision for the volumes and for the flat shapes…
and the combinaisons:
volume & volume
volume & shape
shape & shape
That seems a bit complicate.
There is no means of simplifying your problem ?