summaryrefslogblamecommitdiff
path: root/hw2/include/triangle.h
blob: f7d85bf551e84a70ef0cfb0d984dde0f88b7cf2c (plain) (tree)


















































































































                                                                                                                                
/******************************************************************/
/* This file is part of the homework assignments for CSCI-427/527 */
/* at The College of William & Mary and authored by Pieter Peers. */
/* No part of this file, whether altered or in original form, can */
/* be distributed or used outside the context of CSCI-427/527     */
/* without consent of either the College of William & Mary or     */
/* Pieter Peers.                                                  */
/******************************************************************/
#ifndef _TRIANGLE_H_
#define _TRIANGLE_H_

#include <array>
#include <vector>
#include <memory>
#include <ostream>

#include "ray.h"
#include "vec2d.h"
#include "vec3d.h"
#include "boundingBox.h"

class triangle {
 public:
  //////////////////
  // Constructors //
  //////////////////
  triangle(void);
  triangle(const triangle& t);
  triangle(triangle&& t);

  triangle(const vec3d& v1, const vec3d& v2, const vec3d& v3);
  triangle(size_t v1_idx, size_t v2_idx, size_t v3_idx, const std::shared_ptr<const std::vector<vec3d>>& vertex_list);

  triangle(const vec3d& v1, const vec3d& v2, const vec3d& v3,
	   const vec3d& n1, const vec3d& n2, const vec3d& n3);
  triangle(size_t v1_idx, size_t v2_idx, size_t v3_idx, const std::shared_ptr<const std::vector<vec3d>>& vertex_list,
           size_t n1_idx, size_t n2_idx, size_t n3_idx, const std::shared_ptr<const std::vector<vec3d>>& normal_list);

  triangle(const vec3d& v1, const vec3d& v2, const vec3d& v3,
	   const vec2d& t1, const vec2d& t2, const vec2d& t3);
  triangle(size_t v1_idx, size_t v2_idx, size_t v3_idx, const std::shared_ptr<const std::vector<vec3d>>& vertex_list,
	   size_t t1_idx, size_t t2_idx, size_t t3_idx, const std::shared_ptr<const std::vector<vec2d>>& texcoord_list);

  triangle(const vec3d& v1, const vec3d& v2, const vec3d& v3,
	   const vec3d& n1, const vec3d& n2, const vec3d& n3,
	   const vec2d& t1, const vec2d& t2, const vec2d& t3);
  triangle(size_t v1_idx, size_t v2_idx, size_t v3_idx, const std::shared_ptr<const std::vector<vec3d>>& vertex_list,
	   size_t n1_idx, size_t n2_idx, size_t n3_idx, const std::shared_ptr<const std::vector<vec3d>>& normal_list,
	   size_t t1_idx, size_t t2_idx, size_t t3_idx, const std::shared_ptr<const std::vector<vec2d>>& texcoord_list);

  ////////////////
  // Inspectors //
  ////////////////
  const vec3d& vertex(size_t index) const;
  const vec3d& normal(size_t index) const;
  const vec2d& textureCoordinate(size_t index) const;

  bool hasPerVertexNormals(void) const;
  bool hasPerVertexTextureCoordinates(void) const;

  ///////////////
  // Operators //
  ///////////////
  triangle& operator=(const triangle& t);  
  triangle& operator=(triangle&& t); 

  /////////////
  // Methods //
  /////////////
  bool intersect(const ray& r, vec3d& barycentricCoord, float& t) const;

  boundingBox boundingbox(void) const;
  vec3d vertex(const vec3d& barycentricCoord) const;
  vec3d normal(void) const;
  vec3d shadingAxis(void) const;
  vec3d normal(const vec3d& barycentricCoord) const;
  vec2d textureCoordinate(const vec3d& barycentricCoord) const;

  vec3d sample(float r1, float r2, vec3d& barycentricCoord, float& pdf) const;
  float area(void) const;

  /////////////
  // Friends //
  /////////////
  friend void swap(triangle& a, triangle& b) { a._swap(b); }
  
  friend std::ostream& operator<<(std::ostream& s, const triangle& t)
  {
    s << "Triangle: v=(" << t.vertex(0)            << "," << t.vertex(1)            << "," << t.vertex(2)            << ")";
    if(t._normal_list) 
      s           << ", n=(" << t.normal(0)            << "," << t.normal(1)            << "," << t.normal(2)            << ")";
    if(t._textureCoord_list) 
      s           << ", t=(" << t.textureCoordinate(0) << "," << t.textureCoordinate(1) << "," << t.textureCoordinate(2) << ")";
    return s;
  }

private:
  /////////////////////
  // Private Methods //
  /////////////////////
  void _assign(const triangle& t);
  void _swap(triangle& t); 

  //////////////////
  // Data Members //
  //////////////////
  std::array<size_t, 3> _vertex_idx;
  std::array<size_t, 3> _normal_idx;
  std::array<size_t,3 > _textureCoord_idx;
  std::shared_ptr<const std::vector<vec3d>> _vertex_list;
  std::shared_ptr<const std::vector<vec3d>> _normal_list;
  std::shared_ptr<const std::vector<vec2d>> _textureCoord_list;
};

#endif /* _TRIANGLE_H_ */