CS 621 Contemporay Computer Graphics
Lecture Notes
Dr. Tong Yu, April, 2010
    1. Introduction
    2. Color and Lighting
    3. Ray Tracing
    4. Intersection Testing
    5. Animation
     
    6. Sky and Terrain Rendering
    7. Particle Systems
    8. 3D Movies I
    9. 3D Movies II
    10. Radiosity
    11. Scene Graphs

    Intersection Testing

    1. Ray-Surface Intersection

    2. Representing Lines and Planes

      In this section, vectors are expressed in bold while points are not.

      A line is defined by two points; it is infinite in length passing through the points and extending forever in both directions.

      A line segment ( segment for short ) is defined by two endpoints.

      A ray is semi-infinite; it is specified by a point and a direction.

      So, a line, a segment, and a ray all consist of points; in our notation, they should not be bold. ( Recall the homogeneous coordinate representation and affine combination of points. ) We use a parameter t to describe them ( parametric representation ).

      Suppose P1 and P2 are two points defining a line L(t). Let b = P2 - P1. Then

        L(t) = P1 + bt
      The line, ray, and segment are all represented by the same L(t) and differ parametrically only in the values of t that are relevant:
        segment:   0 ≤ t ≤ 1
        ray:   0 ≤ t ≤ ∞
        line:   -∞ < t < ∞
      P1 is often called the starting point of the ray.

        class Ray
        {
        private:
          Point3 origin;	//starting point
          Vector3 direction;	//vector
        public:
          Ray() : origin( Point3( 0, 0, 0 ) ), direction( Vector3( 0, 1, 0 ) ) {};
          Ray( Point3& an_origin, Vector3& a_direction );
          ....
        };
        	

    3. Ray-Plane Intersection

      As mentioned above, a ray is specified by its starting position O and a unit vector D and can be ragarded as a set of points given by

        L = O + tD     0 ≤ t < ∞  
      Note that the sum of a point and a vector is a point.
      We can talk about the line containing the ray, which can be referred to as ray-line.

      A plane is specified by a normal vector N perpendicular to the plane:

            ( P - P' ) ⋅ N = 0
        implies that
            (x - x')Nx + (y - y')Ny + (z - z')Nz = 0
        or
            ax + by + cz + d = 0
         
      Note that the difference between two points is a vector.
      Note also that N = ( a, b, c )

      Suppose P is the intersection of the line and the plane. Then
        0 = ( P - P' )N = ( O + tD - P') N

      Solving for t, we have

      	     ( P'  - O )N 
            t =  ---------------
      	         D⋅N
       

      • if D . N = 0, the ray L that contains P is parallel to the plane ( they don't intersect )
      • if D . N < 0, the ray is downward relative to the plane
      • if t < 0, the ray L does not intersect the plane
      Class Exercise ( 0.1 EC )
        A plane passes through the points P1 = (3, 4, 0), P2 = (4, 4, 0), and P3 = (5, 3, -1).
        Determine whether the ray that originates from O = (2, 1, 0) and passes through the point
        P0 = (1, 3, 0) will intersect with the plane. If yes, what is the intersection point?

    4. Ray-Slab Intersection

        L(t) = O + Dt
      	     ( P1' - O)N 
            t1 =  ---------------
      	         D⋅N
      	     ( P2' - O )N 
            t2 =  ---------------
      	         D⋅N

    5. Ray-Box Intersection

    6. Ray-Triangle Intersection

      • All surfaces can be approximated by triangles ( planar patches )
      • Triangle: ( v0, v1, v2 )
      • Plane containing triangle:
      • Let n = vector normal to the plane
      • d = n ⋅(p - O),     p is a point on the plane
      • n and d can be computed by
          N = ( v1 - v0 ) x ( v2 - v0 )
          n = N / |N|
          d = n ⋅(v0 - O) is the distance from the origin to the plane if n is normalized
      • Intersection point q is determined by ray-plane intersection test
      •  
      • Need to determine if q is inside or outside triangle
        Barycentric Coordinates

          P = S1P1 + S2P2 + S3P3

        Si, i = 1, 2, 3 are proportional to the areas of the corresponding subtriangles and

        S1 + S2 + S3 = 1
        If the area of the triangle is normalized to 1, so that Si becomes the area of the actual subtriangle, we have homogeneous Barycentric coordinates
        ( S1, S2, S3 ) are referred to as Barycentric coordinates of P

        Criteria for inside triangle:

          0 ≤ Si ≤ 1, i = 1, 2, 3

        So, if we know the barycentric coordinates of the hit point, we can accept or reject the ray with very simple tests: Point P is outside the triangle if one of the barycentric coordinates Si is smaller than zero

         

        Area of a polygon is

          n-1  
        A = ½ xi yi+1 - xi+1 yi
          i=0  
        where i+1 is taken mod n
        We can use this formula to determine S1, S2, and S3 or they can be calculated using the following methods.

        Suppose vertices P1, P2 and P3 form the triangle and ( α, β, γ ) are barycentric coordinates of point P:

        P = αP1 + βP2 + γP3

        Substituting with α = 1 - β - γ, we have

        β( P2 - P1 ) + γ( P3 - P1 ) = P - P1     ---   ( 1 )

        It is easier to solve if we project this in a 2D plane. ( Projecting both the triangle and the hit-point P onto another plane does not change the barycentric coordinates of P. After projection, all computations can be performed more efficiently in 2D. For example, we can project them into the XY plane. If we let c = (P2 - P1) , b = (P3 - P1), and h = P - P1. , we can rewrite (1) as

        βc + γb = h

        When projected onto the XY plane, we obtain the equations,

        βcx + γbx = hx

        βcy + γby = hy

        So we have two equations and two unknowns ( β, γ ) which can then be easily solved:
      	     bxhy - byhx
      	β = ------------ 
      	     bxcy - bycx
      	
      	     hxcy - hycx
      	γ = ------------ 
      	     bxcy - bycx
      	
        Implemenation:

        bool intersect_ray_triangle (  const Triangle triangle,  Ray &ray, double &t )
        {
          Vec3 v01 = triangle.p1 - triangle.p0;
          Vec3 v02 = triangle.p2 - triangle.p0;
          Vec3 normal = v01 ^ v02;		//normal to triangle
          Plane plane ( triangle.p0, normal );	//plane containing triangle
          bool hit_plane = intersect_ray_plane ( plane, ray, t );
          if ( !hit_plane ) return false;
        
          Point3 q = ray.getPoint( t );
        
          //check if q is inside triangle
          double bx, by, cx, cy, hx, hy;
          double beta, gamma;
          Vec3 b, c, h;
        
          c = v01;
          b = v02;
          h = q - triangle.p0;
         
          //find the dominant axis
          char axis;
          if ( fabs ( normal.x ) > fabs ( normal.y ) )
            if ( fabs ( normal.x ) > fabs ( normal.z ) )
        	axis = 'x';
            else
        	axis = 'z';
          else
            if ( fabs ( normal.y ) > fabs ( normal.z ) )
        	axis = 'y';
            else
        	axis = 'z';
          
          switch ( axis ) {
            case 'x':		//project on YZ plane
              bx = b.y;	by = b.z;
              cx = c.y; cy = c.z;
              hx = h.y; hy = h.z;
              break;
            case 'y':		//project on ZX plane
              bx = b.z;	by = b.x;
              cx = c.z; cy = c.x;
              hx = h.z; hy = h.x;
              break;
            case 'z':		//project on XY plane
              bx = b.x;	by = b.y;
              cx = c.x; cy = c.y;
              hx = h.x; hy = h.y;
              break;
          }
        
          double denominator =  bx * cy - by * cx;
          beta = ( bx * hy - by * hx ) / denominator;
          gamma = ( hx * cy - hy * cx ) / denominator;
        
          if ( beta < 0 ) return false;
          if ( gamma < 0 ) return false;
          if ( beta + gamma > 1 ) return false;
         
          return true;
        }
        	

        We may preprocess some values to speed up the process.

    7. Ray-Sphere Intersection

      Ray:   L(t) = O + tD
      Sphere:   ( P - C )2 - R2 = 0
      Intersect at L(t) = P:   ( O + tD - C )2 - R2 = 0
      Solving for t:   at2 + bt + c = 0
      a = D2
      b = 2(O - C)⋅D
      c = (O - C)2 - R2
      Solution:  
           -b ± √(b2 - 4ac)
      t = -----------------
      	   2a
      	
       

    8. Ray-Tapered Cylinder Intersection
      • Consider the side of the tapered cylinder as an infinitely long wall, with radius of 1 at z = 0 and a small radius of s at z = 1. Equation of wall: Implicit form: x2 + y2 - (1 + (s-1)z)2 = 0       for 0 < z < 1     --- ( 1 )

        If s = 1, it becomes the generic cylinder; if s = 0, it becomes the generic cone.

      • Figure a) A generic cyliner, b) A tapered cylinder

        Suppose ray A hits the wall twice; ray B enters through the cap and hits the wall once; ray C hits the wall once and exits through the base; ray D enters the base and exits through the cap
      • Suppose Ray is, L(t) = O + tD
      • Check if Ray hits Wall:
        • Substituting this into (1) for the intersection point, we obtain a quadratic equation of the form at2 + 2bt + c = 0 where a = Dx2 + Dy2 - d2
          b = OxDx + OyDy - Fd
          c = Ox2 + Oy2 - F2
          d = (s - 1)Dx
          F = 1 + (s - 1)Oz
        • Again, we use the discriminant "Det = (2b)2 - 4ac" to determine intersections:
        • If Det < 0, no intersection ( the ray passes by the cylinder )
        • If Det ≥ 0, ray hits the wall and thit can be found. To determine if the ray hits the cylinder wall, check if 0 ≤ z ≤ 1 at thit.
      • Check if Ray hits Base:
      • Apply Ray-plane intersection check with plane z = 0. Suppose Ray hits plane at point (x, y, 0); the hit spot lies within base if x2 + y2 < 1
      • Check if Ray hits Cap:
      • Apply Ray-plane intersection check with plane z = 1. Suppose Ray hits plane at point (x, y, 1); the hit spot lies within the cap if x2 + y2 < s2

    9. Ray-Quadric Intersection
      • A quadric is a surface in 3-space consisting of points satisfying a polynomial of degree 2: f(x, y, z) = Ax2 + By2 + Cz2 + Dxy + Exz + Fyz + Gx + Hy + Jz + K = 0

        e.g. spheres, cylinders, ellipsoids, paraboloids, hyperboloids, cones

      • Ray: (x(t), y(t), z(t)) = L(t) = O + tD Substituting this into the quadric equation at the point of intersection, we again obtain a quadratic equation of t: at2 + 2bt + c = 0 Solutions give us one or two thit, or no intersection if the discriminant < 0

      • The normal to the surface at the intersection point is given by the gradient: f
    10. Prunning Intersection Tests

    11. Enclose objects with bounding volume
      • intersection test with bounding volume can be simple
      • Examples:
        1. bounding spheres: sphere completely encloses object
        2. bounding boxes:
        1. AABB -- axis-aligned bounding box, edges parallel to x, y, z-axes ( Fig. b )
        2. OBBs -- oriented bounding box, arbitrary orientation ( Fig. c )
        3. k-DOP -- Discrete Oriented Polygon, a convex polytope bounded by k planes ( Fig. d, k = 3 )

    12. Partitioning space into regions
      • room or cell-based partitions
        good for situations where space is partitioned into rooms or regions, e.g. 3-D modeling of houses or buildings
      • quadrees or octtrees
        partition 2-space into hierarchically into square regions;
        root of quadtree is an-axis containing entire region, which is then split into four squares and so on
      • k-d ( k-dimensional )trees
        generalization of quadtrees
        a space-partitioning data structure for organizing points in a k-dimensional space
        divide a region into two subregions recursively
        only splitting planes that are perpendicular to one of the coordinate system axes
        void buildkdtree( Node* node )
        {
          if (stopcriterionmet()) return
          splitpos = findoptimalsplitposition()
          leftnode = new Node()
          rightnode = new Node()
          for (all primitives in node)
          {
            if (node->intersectleftnode()) leftnode->addprimitive( primitive )
            if (node->intersectrightnode()) rightnode->addprimitive( primitive )
          }
          buildkdtree( leftnode )
          buildkdtree( rightnode )
        }
        	

      • BSP ( Binary Space Partitioning ) trees
        a method for recursively subdividing a space into convex sets by hyperplanes
        generalization of kd trees by allowing partitioning by arbitrary plane

        G becomes a leaf as it is convex