|
![](/i/fill.gif) |
Warp wrote:
>...
> And I can believe that there could be a shortcut to see if a line
> intersects a triangle. It's just too complicated for me to think being
> this tired (and lazy) :)
I think that my RayIntersectsTriangle() macro in the code below
provides such a shortcut (*), but I'm not sure yet if it is optimal.
(*) Not really for lines, but for rays (which has a defined direction)
Tor Olav
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
// Copyright 2002 by Tor Olav Kristensen
// Email: tor### [at] hotmail com
// http://www.crosswinds.net/~tok/povray
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
#version 3.5;
#include "colors.inc"
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
// Intersection macros
#macro RayIntersectsTriangle(pRay, vRay, pA, pB, pC)
#local vRA = pA - pRay;
#local vRB = pB - pRay;
#local vRC = pC - pRay;
#local vABN = vcross(vRA, vRB);
#local vBCN = vcross(vRB, vRC);
#local vCAN = vcross(vRC, vRA);
#local STP = vdot(vABN, vRC);
#if (STP = 0)
#debug "Macro RayIntersectsTriangle: "
#debug "Degenerate triangle or "
#debug "origin of ray lies in same plane as triangle\n"
#local Intersect = false;
#else
#local AB = vdot(vRay, vABN);
#local BC = vdot(vRay, vBCN);
#local CA = vdot(vRay, vCAN);
#if (AB = 0 | BC = 0 | CA = 0)
#local Intersect = true; // Intersection at one or two edges
#else
#if (STP > 0)
#local Intersect = (AB > 0 & BC > 0 & CA > 0);
#else
#local Intersect = (AB < 0 & BC < 0 & CA < 0);
#end // if
#end // if
#end // if
Intersect
#end // macro RayIntersectsTriangle
#macro LinePlaneIntersection(pLine, vLine, pPlane, vPlane)
(pLine + vLine*vdot(pPlane - pLine, vPlane)/vdot(vLine, vPlane))
#end // macro LinePlaneIntersection
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
// Set up and show triangle
#declare p0 = <1, 3, -2>;
#declare p1 = <2, -3, 3>;
#declare p2 = <-2, 1, -3>;
triangle {
p0, p1, p2
pigment { color rgbf <1, 1, 0, 0.2> }
}
union {
sphere { p0, 0.03 }
sphere { p1, 0.03 }
sphere { p2, 0.03 }
pigment { color Magenta*2 }
}
union {
cylinder { p0, p1, 0.02 }
cylinder { p1, p2, 0.02 }
cylinder { p2, p0, 0.02 }
pigment { color Cyan*2 }
}
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
// Shoot some random rays and highlight those that hits the triangle
#declare R = 4;
#declare S = seed(5);
#declare Cnt = 0;
#while (Cnt < 150)
#declare pR = (<1, 1, 1> - 2*<rand(S), rand(S), rand(S)>)*R;
#declare vR = (<1, 1, 1> - 2*<rand(S), rand(S), rand(S)>);
#if (vlength(vR) > 0)
sphere {
pR, 0.04
pigment { color Green*2 }
}
cylinder {
pR, pR + 100*vnormalize(vR), 0.02
pigment { color White }
}
#if (RayIntersectsTriangle(pR, vR, p0, p1, p2))
#local vPlaneNormal = vcross(p1 - p0, p2 - p0);
#local pIntersect =
LinePlaneIntersection(pR, vR, p0, vPlaneNormal);
cylinder {
pR, pIntersect, 0.021
pigment { color White*4 }
}
sphere {
pIntersect, 0.06
pigment { color Red*2 }
}
#end // if
#end // if
#declare Cnt = Cnt + 1;
#end // while
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
background { color Blue/2 }
light_source {
<1, 1, -3>*100 color White
shadowless
}
camera {
location -10*z
look_at <0, 0, 0>
}
// ===== 1 ======= 2 ======= 3 ======= 4 ======= 5 ======= 6 ======= 7
Post a reply to this message
|
![](/i/fill.gif) |