Arty
cameras.h
1 #ifndef CAMERA_H
2 #define CAMERA_H
3 
4 #include "float3.h"
5 #include "float2.h"
6 #include "intersect.h"
7 
9 struct CameraGeometry {
10  float cos;
11  float dist;
12  float area;
13  CameraGeometry() {}
14  CameraGeometry(float c, float d, float a)
15  : cos(c), dist(d), area(a)
16  {}
17 };
18 
20 class Camera {
21 public:
22  virtual ~Camera() {}
24  virtual Ray gen_ray(float u, float v) const = 0;
26  virtual float3 project(const float3& p) const = 0;
28  virtual float3 unproject(const float3& p) const = 0;
30  virtual CameraGeometry geometry(float u, float v) const = 0;
32  virtual void mouse_motion(float x, float y) = 0;
34  virtual void keyboard_motion(float x, float y, float z) = 0;
35 };
36 
39 class PerspectiveCamera : public Camera {
40 public:
41  PerspectiveCamera(const float3& e, const float3& c, const float3& u, float fov, float ratio) {
42  eye = e;
43  dir = normalize(c - e);
44  right = normalize(cross(dir, u));
45  up = normalize(cross(right, dir));
46 
47  w = std::tan(fov * pi / 360.0f);
48  h = w / ratio;
49  right *= w;
50  up *= h;
51  }
52 
53  Ray gen_ray(float u, float v) const override final {
54  return Ray(eye, normalize(dir + u * right + v * up));
55  }
56 
57  float3 project(const float3& p) const override final {
58  auto d = normalize(p - eye);
59  return float3(dot(d, right) / (w * w), dot(d, up) / (h * h), dot(d, dir));
60  }
61 
62  float3 unproject(const float3&) const override final {
63  return eye;
64  }
65 
66  CameraGeometry geometry(float u, float v) const override final {
67  float d = std::sqrt(1.0f + u * u * w * w + v * v * h * h);
68  return CameraGeometry(1.0f / d, d, 1.0f / (4.0f * w * h));
69  }
70 
71  void mouse_motion(float x, float y) override final {
72  dir = rotate(dir, right, -y);
73  dir = rotate(dir, up, -x);
74  dir = normalize(dir);
75  right = normalize(cross(dir, up));
76  up = normalize(cross(right, dir));
77 
78  right *= w;
79  up *= h;
80  }
81 
82  void keyboard_motion(float x, float y, float z) override final {
83  eye += dir * z + right * x + up * y;
84  }
85 
86 private:
87  float3 eye;
88  float3 dir;
89  float3 up;
90  float3 right;
91  float w, h;
92  float area;
93 };
94 
95 #endif // CAMERA_H
void keyboard_motion(float x, float y, float z) override final
Updates the camera after keyboard input.
Definition: cameras.h:82
Definition: float3.h:10
Definition: cameras.h:39
Ray gen_ray(float u, float v) const override final
Generates a ray for a point on the image plane, represented by (u, v) in [-1,1]^2.
Definition: cameras.h:53
float cos
Cosine between the local camera direction and the image plane normal.
Definition: cameras.h:10
float area
Local pixel area divided by total area.
Definition: cameras.h:12
float dist
Distance between the camera and the point on the image plane.
Definition: cameras.h:11
void mouse_motion(float x, float y) override final
Updates the camera after mouse input.
Definition: cameras.h:71
float3 project(const float3 &p) const override final
Projects a point onto the image plane and returns the corresponding (u, v, z) coordinates.
Definition: cameras.h:57
CameraGeometry geometry(float u, float v) const override final
Returns the geometry at a given point on the image plane.
Definition: cameras.h:66
Structure that holds the local geometry information on a camera lens.
Definition: cameras.h:9
Ray defined as org + t * dir, with t in [tmin, tmax].
Definition: intersect.h:11
float3 unproject(const float3 &) const override final
Unprojects a point on the image plane, represented by (u, v, z) with (u, v) in [-z, z]^2 and z in [0, inf[.
Definition: cameras.h:62
Base class for cameras.
Definition: cameras.h:20