aboutsummaryrefslogtreecommitdiff
path: root/ray.c
diff options
context:
space:
mode:
authorJulian T <julian@jtle.dk>2020-03-26 21:47:51 +0100
committerJulian T <julian@jtle.dk>2020-03-26 21:47:51 +0100
commita9651189ac52139c374f97a311d090a8d95b957e (patch)
treefc6fd39fd4bcb4afd0214f145bd287958cf88618 /ray.c
parentcdfd399ea9d79dcfac3107b23cbab7b25c7a12e0 (diff)
MOved hemisphere transformation stuff out of ray.c
Diffstat (limited to 'ray.c')
-rw-r--r--ray.c69
1 files changed, 40 insertions, 29 deletions
diff --git a/ray.c b/ray.c
index 465b154..3932f23 100644
--- a/ray.c
+++ b/ray.c
@@ -1,7 +1,9 @@
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
+#include <assert.h>
#include "vector.h"
+#include "ctranslate.h"
#include "ray.h"
@@ -186,7 +188,35 @@ static void contribution_from_pointlight(space_t *s, color_t *dest, object_t *o,
reflected_at(o, dest, light, d, point, &l, V, N);
}
-static void direct_light(space_t *s, color_t *dest, object_t *o, vector_t *N, vector_t *eye, vector_t *point)
+// Many of these can maybe be put in a context struct
+static void contribution_from_arealight(space_t *s, color_t *dest, object_t *o, light_t *light, vector_t *point, vector_t *V, vector_t *N, void *seed)
+{
+ // This only works with spheres
+ assert(o->type == TYPE_SPHERE);
+
+ // Color to collect temporary results in
+ color_t c;
+
+ ray_t ray;
+ ray.start = point;
+
+ // Do the same monte carlo as with environment but the starting point is the center of the circle.
+ // And the result is a point on the circle
+ for (int i = 0; i < 16; i++) {
+ // Do the monte carlo random distribution thing from the article
+ COORD_T r1 = ray_rand(seed);
+ COORD_T r2 = ray_rand(seed);
+
+ COORD_T sinTheta = sqrt(1 - r1 * r1);
+ COORD_T phi = 2 * PI * r2;
+
+ // Cast a ray
+
+ }
+
+}
+
+static void direct_light(space_t *s, color_t *dest, object_t *o, vector_t *N, vector_t *eye, vector_t *point, void *seed)
{
// And vector towards viewer
vector_t V;
@@ -209,21 +239,9 @@ static void direct_light(space_t *s, color_t *dest, object_t *o, vector_t *N, ve
// https://www.scratchapixel.com/lessons/3d-basic-rendering/global-illumination-path-tracing/global-illumination-path-tracing-practical-implementation
static void env_light(space_t *s, color_t *dest, object_t *o, vector_t *N, vector_t *point, void *seed)
{
- // Create new coordinate system where N is up. To do this we need two more vectors for the other axises.
- // Create the 2. by setting x or y to 0
- vector_t Nt;
- if (N->x > N->y) {
- vector_set(&Nt, N->z, 0, -N->x);
- } else {
- vector_set(&Nt, 0, -N->z, N->y);
- }
- // Normalice
- vector_scale_inv(&Nt, &Nt, vector_len(&Nt));
-
- // Create the 3. axis by taking the cross of the other
- vector_t Nb;
- vector_cross(&Nb, N, &Nt);
-
+ csystem_t cs;
+ csystem_init(&cs, N);
+
// Prepare ray
ray_t r;
r.start = point;
@@ -233,21 +251,14 @@ static void env_light(space_t *s, color_t *dest, object_t *o, vector_t *N, vecto
color_set(&acc, 0, 0, 0);
for (unsigned i = 0; i < s->env_samples; i++) {
- // Do the monte carlo random distribution thing from the article
COORD_T r1 = ray_rand(seed);
- COORD_T r2 = ray_rand(seed);
-
- COORD_T sinTheta = sqrt(1 - r1 * r1);
- COORD_T phi = 2 * PI * r2;
-
+ //
// Calculate the random direction vector
vector_t randdir;
- vector_set(&randdir, sinTheta * cos(phi), r1, sinTheta * sin(phi));
+ csystem_hemisphere_random(&cs, r1, ray_rand(seed), &randdir);
// Convert to world cordinates using the calculated N vectors.
- vector_set(&randdir, randdir.x * Nb.x + randdir.y * N->x + randdir.z * Nt.x,
- randdir.x * Nb.y + randdir.y * N->y + randdir.z * Nt.y,
- randdir.x * Nb.z + randdir.y * N->z + randdir.z * Nt.z);
+ csystem_calc_real(&cs, &randdir, &randdir);
// Check the direction for obstacles
r.direction = &randdir;
@@ -261,7 +272,7 @@ static void env_light(space_t *s, color_t *dest, object_t *o, vector_t *N, vecto
color_t tmp;
color_scale(&tmp, &s->env_color, r1);
- acc.r += tmp.r; acc.g += tmp.g; acc.b += tmp.b;
+ color_add(&acc, &acc, &tmp);
}
// Devide by number of samples and pdf
@@ -285,7 +296,7 @@ int ray_trace_recur(space_t *s, color_t *dest, ray_t *ray, unsigned hop, COORD_T
}
vector_t rdir, rstart;
- ray_t r = {start: &rstart, direction: &rdir};
+ ray_t r = {.start = &rstart, .direction = &rdir};
vector_scale(r.start, ray->direction, dist);
vector_add(r.start, r.start, ray->start);
@@ -302,7 +313,7 @@ int ray_trace_recur(space_t *s, color_t *dest, ray_t *ray, unsigned hop, COORD_T
// Check if we should calculate light
if (o->m->defuse + o->m->specular > ZERO_APROX) {
// Add all light hitting o at r.start to c
- direct_light(s, &c, o, &N, ray->start, r.start);
+ direct_light(s, &c, o, &N, ray->start, r.start, seed);
}
// Calculate environmental light