POV-Ray : Newsgroups : povray.general : Trace()? : Re: Trace()? Server Time
7 Aug 2024 11:17:10 EDT (-0400)
  Re: Trace()?  
From: Mike Williams
Date: 22 Nov 2001 13:01:01
Message: <yceboGAMPH$7Ew7m@econym.demon.co.uk>
Wasn't it Mahalis who wrote:

>Could anyone explain to me exactly how one uses the trace() function to
>detect object collisions? The docs say that 'trace() can be used to detect
>the exact point a ray intersects a surface' and then gives a perfectly
>incomprehensible (to me at least) example.

It occurred to me that it ought to be possible to detect whether two
convex objects had collided by tracing in both directions along the line
that joins their centres.

Consider two convex objects that are not touching. As we look along the
line that joins their centres we encounter the significant points in the
following order:-
        Centre of object 1
        Surface of object 1
        Surface of object 2
        Centre of object 2

If the objects are moved closer so that they intersect, then the order
changes to
        Centre of object 1
        Surface of object 2
        Surface of object 1
        Centre of object 2

(With concave objects all bets are off. It's possible for two concave
objects to touch at the ends while there is still a gap between them
along the line that joins their centres).


I came up with code that looks like this

// trace object2 from the centre of object 1 and vice verca
#declare Surface2 = trace(Object2, Centre1, (Centre2-Centre1));
#declare Surface1 = trace(Object1, Centre2, (Centre1-Centre2));

// The objects intersect if Surface2 is nearer to Centre1
// than Surface1 is
#if (vlength(Surface2-Centre1) < vlength(Surface1-Centre1))
  #debug "They intersect\n"
#else
  #debug "They don't\n"
#end

But that code can sometimes give the wrong answer if the objects overlap
to such an extent that the centre of one lies inside the surface of the
other. For example, if the centres are very close the order might be
        Surface of Object 1
        Centre of Object 1
        Centre of Object 2
        Surface of Object 2
and the surfaces could be at any distance.



I think that this works

// trace object2 from the centre of object 1 and vice verca
#declare Surface2 = trace(Object2, Centre1, (Centre2-Centre1));
#declare Surface1 = trace(Object1, Centre2, (Centre1-Centre2));

// The objects intersect if the centre-centre distance
// is less than the sum of the centre-surface distances
#if ((vlength(Centre2-Centre1)  < (vlength(Surface1-Centre1) +     
     vlength(Surface2-Centre2)))) 
  #debug "They intersect\n"
#else
  #debug "They don't\n"
#end

-- 
Mike Williams
Gentleman of Leisure


Post a reply to this message

Copyright 2003-2023 Persistence of Vision Raytracer Pty. Ltd.