summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt4
-rw-r--r--hitlist.h29
-rw-r--r--material_dielectric.cpp3
-rw-r--r--material_diffusive.cpp4
-rw-r--r--material_reflective.cpp23
-rw-r--r--tracelog.h17
-rw-r--r--vec.h3
-rw-r--r--viewport.h15
8 files changed, 74 insertions, 24 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index a197031..fc3e6f3 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -12,9 +12,9 @@ set(CMAKE_VERBOSE_MAKEFILE on)
# main executable
-add_executable(rt main.cpp vec.h bitmap.h ray.h bitfont.h hitlist.h object.h sphere.h viewport.h aa.h material.h material_diffusive.h material_diffusive.cpp material_reflective.h material_reflective.cpp material_dielectric.cpp material_dielectric.h)
+add_executable(rt main.cpp vec.h bitmap.h ray.h bitfont.h hitlist.h object.h sphere.h viewport.h aa.h material.h material_diffusive.h material_diffusive.cpp material_reflective.h material_reflective.cpp material_dielectric.cpp material_dielectric.h tracelog.h)
add_executable(image_output main_image_output.cpp vec.h bitmap.h bitfont.h hitlist.h object.h sphere.h viewport.h)
-add_executable(simple_scanner main_simple_scanner.cpp vec.h bitmap.h ray.h timer.h bitfont.h hitlist.h object.h sphere.h viewport.h aa.h material.h material_diffusive.h material_diffusive.cpp material_reflective.h material_reflective.cpp material_dielectric.cpp material_dielectric.h)
+add_executable(simple_scanner main_simple_scanner.cpp vec.h bitmap.h ray.h timer.h bitfont.h hitlist.h object.h sphere.h viewport.h aa.h material.h material_diffusive.h material_diffusive.cpp material_reflective.h material_reflective.cpp material_dielectric.cpp material_dielectric.h tracelog.h)
# googletest
diff --git a/hitlist.h b/hitlist.h
index 1ad040a..ab9cca3 100644
--- a/hitlist.h
+++ b/hitlist.h
@@ -11,6 +11,7 @@
#include "ray.h"
#include "vec.h"
#include "object.h"
+#include "tracelog.h"
#include <cstdlib>
#include <memory>
#include <limits>
@@ -22,15 +23,6 @@
//#define T_NORM_VISUAL
#define T_DIFFUSE
-// log ray traces to stderr
-//#define LOG_TRACE
-
-#ifdef LOG_TRACE
-#define TRACELOG(...) (fprintf(stderr, __VA_ARGS__))
-#else
-#define TRACELOG(...)
-#endif
-
// A world, T is color depth
class hitlist {
std::vector<std::shared_ptr<object>> objects;
@@ -50,9 +42,10 @@ public:
pixel<T> color(ray3d r, random_uv_gen_3d &ruvg, uint_fast32_t max_recursion_depth = 64) const {
assert(r.decay().is_one());
TRACELOG("+++ start tracing (limit=%zu)\n", max_recursion_depth);
- TRACELOG(" ray: [%10f,%10f,%10f], decay=[%10f,%10f,%10f]\n",
+ TRACELOG(" ray: [%-10f,%-10f,%-10f], decay=[%-10f,%-10f,%-10f]\n",
r.direction().x, r.direction().y, r.direction().z, r.decay().x, r.decay().y, r.decay().z);
while (max_recursion_depth-- > 0) {
+ TRACELOG(" step start (remaining: %lu)\n", max_recursion_depth + 1);
// Detect hits
bool hit = false;
double hit_t = std::numeric_limits<double>::infinity();
@@ -77,7 +70,8 @@ public:
#ifdef LOG_TRACE
const auto _hit_p_ = r.at(hit_t);
const auto _rn_ = dot(r.direction(), hit_obj->normal_vector(_hit_p_));
- TRACELOG(" hit object <%p> at [%10f,%10f,%10f], t=%10f, surface=%10f (%s)\n",
+ TRACELOG(" hit object %s <%p> at [%-10f,%-10f,%-10f], t=%-10f, surface=%-10f (%s)\n",
+ typeid(*hit_obj).name(),
hit_obj.get(), _hit_p_.x, _hit_p_.y, _hit_p_.z,
hit_t, _rn_, (_rn_ < 0) ? "outside" : "inside");
#endif
@@ -94,7 +88,7 @@ public:
#ifdef T_DIFFUSE
const auto &materi = hit_obj->material();
if (materi.scatter(r, *hit_obj, hit_t, ruvg)) {
- TRACELOG(" scattered: [%10f,%10f,%10f], decay=[%10f,%10f,%10f]\n",
+ TRACELOG(" scattered ray: [%-10f,%-10f,%-10f], decay=[%-10f,%-10f,%-10f]\n",
r.direction().x, r.direction().y, r.direction().z,
r.decay().x, r.decay().y, r.decay().z);
continue; // The ray is scatted by an object. Continue processing the scattered ray.
@@ -105,6 +99,7 @@ public:
#endif
}
+ TRACELOG(" hit infinity (light source)\n");
// Does not hit anything. Get background color (infinity)
const auto u = (r.direction().y + 1.0) * 0.5;
const auto c = mix(
@@ -113,19 +108,15 @@ public:
1.0 - u,
u
);
+
+ TRACELOG("--- finish (hit infinity)\n");
#ifdef T_DIFFUSE
-#ifdef LOG_TRACE
- const auto co = pixel8b::from(r.hit(c));
- TRACELOG(" result: [%d, %d, %d]\n", co.r, co.g, co.b);
- TRACELOG("--- finish (reached infinity)\n");
-#endif
return r.hit(c);
#else
- TRACELOG("--- finish (hit)\n");
return c;
#endif
}
- TRACELOG("--- finish (max search depth)\n");
+ TRACELOG("--- finish (trace step limit reached) [XX]\n");
return pixel<T>::black(); // reached recursion time limit, very little light
}
};
diff --git a/material_dielectric.cpp b/material_dielectric.cpp
index ed8e4eb..61e34ec 100644
--- a/material_dielectric.cpp
+++ b/material_dielectric.cpp
@@ -3,6 +3,7 @@
//
#include "material_dielectric.h"
+#include "tracelog.h"
bool material_dielectric::scatter(ray3d &r, const object &hit_obj, double hit_t, random_uv_gen_3d &ruvg) const {
const auto hit_p = r.at(hit_t);
@@ -22,9 +23,11 @@ bool material_dielectric::scatter(ray3d &r, const object &hit_obj, double hit_t,
// determine reflection or refraction using Schlick's Approximation.
if (reflectance(cos1, ri_) > ruvg.range01_scalar()) {
// reflect
+ TRACELOG(" reflect (dielectric material, schlick, ri=%-10f)\n", ri_);
r2 = n.reflect(r.direction());
} else {
// refract
+ TRACELOG(" refract (dielectric material, schlick, ri=%-10f)\n", ri_);
r2 = n.refract<true>(r.direction(), ri_);
}
r.direction(r2.unit_vec());
diff --git a/material_diffusive.cpp b/material_diffusive.cpp
index b3f0207..58c9c45 100644
--- a/material_diffusive.cpp
+++ b/material_diffusive.cpp
@@ -4,6 +4,7 @@
#include "vec.h"
#include "material_diffusive.h"
+#include "tracelog.h"
bool material_diffuse_lambertian::scatter(ray3d &r, const object &hit_obj, double hit_t, random_uv_gen_3d &ruvg) const {
@@ -16,6 +17,7 @@ bool material_diffuse_lambertian::scatter(ray3d &r, const object &hit_obj, doubl
r.decay(albedo); // lose some light when diffused
r.source(hit_point);
r.direction((diffuse_target - hit_point).unit_vec()); // the new diffused ray we trace on
+ TRACELOG(" reflected (diffusive, lambertian material)\n");
return true;
}
@@ -52,6 +54,7 @@ bool material_diffuse_simple::scatter(ray3d &r, const object &hit_obj, double hi
r.decay(albedo); // lose some light when diffused
r.source(hit_point);
r.direction((diffuse_target - hit_point).unit_vec()); // the new diffused ray we trace on
+ TRACELOG(" reflected (diffusive, simple material)\n");
return true;
}
@@ -80,6 +83,7 @@ material_diffuse_hemispherical::scatter(ray3d &r, const object &hit_obj, double
r.decay(albedo); // lose some light when diffused
r.source(hit_point);
r.direction((diffuse_target - hit_point).unit_vec()); // the new diffused ray we trace on
+ TRACELOG(" reflected (diffusive, hemispherical material)\n");
return true;
}
diff --git a/material_reflective.cpp b/material_reflective.cpp
index aa0d361..6cffcf3 100644
--- a/material_reflective.cpp
+++ b/material_reflective.cpp
@@ -5,6 +5,7 @@
#include "vec.h"
#include "material.h"
#include "material_reflective.h"
+#include "tracelog.h"
// perfectly-smooth reflective
template<>
@@ -15,7 +16,16 @@ bool material_reflective_<false>::scatter(ray3d &r, const object &hit_obj, doubl
r.source(hit_point);
r.direction(reflected);
r.decay(albedo);
- return dot(reflected, nv) > 0;
+ const auto alive = dot(reflected, nv) > 0;
+#ifdef LOG_TRACE
+ if (!alive) {
+ TRACELOG(" absorbed (perfectly smooth material) (reflected: [%-10f,%-10f,%-10f], nv: [%-10f,%-10f,%-10f])\n",
+ reflected.x, reflected.y, reflected.z, nv.x, nv.y, nv.z);
+ } else {
+ TRACELOG(" reflected (perfectly smooth material)\n");
+ }
+#endif
+ return alive;
}
// fuzzy reflective
@@ -27,5 +37,14 @@ bool material_reflective_<true>::scatter(ray3d &r, const object &hit_obj, double
r.source(hit_point);
r.direction(reflected.unit_vec());
r.decay(albedo);
- return dot(reflected, nv) > 0;
+ const auto alive = dot(reflected, nv) > 0;
+#ifdef LOG_TRACE
+ if (!alive) {
+ TRACELOG(" absorbed (fuzzy reflective material) (reflected: [%-10f,%-10f,%-10f], nv: [%-10f,%-10f,%-10f])\n",
+ reflected.x, reflected.y, reflected.z, nv.x, nv.y, nv.z);
+ } else {
+ TRACELOG(" reflected (fuzzy reflective material)\n");
+ }
+#endif
+ return alive;
} \ No newline at end of file
diff --git a/tracelog.h b/tracelog.h
new file mode 100644
index 0000000..cee85d4
--- /dev/null
+++ b/tracelog.h
@@ -0,0 +1,17 @@
+//
+// Created by Keuin on 2022/4/16.
+//
+
+#ifndef RT_TRACELOG_H
+#define RT_TRACELOG_H
+
+// log ray traces to stderr
+//#define LOG_TRACE
+
+#ifdef LOG_TRACE
+#define TRACELOG(...) (fprintf(stderr, __VA_ARGS__))
+#else
+#define TRACELOG(...)
+#endif
+
+#endif //RT_TRACELOG_H
diff --git a/vec.h b/vec.h
index d2dece0..e3e15b8 100644
--- a/vec.h
+++ b/vec.h
@@ -10,6 +10,7 @@
#include <ostream>
#include <cassert>
#include <algorithm>
+#include "tracelog.h"
static inline bool eq(int a, int b) {
return a == b;
@@ -134,8 +135,10 @@ struct vec3 {
// TODO test TIR
if (Enable_TIR) {
// ri_inv < sin(a1), cannot refract, must reflect (Total Internal Reflection)
+ TRACELOG(" reflect (TIR, d=%f)\n", d);
return reflect(r1);
} else {
+ TRACELOG(" refract (forced, d=%f)\n", d);
d = -d; // abs, just make the sqrt has a real solution
}
}
diff --git a/viewport.h b/viewport.h
index 85d17f5..2924582 100644
--- a/viewport.h
+++ b/viewport.h
@@ -10,6 +10,7 @@
#include "ray.h"
#include "vec.h"
#include "hitlist.h"
+#include "tracelog.h"
#include <cstdlib>
#include <memory>
#include <limits>
@@ -97,7 +98,19 @@ public:
const auto dir = r + off; // direction vector from camera to current pixel on screen
ray3d ray{viewpoint, dir}; // from camera to pixel (on the viewport)
const auto pixel = world.color<T>(ray, ruvg);
- image.set(i + img_hw, -j + img_hh, pixel);
+ const auto x_ = i + img_hw, y_ = -j + img_hh;
+ image.set(x_, y_, pixel);
+
+#ifdef LOG_TRACE
+ const auto ret = pixel;
+ const auto ret8b = pixel8b::from(ret);
+ const auto ret8bg2 = pixel8b::from(ret.gamma2());
+ TRACELOG(" ^ apply to pixel: (%d, %d), color: [%f, %f, %f] (8bit: [%d, %d, %d], 8bit-gamma2: [%d, %d, %d])\n",
+ x_, y_,
+ (double) ret.r, (double) ret.g, (double) ret.b,
+ ret8b.r, ret8b.g, ret8b.b,
+ ret8bg2.r, ret8bg2.g, ret8bg2.b);
+#endif
}
}
return image;