src/raytracer.cc
branchpyrit
changeset 32 8af5c17d368b
parent 31 b4e09433934a
child 33 83d0200d4c09
--- a/src/raytracer.cc	Sun Dec 09 10:45:26 2007 +0100
+++ b/src/raytracer.cc	Sun Dec 09 13:31:38 2007 +0100
@@ -214,39 +214,24 @@
 static void *renderrow(void *data)
 {
 	RenderrowData *d = (RenderrowData*) data;
-	int subsample = d->rt->getSubsample();
-	Float subsample2 = 1.0/(subsample*subsample);
-	int ww = d->w*3;
+	const int subsample = d->rt->getSubsample();
+	const Float subsample2 = 1.0/(subsample*subsample);
+	const int oversample = d->rt->getOversample();
+	const int ww = d->w*3;
 	Vector3 dir = d->dfix;
 	for (int x = 0; x < d->w; x += subsample) {
 		// generate a ray from eye passing through this pixel
-#if OVERSAMPLING
-		// 5x oversampling
-		Colour c = Colour();
-
-		for (int i = 0; i < 5; i++)
-		{
-			Float osax[] = {0.0, -0.4, +0.4, +0.4, -0.4};
-			Float osay[] = {0.0, -0.4, -0.4, +0.4, +0.4};
-			Vector3 tmpdir = dir + osax[i]*d->dx + osay[i]*d->dy;
-			tmpdir.normalize();
-			Ray ray(d->eye, tmpdir);
-			c += d->rt->raytrace(ray, 0, NULL);
-		}
-		c = c * (1./5);
-#else
-		// no oversampling
-		dir.normalize();
-		Ray ray(d->eye, dir);
-		Colour c = d->rt->raytrace(ray, 0, NULL);
 		if (subsample > 1)
 		{
 			Colour ic;
-			// top-left is 'c'
+			// top-left
+			dir.normalize();
+			Ray ray(d->eye, dir);
+			Colour c1 = d->rt->raytrace(ray, 0, NULL);
 			// top-right
 			Vector3 tmpdir = dir + (subsample-1)*d->dx;
 			tmpdir.normalize();
-			Ray ray(d->eye, tmpdir);
+			ray.dir = tmpdir;
 			Colour c2 = d->rt->raytrace(ray, 0, NULL);
 			// bottom right
 			tmpdir += (subsample-1)*d->dy;
@@ -259,10 +244,10 @@
 			ray.dir = tmpdir;
 			Colour c3 = d->rt->raytrace(ray, 0, NULL);
 			// are the colors similar?
-			Float m = (c-c2).mag2();
+			Float m = (c1-c2).mag2();
 			m = max(m, (c2-c3).mag2());
 			m = max(m, (c3-c4).mag2());
-			m = max(m, (c4-c).mag2());
+			m = max(m, (c4-c1).mag2());
 			if (m < 0.001)
 			{
 				// interpolate
@@ -271,7 +256,7 @@
 				{
 					for (int y = 0; y < subsample; y++)
 					{
-						ic = c*(subsample-x)*(subsample-y)*subsample2
+						ic = c1*(subsample-x)*(subsample-y)*subsample2
 							+ c2*(x)*(subsample-y)*subsample2
 							+ c3*(subsample-x)*(y)*subsample2
 							+ c4*(x)*(y)*subsample2;
@@ -288,9 +273,9 @@
 				// render
 				Vector3 tmpdir = dir;
 				// first column
-				*(d->iter) = c.r;
-				*(d->iter + 1) = c.g;
-				*(d->iter + 2) = c.b;
+				*(d->iter) = c1.r;
+				*(d->iter + 1) = c1.g;
+				*(d->iter + 2) = c1.b;
 				for (int y = 1; y < subsample-1; y++)
 				{
 					Vector3 tmp2dir = tmpdir + y*d->dy;
@@ -342,9 +327,53 @@
 				d->iter += 3;
 			}
 		}
-#endif
-		if (subsample <= 1)
+		else // subsample <= 1
 		{
+			Colour c;
+			if (oversample <= 0)
+			{
+				// no oversampling
+				dir.normalize();
+				Ray ray(d->eye, dir);
+				c = d->rt->raytrace(ray, 0, NULL);
+			}
+			else
+			if (oversample <= 3)
+			{
+				// grid oversampling
+				static const int gridsamples[] = {5,9,16};
+				static const Float osa5x[] = {0.0, -0.4, +0.4, +0.4, -0.4};
+				static const Float osa5y[] = {0.0, -0.4, -0.4, +0.4, +0.4};
+				static const Float osa9x[] = {-0.34,  0.00, +0.34,
+					-0.34,  0.00, +0.34, -0.34,  0.00, +0.34};
+				static const Float osa9y[] = {-0.34, -0.34, -0.34,
+					 0.00,  0.00,  0.00, +0.34, +0.34, +0.34};
+				static const Float osa16x[] = {-0.375, -0.125, +0.125, +0.375,
+					-0.375, -0.125, +0.125, +0.375, -0.375, -0.125, +0.125, +0.375,
+					-0.375, -0.125, +0.125, +0.375};
+				static const Float osa16y[] = {-0.375, -0.375, -0.375, -0.375,
+					-0.125, -0.125, -0.125, -0.125, +0.125, +0.125, +0.125, +0.125,
+					+0.375, +0.375, +0.375, +0.375};
+				static const Float *osaSx[] = {osa5x, osa9x, osa16x};
+				static const Float *osaSy[] = {osa5y, osa9y, osa16y};
+				const int samples = gridsamples[oversample-1];
+				const Float *osax = osaSx[oversample-1];
+				const Float *osay = osaSy[oversample-1];
+				for (int i = 0; i < samples; i++)
+				{
+					Vector3 tmpdir = dir + osax[i]*d->dx + osay[i]*d->dy;
+					tmpdir.normalize();
+					Ray ray(d->eye, tmpdir);
+					c += d->rt->raytrace(ray, 0, NULL);
+				}
+				c = c * (1.0/samples);
+			}
+			else
+			{
+				// stochastic oversampling
+				// ...todo
+			}
+			// write color to buffer
 			*d->iter++ = c.r;
 			*d->iter++ = c.g;
 			*d->iter++ = c.b;