POV-Ray : Newsgroups : povray.advanced-users : How does one test to see if a triangle's verticies are arranged in a clockwise or counter clockwise direction? : Re: How does one test to see if a triangle's verticies are arranged in a clockwise or counter clockwise direction? Server Time
29 Jul 2024 18:17:26 EDT (-0400)
  Re: How does one test to see if a triangle's verticies are arranged in a clockwise or counter clockwise direction?  
From: Tor Olav Kristensen
Date: 4 Jul 2002 16:05:57
Message: <3D24A919.B548913B@hotmail.com>
Warp wrote:
> 
> Tor Olav Kristensen <tor### [at] hotmailcom> wrote:
> > If one does not want the edges and vertices to count as
> > part of the triangle, then just replace the >= and <=
> > operators below with > and < operators.
> 
>   My suggestion was that if such case is detected, then the whole ray is
> discarded and another ray is shot to another direction. The reason being
> that it's easier to do that than to figure out whether the intersection
> should be counted or not (there are cases where it has to be counted and
> cases where it must not be counted). Making the wrong decision can result
> in the wrong result (since the result of the test is a yes/no answer,
> giving the wrong answer is catastrophical).

Ok, I think I understand now.

Then I propose something similar to the approach
in the macro below. It detects several cases.

But it could even be refined further:

E.g. it could detect whether the ray hits an edge
or a vertice, even if the ray origin lies in the
same plane as the triangle.

And it could be improved so that it takes care of
round off problems (in programming languages other
than POV-Ray SDL).

Note that this macro has not been tested very
thoroughly, but for me it seems to work ok.


Tor Olav


#macro RayIntersectsTriangle(pRay, vRay, pA, pB, pC)

  #local DegenTri = -2;
  #local InPlane  = -1;
  #local Outside  =  0;
  #local Edge     =  1;
  #local Vertice  =  2;
  #local Inside   =  3;
  #local vRA = pA - pRay;
  #local vRB = pB - pRay;
  #local vRC = pC - pRay;
  #local vABN = vcross(vRA, vRB);
  #local STP = vdot(vABN, vRC);
  #if (STP = 0)
    #if (vlength(vcross(pB - pA, pC - pA)) = 0)
      #local State = DegenTri;
    #else
      #local State = InPlane;
    #end // if
  #else
    #local vBCN = vcross(vRB, vRC);
    #local vCAN = vcross(vRC, vRA);
    #local AB = vdot(vRay, vABN);
    #local BC = vdot(vRay, vBCN);
    #local CA = vdot(vRay, vCAN);
    #if (STP > 0)
      #if (AB < 0 | BC < 0 | CA < 0)
        #local State = Outside;
      #else
        #if (AB > 0 & BC > 0 & CA > 0)
          #local State = Inside;
        #else
          #if ((CA = 0 & AB = 0) | (AB = 0 & BC = 0) | (BC = 0 & CA = 0))
            #local State = Vertice;
          #else
            #local State = Edge;
          #end // if
        #end // if
      #end // if
    #else
      #if (AB > 0 | BC > 0 | CA > 0)
        #local State = Outside;
      #else
        #if (AB < 0 & BC < 0 & CA < 0)
          #local State = Inside;
        #else
          #if ((CA = 0 & AB = 0) | (AB = 0 & BC = 0) | (BC = 0 & CA = 0))
            #local State = Vertice;
          #else
            #local State = Edge;
          #end // if
        #end // if
      #end // if
    #end // if
  #end // if
  #debug "Macro RayIntersectsTriangle: "
  #switch (State)
    #case (DegenTri)
      #debug "Degenerate triangle"
    #break
    #case (InPlane)
      #debug "Ray origin lies in triangle plane"
    #break
    #case (Outside)
      #debug "Ray does not hit triangle"
    #break
    #case (Edge)
      #debug "Ray hits an edge of triangle"
    #break
    #case (Vertice)
      #debug "Ray hits a vertice of triangle"
    #break
    #case (Inside)
      #debug "Ray hits inside triangle"
    #break
  #end // switch
  #debug "\n"

  State

#end // macro RayIntersectsTriangle


Post a reply to this message

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