[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [15575] branches/soc-2008-unclezeiv/source /blender/render/intern/source/lightcuts.c: - fixed terrible bug that prevented different light types to work together meaningfully

Davide Vercelli davide.vercelli at gmail.com
Tue Jul 15 00:23:42 CEST 2008


Revision: 15575
          http://projects.blender.org/plugins/scmsvn/viewcvs.php?view=rev&root=bf-blender&revision=15575
Author:   unclezeiv
Date:     2008-07-15 00:23:39 +0200 (Tue, 15 Jul 2008)

Log Message:
-----------
- fixed terrible bug that prevented different light types to work together meaningfully
- fixed silly bug in stats (large int multiplication could easily overflow...)
- fixed a bug where cosine bounding for oriented lights returned wrong value
- fixed: max_lights and max_cuts were still used interchangeably despite now having different meanings
- textured area light does not create black lights anymore (as for environment maps)
- debug: more logging (compiled out by default)
- debug: changed false colour rendering (G: #directional lights / #cut; B: #oriented lights / #cut)

Modified Paths:
--------------
    branches/soc-2008-unclezeiv/source/blender/render/intern/source/lightcuts.c

Modified: branches/soc-2008-unclezeiv/source/blender/render/intern/source/lightcuts.c
===================================================================
--- branches/soc-2008-unclezeiv/source/blender/render/intern/source/lightcuts.c	2008-07-14 20:30:23 UTC (rev 15574)
+++ branches/soc-2008-unclezeiv/source/blender/render/intern/source/lightcuts.c	2008-07-14 22:23:39 UTC (rev 15575)
@@ -681,6 +681,7 @@
 	float area, gapx, gapy, factor, realw, realh;
 	float xdir[3];
 	float ydir[3];
+	float col[3];
 	float stepx, stepy, texvec[2];
 	LampRen *lar;
 	float density;
@@ -726,19 +727,12 @@
 			 * objects... do we need objects there?
 			 */
 			gonew->ob= 0; /* XXX: or go->ob */
-
-			lar = (LampRen *)MEM_callocN(sizeof(LampRen), "lampren");
-
-			create_lamp_oriented(re, lar, orig);
 			
 			/* place a light in its own square with random jittering */
 			texvec[0]= gapx * (x + BLI_frand());
 			texvec[1]= gapy * (y + BLI_frand());
 			stepx= orig->area_size * (texvec[0] - 0.5f);
 			stepy= orig->area_sizey * (texvec[1] - 0.5f);
-			lar->co[0]= orig->co[0] + xdir[0] * stepx + ydir[0] * stepy;
-			lar->co[1]= orig->co[1] + xdir[1] * stepx + ydir[1] * stepy;
-			lar->co[2]= orig->co[2] + xdir[2] * stepx + ydir[2] * stepy;
 			
 			if (use_texture) {
 				int ret;
@@ -749,19 +743,35 @@
 				texvec[1]= texvec[1]*2.0f - 1.0f;
 				ret= multitex_ext(tex, texvec, NULL, NULL, 0, &texres);
 				
-				lar->r= texres.tr * factor * orig->energy;
-				lar->g= texres.tg * factor * orig->energy;
-				lar->b= texres.tb * factor * orig->energy;
+				col[0]= texres.tr * orig->energy;
+				col[1]= texres.tg * orig->energy;
+				col[2]= texres.tb * orig->energy;
 			}
 			else {
-				lar->r= orig->r * factor;
-				lar->g= orig->g * factor;
-				lar->b= orig->b * factor;	
+				col[0]= orig->r;
+				col[1]= orig->g;
+				col[2]= orig->b;
 			}
+			
+			/* XXX: arbitrary limit */
+			if (LC_LUMINOSITY(col) < 0.01f)
+				continue;
+			
+			lar = (LampRen *)MEM_callocN(sizeof(LampRen), "lampren");
+
+			create_lamp_oriented(re, lar, orig);
+			
+			lar->co[0]= orig->co[0] + xdir[0] * stepx + ydir[0] * stepy;
+			lar->co[1]= orig->co[1] + xdir[1] * stepx + ydir[1] * stepy;
+			lar->co[2]= orig->co[2] + xdir[2] * stepx + ydir[2] * stepy;
+			
+			lar->r= col[0] * factor;
+			lar->g= col[1] * factor;
+			lar->b= col[2] * factor;
 			lar->energy= orig->energy * factor;
 
 #ifdef LIGHTCUTS_DEBUG
-			printf("coordinates: %4f %4f %4f\n", lar->co[0], lar->co[1], lar->co[2]);
+			//printf("coordinates: %4f %4f %4f\n", lar->co[0], lar->co[1], lar->co[2]);
 #endif
 
 			BLI_addtail(&re->lampren, lar);
@@ -879,7 +889,7 @@
 	BLI_timestr(lcd->tree_creation_time, tree_time_str);
 	printf("Tree creation time: %12s\n", tree_time_str);
 
-	lcd->cut_nodes_size= (lcd->max_lights * 2 + 1);
+	lcd->cut_nodes_size= (lcd->max_cut * 2 + 1);
 	lcd->cut_nodes= MEM_callocN(sizeof(CutNode) * lcd->cut_nodes_size * re->r.threads, "cut_nodes");
 	
 	re->i.infostr= NULL;
@@ -1005,7 +1015,7 @@
 		cos_t= compute_cosine_bound(transmin, transmax);
 		angle= acosf(cos_t);
 		
-		if (angle < clus->cone_angle)
+		if (angle <= clus->cone_angle)
 			return 1.0;
 		return lcd->max_spot_dist / (lcd->max_spot_dist + len_sq) * MAX2(0.0f, cosf(angle - clus->cone_angle));
 		
@@ -1024,9 +1034,10 @@
 void lightcuts_do_lights(LightcutsData *lcd, ShadeInput *shi, ShadeResult *shr)
 {
 	CutNode *cut_nodes;
-	int free_node= 1;
+	int free_node= 0;
 	int it= 0;
 	int used= 0;
+	int used_type[3]= {0, 0, 0};
 	float i, i_noshad, t;
 	float tsm[3][3]; /* tangent space matrix */
 	float msm[3][3]; /* mirror direction space matrix */
@@ -1083,7 +1094,6 @@
 
 	/* initial nodes in the queue */
 	{
-		int free_cut= 0;
 		int j;
 
 		for (j= 0; j<_TREES_SIZE; j++) {
@@ -1091,7 +1101,7 @@
 
 			if (tree->counter > 0) {
 				LightcutsCluster *clus= &tree->array[tree->root];
-				CutNode *root= &cut_nodes[free_cut];
+				CutNode *root= &cut_nodes[free_node];
 
 				root->id= tree->root;
 				root->type= clus->type;
@@ -1120,19 +1130,26 @@
 
 					if (!IS_LEAF(clus)) {
 						BLI_heap_insert(cut, -root->error_bound * clus->luminance, root);
-						free_cut++;
+						free_node++;
 					}
-					else
+					else {
 						used++;
+#ifdef LIGHTCUTS_DEBUG
+						if (lcd->dbg_first_pixel==0)
+							printf("A t:%d id:%4d eb:%7.5f fc:%7.5f\n",
+									j, root->id, root->error_bound, root->f_clus);
+#endif
+					}
 				}
 				else
 					used++;
+				used_type[j]++;
 			}
 		}
 	}
 
 	/* at each iteration the heap may grow by one, but we have a maximum size */
-	while (BLI_heap_size(cut) < (lcd->max_lights - used) && BLI_heap_size(cut) > 0) {
+	while (BLI_heap_size(cut) < (lcd->max_cut - used) && BLI_heap_size(cut) > 0) {
 		LightcutsCluster *hinode;
 		CutNode *cn_hinode;
 
@@ -1150,6 +1167,11 @@
 
 		hinode= &array[cn_hinode->id];
 #ifdef LIGHTCUTS_DEBUG
+		if (lcd->dbg_first_pixel==0)
+			printf("E t:%d id:%4d eb:%7.5f ebl:%7.5f fc:%7.5f (c1:%4d c2:%4d)\n",
+					CLUSTER_TYPE_TO_ARRAY_IDX(cn_hinode->type), cn_hinode->id,
+					cn_hinode->error_bound, cn_hinode->error_bound * hinode->luminance, cn_hinode->f_clus,
+					hinode->child1, hinode->child2);
 		if (cn_hinode->error_bound + FLT_EPSILON < cn_hinode->contr_factor) {
 			printf("troublesome node! at %d, %d (it=%d): eb %7.5f < cf %7.5f, (%10.6f * 10^6)\n",
 			shi->xs, shi->ys, it, cn_hinode->error_bound, cn_hinode->contr_factor, 1000000.0f * fabs(cn_hinode->error_bound - cn_hinode->contr_factor));
@@ -1159,6 +1181,7 @@
 		if (IS_LEAF(hinode)) {
 			/* can't go further down */
 			used++;
+			used_type[CLUSTER_TYPE_TO_ARRAY_IDX(cn_hinode->type)]++;
 			printf("Leaf node in queue: this should never happen\n");
 			break;
 		}
@@ -1211,11 +1234,19 @@
 
 				if (!IS_LEAF(rep))
 					BLI_heap_insert(cut, -cn_rep->error_bound * rep->luminance, cn_rep);
-				else
+				else {
 					used++;
+#ifdef LIGHTCUTS_DEBUG
+					if (lcd->dbg_first_pixel==0)
+						printf("A t:%d id:%4d eb:%7.5f fc:%7.5f\n",
+								CLUSTER_TYPE_TO_ARRAY_IDX(cn_rep->type), cn_rep->id,
+								cn_rep->error_bound, cn_rep->f_clus);
+#endif
+				}
 			}
 			else
 				used++;
+			used_type[CLUSTER_TYPE_TO_ARRAY_IDX(cn_rep->type)]++;
 
 			/* for the "unrepresented" light we have to compute stuff from scratch */
 			cn_unrep->id= unrep->id;
@@ -1237,11 +1268,19 @@
 
 				if (!IS_LEAF(unrep))
 					BLI_heap_insert(cut, -cn_unrep->error_bound * unrep->luminance, cn_unrep);
-				else
+				else {
 					used++;
+#ifdef LIGHTCUTS_DEBUG
+					if (lcd->dbg_first_pixel==0)
+						printf("A t:%d id:%4d eb:%7.5f fc:%7.5f\n",
+								CLUSTER_TYPE_TO_ARRAY_IDX(cn_unrep->type), cn_unrep->id,
+								cn_unrep->error_bound, cn_unrep->f_clus);
+#endif
+				}
 			}
 			else
 				used++;
+			used_type[CLUSTER_TYPE_TO_ARRAY_IDX(cn_unrep->type)]++;
 
 			if(shi->passflag & (SCE_PASS_DIFFUSE|SCE_PASS_SHADOW)) {
 				VECADDFAC(totest_noshad, totest_noshad, rep->col, -cn_hinode->f_clus_noshad);
@@ -1280,13 +1319,17 @@
 
 	if (shi->passflag & SCE_PASS_LCFAUX) {
 		shr->faux[0]= (float)(used + BLI_heap_size(cut)) / lcd->max_cut;
-		shr->faux[1]= (float)used/(float)lcd->max_cut;
-		shr->faux[2]= 0.5;
+		// shr->faux[0]= ((float)used_type[0]) / lcd->max_cut;
+		shr->faux[1]= ((float)used_type[1]) / lcd->max_cut;
+		shr->faux[2]= ((float)used_type[2]) / lcd->max_cut;
 		shr->faux[3]= (float)((used + BLI_heap_size(cut)) > 0.0);
 	}
 
 	lcd->stat_cut_size+= (used + BLI_heap_size(cut));
 	lcd->stat_samples++;
+#ifdef LIGHTCUTS_DEBUG
+	lcd->dbg_first_pixel++;
+#endif
 
 	BLI_heap_free(cut, 0);
 }
@@ -1307,7 +1350,7 @@
 		lcd->max_cut,
 		(float)lcd->stat_cut_size / (float)lcd->stat_samples,
 		(float)lcd->stat_rays_shot / (float)lcd->stat_samples,
-		100.0f * lcd->stat_rays_shot / (float)(lcd->stat_samples * lcd->light_counter));
+		100.0f * (float)lcd->stat_rays_shot / ((float)(lcd->stat_samples) * (float)(lcd->light_counter)));
 }
 
 void lightcuts_free(LightcutsData **p)





More information about the Bf-blender-cvs mailing list