00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "square.h"
00024 #include "common/math/point3.h"
00025 #include "common/math/real.h"
00026 #include "common/math/vector3.h"
00027 #include "context.h"
00028 #include "hit.h"
00029 #include "isurfaceshader.h"
00030 #include "ray.h"
00031 #include "scene.h"
00032 #include "settings.h"
00033 #include "statistics.h"
00034 #include "utilities.h"
00035
00036 #include <cmath>
00037
00038 using namespace sheep;
00039 using namespace std;
00040 using namespace toxic;
00041
00042 Square::Square(const Matrix4 &m,
00043 const ISurfaceShader *surface_shader,
00044 IntersectionMask intersection_mask ) :
00045 IAreaLight(m, surface_shader, intersection_mask),
00046 m_center(TransformToWorld(Point3(0.0))),
00047 m_normal(TransformNormalToWorld(Vector3(0.0, 1.0, 0.0))),
00048 m_basis(m_normal),
00049 m_ex(TransformToWorld(Vector3(1.0, 0.0, 0.0))),
00050 m_ez(TransformToWorld(Vector3(0.0, 0.0, 1.0)))
00051 {
00052 m_aabb = AABB3(Point3(-0.5, 0.0, -0.5), Point3(0.5, 0.0, 0.5)).Transform(m);
00053
00054
00055 m_aabb.Extend(OBJECT_AABB_EXTENSION);
00056 }
00057
00058 bool Square::Intersect(const Context &context,
00059 const Ray &ray,
00060 Hit *hit ) const
00061 {
00062
00063 if(!(m_intersection_mask & ray.GetType()))
00064 return false;
00065
00066
00067
00068 ++context.m_statistics->m_tested_intersections;
00069
00070 const Ray r = TransformToLocal(ray);
00071
00072 if(r.m_direction.m_y == 0.0)
00073 return false;
00074
00075 const Real t = - r.m_origin.m_y / r.m_direction.m_y;
00076
00077 if(t < 0.0)
00078 return false;
00079
00080 const Real x = r.m_origin.m_x + t * r.m_direction.m_x;
00081
00082 if(x < -0.5 || x > 0.5)
00083 return false;
00084
00085 const Real z = r.m_origin.m_z + t * r.m_direction.m_z;
00086
00087 if(z < -0.5 || z > 0.5)
00088 return false;
00089
00090 ++context.m_statistics->m_intersections_found;
00091
00092 if(hit) {
00093 hit->m_object = this;
00094 hit->m_abscissa = t;
00095 hit->m_geometric_normal = Vector3(0.0, 1.0, 0.0);
00096 hit->m_shading_normal = hit->m_geometric_normal;
00097 hit->m_u = 0.5 + x;
00098 hit->m_v = 0.5 + z;
00099 }
00100
00101 return true;
00102 }