erebus

changeset 28:4a0a288ffb27

phong/lafortune BRDF
author John Tsiombikas <nuclear@member.fsf.org>
date Fri, 06 Jun 2014 14:39:40 +0300
parents 0ced900e15a7
children fb20e3855740
files liberebus/src/brdf.cc liberebus/src/brdf.h liberebus/src/rt.cc liberebus/src/scene.cc test/scene
diffstat 5 files changed, 87 insertions(+), 7 deletions(-) [+]
line diff
     1.1 --- a/liberebus/src/brdf.cc	Mon Jun 02 00:53:01 2014 +0300
     1.2 +++ b/liberebus/src/brdf.cc	Fri Jun 06 14:39:40 2014 +0300
     1.3 @@ -130,3 +130,45 @@
     1.4  {
     1.5  	return 1.0f;
     1.6  }
     1.7 +
     1.8 +// --- class PhongRefl ---
     1.9 +PhongRefl::PhongRefl()
    1.10 +{
    1.11 +	shininess = 42.0;
    1.12 +}
    1.13 +
    1.14 +Vector3 PhongRefl::sample_dir(const Vector3 &norm, const Vector3 &outdir) const
    1.15 +{
    1.16 +	// construct orthonormal basis with k being the reflection dir
    1.17 +	Vector3 refl = outdir.reflection(norm).normalized();
    1.18 +	Vector3 up = Vector3(0, 0, 1);
    1.19 +	if(fabs(dot_product(refl, up)) - 1.0 < 0.001) {
    1.20 +		up = Vector3(0, 1, 0);
    1.21 +	}
    1.22 +	Vector3 right = cross_product(up, refl);
    1.23 +	up = cross_product(refl, right);
    1.24 +
    1.25 +	// construct the matrix transposed to move the sample from reflection
    1.26 +	// space to world space
    1.27 +	Matrix3x3 xform;
    1.28 +	xform.set_column_vector(right, 0);
    1.29 +	xform.set_column_vector(up, 1);
    1.30 +	xform.set_column_vector(refl, 2);
    1.31 +
    1.32 +	float phi = acos(pow(randf(), 1.0 / (shininess + 1)));
    1.33 +	float theta = 2.0 * M_PI * randf();
    1.34 +
    1.35 +	Vector3 v;
    1.36 +	v.x = cos(theta) * sin(phi);
    1.37 +	v.y = sin(theta) * sin(phi);
    1.38 +	v.z = cos(phi);
    1.39 +	v.transform(xform);
    1.40 +	return v;
    1.41 +}
    1.42 +
    1.43 +float PhongRefl::eval(const Vector3 &norm, const Vector3 &outdir, const Vector3 &indir) const
    1.44 +{
    1.45 +	Vector3 refl = outdir.reflection(norm);
    1.46 +	float dot = std::max<float>(dot_product(indir, refl), 0.0f);
    1.47 +	return pow(dot, shininess);
    1.48 +}
     2.1 --- a/liberebus/src/brdf.h	Mon Jun 02 00:53:01 2014 +0300
     2.2 +++ b/liberebus/src/brdf.h	Fri Jun 06 14:39:40 2014 +0300
     2.3 @@ -53,4 +53,14 @@
     2.4  	float eval(const Vector3 &norm, const Vector3 &outdir, const Vector3 &indir) const override;
     2.5  };
     2.6  
     2.7 +class PhongRefl : public Reflectance {
     2.8 +public:
     2.9 +	float shininess;
    2.10 +
    2.11 +	PhongRefl();
    2.12 +
    2.13 +	Vector3 sample_dir(const Vector3 &norm, const Vector3 &outdir) const override;
    2.14 +	float eval(const Vector3 &norm, const Vector3 &outdir, const Vector3 &indir) const override;
    2.15 +};
    2.16 +
    2.17  #endif	// BRDF_H_
     3.1 --- a/liberebus/src/rt.cc	Mon Jun 02 00:53:01 2014 +0300
     3.2 +++ b/liberebus/src/rt.cc	Fri Jun 06 14:39:40 2014 +0300
     3.3 @@ -2,7 +2,7 @@
     3.4  #include "rt.h"
     3.5  #include "erebus_impl.h"
     3.6  
     3.7 -#define MAX_ITER	8
     3.8 +#define MAX_ITER	6
     3.9  
    3.10  Color ray_trace(struct erebus *ctx, const Ray &ray, int iter)
    3.11  {
    3.12 @@ -40,14 +40,18 @@
    3.13  	Vector2 texcoords = hit.calc_texcoords();
    3.14  
    3.15  	Color color = mtl->get_attrib_color("diffuse", texcoords.x, texcoords.y);
    3.16 -	Color res = mtl->get_attrib_color("emissive") + color * scn->get_env().ambient;
    3.17 +	Color specular = mtl->get_attrib_color("specular", texcoords.x, texcoords.y);
    3.18 +	Color res = mtl->get_attrib_color("emissive", texcoords.x, texcoords.y) +
    3.19 +		color * scn->get_env().ambient;
    3.20 +	float shininess = mtl->get_attrib_value("shininess");
    3.21  
    3.22  	Vector3 sample_dir;
    3.23  	float prob = brdf->sample(norm, -hit.world_ray.dir, &sample_dir);
    3.24 -	if(iter < max_iter && randf() <= prob) {
    3.25 +	if(iter < max_iter && randf() <= prob && ray.energy * prob > 0.001) {
    3.26  		Ray sample_ray;
    3.27  		sample_ray.origin = ray.origin + ray.dir * hit.dist;
    3.28  		sample_ray.dir = sample_dir;
    3.29 +		sample_ray.energy = ray.energy * prob;
    3.30  
    3.31  		res += ray_trace(ctx, sample_ray, iter + 1) * color;
    3.32  	}
     4.1 --- a/liberebus/src/scene.cc	Mon Jun 02 00:53:01 2014 +0300
     4.2 +++ b/liberebus/src/scene.cc	Fri Jun 06 14:39:40 2014 +0300
     4.3 @@ -140,9 +140,22 @@
     4.4  
     4.5  bool Scene::load(FILE *fp)
     4.6  {
     4.7 -	static char buf[256];
     4.8 +	static char buf[4096];
     4.9 +	int offset = 0;
    4.10  
    4.11 -	while(fgets(buf, sizeof buf, fp)) {
    4.12 +	while(fgets(buf + offset, sizeof buf - offset, fp)) {
    4.13 +		// handle line continuations
    4.14 +		int len = strlen(buf);
    4.15 +		if(strcmp(buf + len - 2, "\\\n") == 0 || strcmp(buf + len - 2, "\\\r") == 0) {
    4.16 +			offset = len - 2;
    4.17 +			continue;
    4.18 +		}
    4.19 +		if(strcmp(buf + len - 3, "\\\r\n") == 0) {
    4.20 +			offset = len - 3;
    4.21 +			continue;
    4.22 +		}
    4.23 +		offset = 0;
    4.24 +
    4.25  		char *line = strip_wspace(buf);
    4.26  		if(!line || !*line || *line == '#') {
    4.27  			continue;
    4.28 @@ -198,6 +211,13 @@
    4.29  				brdf = new LambertRefl;
    4.30  				if(!composite) break;
    4.31  
    4.32 +			} else if(strcmp(argv[i], "phong") == 0) {
    4.33 +				if(composite && brdf) {
    4.34 +					composite->add_brdf(brdf, weight);
    4.35 +				}
    4.36 +				brdf = new PhongRefl;
    4.37 +				if(!composite) break;
    4.38 +
    4.39  			} else if(strcmp(argv[i], "mirror") == 0) {
    4.40  				if(composite && brdf) {
    4.41  					composite->add_brdf(brdf, weight);
     5.1 --- a/test/scene	Mon Jun 02 00:53:01 2014 +0300
     5.2 +++ b/test/scene	Fri Jun 06 14:39:40 2014 +0300
     5.3 @@ -1,8 +1,12 @@
     5.4  # test scene
     5.5  
     5.6 -sphere -position 0 0 0 -scaling 1 1 1 -diffuse 1 0.6 0.5
     5.7 +sphere -position 0 0 0 -scaling 1 1 1 -diffuse 1 0.6 0.5 -brdf composite \
     5.8 +	-brdf lambert -brdf-weight 0.5 \
     5.9 +	-brdf phong -brdf-weight 0.5
    5.10  
    5.11 -box -position 0 -1.25 0 -scaling 4 0.5 4 -diffuse 0.3 0.4 1.0 -brdf composite -brdf lambert -brdf-weight 0.3 -brdf mirror -brdf-weight 0.7
    5.12 +box -position 0 -1.25 0 -scaling 4 0.5 4 -diffuse 0.3 0.4 1.0 -brdf composite \
    5.13 +	-brdf lambert -brdf-weight 0.3 \
    5.14 +	-brdf mirror -brdf-weight 0.7
    5.15  box -position 0 3.75 0 -scaling 20 10 20 -diffuse 1.0 1.0 1.0 -brdf lambert
    5.16  
    5.17  box -position 0 4 0 -scaling 3 0.1 3 -emissive 6 6 6