diff options
-rw-r--r-- | libdimension/color.c | 6 | ||||
-rw-r--r-- | libdimension/dimension/color.h | 5 | ||||
-rw-r--r-- | libdimension/raytrace.c | 22 |
3 files changed, 20 insertions, 13 deletions
diff --git a/libdimension/color.c b/libdimension/color.c index 8201a8f..5220dfa 100644 --- a/libdimension/color.c +++ b/libdimension/color.c @@ -84,6 +84,12 @@ const dmnsn_color dmnsn_cyan = { .trans = 0.0 }; +bool +dmnsn_color_is_black(dmnsn_color color) +{ + return color.R == 0.0 && color.G == 0.0 && color.B == 0.0; +} + /* sRGB's `C' function */ static double dmnsn_sRGB_C(double Clinear) { /* diff --git a/libdimension/dimension/color.h b/libdimension/dimension/color.h index 67fa032..43edbff 100644 --- a/libdimension/dimension/color.h +++ b/libdimension/dimension/color.h @@ -25,6 +25,8 @@ #ifndef DIMENSION_COLOR_H #define DIMENSION_COLOR_H +#include <stdbool.h> + /* Internally, we use sRGB color. */ typedef struct { double filter, trans; /* Filter transparancy only lets light of this color @@ -67,6 +69,9 @@ extern const dmnsn_color dmnsn_black, dmnsn_white, dmnsn_red, dmnsn_green, /* Standard whitepoint, determined by the conversion of sRGB white to CIE XYZ */ extern const dmnsn_CIE_XYZ dmnsn_whitepoint; +/* Is this color black? */ +bool dmnsn_color_is_black(dmnsn_color color); + /* Color conversions */ dmnsn_color dmnsn_color_from_XYZ(dmnsn_CIE_XYZ XYZ); diff --git a/libdimension/raytrace.c b/libdimension/raytrace.c index 0165870..bb44587 100644 --- a/libdimension/raytrace.c +++ b/libdimension/raytrace.c @@ -20,7 +20,6 @@ #include "dimension_impl.h" #include <unistd.h> /* For sysconf */ -#include <stdbool.h> /* * Boilerplate for multithreading @@ -337,12 +336,10 @@ dmnsn_raytrace_pigment(const dmnsn_raytrace_state *state) } /* Get the color of a light ray at an intersection point */ -static bool +static dmnsn_color dmnsn_raytrace_light_ray(const dmnsn_raytrace_state *state, - const dmnsn_light *light, dmnsn_color *color) + const dmnsn_light *light) { - *color = dmnsn_black; - dmnsn_vector x0 = dmnsn_line_point(state->intersection->ray, state->intersection->t); dmnsn_line shadow_ray = dmnsn_new_line(x0, dmnsn_vector_sub(light->x0, x0)); @@ -351,9 +348,9 @@ dmnsn_raytrace_light_ray(const dmnsn_raytrace_state *state, /* Search for an object in the way of the light source */ if (dmnsn_vector_dot(shadow_ray.n, state->intersection->normal) < 0.0) - return false; + return dmnsn_black; - *color = (*light->light_fn)(light, x0); + dmnsn_color color = (*light->light_fn)(light, x0); unsigned int level = state->level; while (level) { @@ -373,21 +370,20 @@ dmnsn_raytrace_light_ray(const dmnsn_raytrace_state *state, dmnsn_color pigment = dmnsn_raytrace_pigment(&shadow_state); if (pigment.filter || pigment.trans) { - *color = dmnsn_color_filter(*color, pigment); + color = dmnsn_color_filter(color, pigment); shadow_ray.x0 = dmnsn_line_point(shadow_ray, shadow_caster->t); shadow_ray.n = dmnsn_vector_sub(light->x0, shadow_ray.x0); shadow_ray = dmnsn_line_add_epsilon(shadow_ray); } else { - *color = dmnsn_black; dmnsn_delete_intersection(shadow_caster); - return false; + return dmnsn_black; } dmnsn_delete_intersection(shadow_caster); --level; } - return true; + return color; } static dmnsn_color @@ -410,8 +406,8 @@ dmnsn_raytrace_lighting(const dmnsn_raytrace_state *state) for (i = 0; i < dmnsn_array_size(state->scene->lights); ++i) { dmnsn_array_get(state->scene->lights, i, &light); - dmnsn_color light_color; - if (dmnsn_raytrace_light_ray(state, light, &light_color)) { + dmnsn_color light_color = dmnsn_raytrace_light_ray(state, light); + if (!dmnsn_color_is_black(light_color)) { if (state->scene->quality & DMNSN_RENDER_FINISH && finish && (finish->diffuse_fn || finish->specular_fn)) { |