[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [43004] trunk/blender: Color management: add "Color Unpremultiply" option for images and render settings.

Brecht Van Lommel brechtvanlommel at pandora.be
Fri Dec 30 15:17:27 CET 2011


Revision: 43004
          http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=43004
Author:   blendix
Date:     2011-12-30 14:17:11 +0000 (Fri, 30 Dec 2011)
Log Message:
-----------
Color management: add "Color Unpremultiply" option for images and render settings.
For premultiplied alpha images, this makes any color space conversion for the image
or render output work on color without alpha multiplied in.

This is typically useful to avoid fringing when the image was or will be composited
over a light background. If the image will be composited over a black background on
the other hand, leaving this option off will give correct results.

In an ideal world, there should never be any color space conversion on images with
alpha, since it's undefined what to do then, but in practice it's useful to have
this option.

Patch by Troy Sobotka, with changes by me.

Modified Paths:
--------------
    trunk/blender/release/scripts/startup/bl_ui/properties_render.py
    trunk/blender/source/blender/blenkernel/intern/image.c
    trunk/blender/source/blender/editors/include/BIF_glutil.h
    trunk/blender/source/blender/editors/render/render_internal.c
    trunk/blender/source/blender/editors/render/render_preview.c
    trunk/blender/source/blender/editors/screen/glutil.c
    trunk/blender/source/blender/editors/space_image/image_buttons.c
    trunk/blender/source/blender/editors/space_node/space_node.c
    trunk/blender/source/blender/imbuf/IMB_imbuf_types.h
    trunk/blender/source/blender/imbuf/intern/divers.c
    trunk/blender/source/blender/makesdna/DNA_image_types.h
    trunk/blender/source/blender/makesdna/DNA_scene_types.h
    trunk/blender/source/blender/makesrna/intern/rna_image.c
    trunk/blender/source/blender/makesrna/intern/rna_scene.c
    trunk/blender/source/blender/nodes/composite/node_composite_util.c
    trunk/blender/source/blender/nodes/composite/nodes/node_composite_image.c
    trunk/blender/source/blender/render/intern/source/pipeline.c

Modified: trunk/blender/release/scripts/startup/bl_ui/properties_render.py
===================================================================
--- trunk/blender/release/scripts/startup/bl_ui/properties_render.py	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/release/scripts/startup/bl_ui/properties_render.py	2011-12-30 14:17:11 UTC (rev 43004)
@@ -316,6 +316,9 @@
         col = split.column()
         col.prop(rd, "use_raytrace", text="Ray Tracing")
         col.prop(rd, "use_color_management")
+        sub = col.row()
+        sub.active = rd.use_color_management == True
+        sub.prop(rd, "use_color_unpremultiply")
         col.prop(rd, "alpha_mode", text="Alpha")
 
 

Modified: trunk/blender/source/blender/blenkernel/intern/image.c
===================================================================
--- trunk/blender/source/blender/blenkernel/intern/image.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/blenkernel/intern/image.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -285,6 +285,10 @@
 				break;
 
 		ibuf->index= index;
+		if(ima->flag & IMA_CM_PREDIVIDE)
+			ibuf->flags |= IB_cm_predivide;
+		else
+			ibuf->flags &= ~IB_cm_predivide;
 
 		/* this function accepts link==NULL */
 		BLI_insertlinkbefore(&ima->ibufs, link, ibuf);
@@ -2304,9 +2308,17 @@
 
 	/* since its possible to access the buffer from the image directly, set the profile [#25073] */
 	ibuf->profile= (iuser->scene->r.color_mgt_flag & R_COLOR_MANAGEMENT) ? IB_PROFILE_LINEAR_RGB : IB_PROFILE_NONE;
-
 	ibuf->dither= dither;
 
+	if(iuser->scene->r.color_mgt_flag & R_COLOR_MANAGEMENT_PREDIVIDE) {
+		ibuf->flags |= IB_cm_predivide;
+		ima->flag |= IMA_CM_PREDIVIDE;
+	}
+	else {
+		ibuf->flags &= ~IB_cm_predivide;
+		ima->flag &= ~IMA_CM_PREDIVIDE;
+	}
+
 	ima->ok= IMA_OK_LOADED;
 
 	return ibuf;

Modified: trunk/blender/source/blender/editors/include/BIF_glutil.h
===================================================================
--- trunk/blender/source/blender/editors/include/BIF_glutil.h	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/include/BIF_glutil.h	2011-12-30 14:17:11 UTC (rev 43004)
@@ -136,13 +136,8 @@
 	 * is expected to be in RGBA byte or float format, and the 
 	 * modelview and projection matrices are assumed to define a 
 	 * 1-to-1 mapping to screen space.
-	 * @param gamma_correct Optionally gamma correct float sources to sRGB for display
 	 */
 
-	/* only for float rects, converts to 32 bits and draws */
-void glaDrawPixelsSafe_to32(float fx, float fy, int img_w, int img_h, int row_w, float *rectf, int gamma_correct);
-
-
 void glaDrawPixelsTex		(float x, float y, int img_w, int img_h, int format, void *rect);
 
 void glaDrawPixelsTexScaled(float x, float y, int img_w, int img_h, int format, void *rect, float scaleX, float scaleY);

Modified: trunk/blender/source/blender/editors/render/render_internal.c
===================================================================
--- trunk/blender/source/blender/editors/render/render_internal.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/render/render_internal.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -138,11 +138,14 @@
 	rectf+= 4*(rr->rectx*ymin + xmin);
 	rectc= (unsigned char*)(ibuf->rect + ibuf->x*rymin + rxmin);
 
-	if(scene && (scene->r.color_mgt_flag & R_COLOR_MANAGEMENT))
+	if(scene && (scene->r.color_mgt_flag & R_COLOR_MANAGEMENT)) {
 		profile_from= IB_PROFILE_LINEAR_RGB;
-	else
+		predivide= (scene->r.color_mgt_flag & R_COLOR_MANAGEMENT_PREDIVIDE);
+	}
+	else {
 		profile_from= IB_PROFILE_SRGB;
-	predivide= 0;
+		predivide= 0;
+	}
 
 	IMB_buffer_byte_from_float(rectc, rectf,
 		4, ibuf->dither, IB_PROFILE_SRGB, profile_from, predivide,

Modified: trunk/blender/source/blender/editors/render/render_preview.c
===================================================================
--- trunk/blender/source/blender/editors/render/render_preview.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/render/render_preview.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -460,12 +460,15 @@
 	Render *re;
 	RenderResult rres;
 	char name[32];
-	int do_gamma_correct=0;
+	int do_gamma_correct=0, do_predivide=0;
 	int offx=0, newx= rect->xmax-rect->xmin, newy= rect->ymax-rect->ymin;
 
 	if (id && GS(id->name) != ID_TE) {
 		/* exception: don't color manage texture previews - show the raw values */
-		if (sce) do_gamma_correct = sce->r.color_mgt_flag & R_COLOR_MANAGEMENT;
+		if (sce) {
+			do_gamma_correct = sce->r.color_mgt_flag & R_COLOR_MANAGEMENT;
+			do_predivide = sce->r.color_mgt_flag & R_COLOR_MANAGEMENT_PREDIVIDE;
+		}
 	}
 
 	if(!split || first) sprintf(name, "Preview %p", (void *)sa);
@@ -488,11 +491,29 @@
 	if(rres.rectf) {
 		
 		if(ABS(rres.rectx-newx)<2 && ABS(rres.recty-newy)<2) {
+
 			newrect->xmax= MAX2(newrect->xmax, rect->xmin + rres.rectx + offx);
 			newrect->ymax= MAX2(newrect->ymax, rect->ymin + rres.recty);
 
-			glaDrawPixelsSafe_to32(rect->xmin+offx, rect->ymin, rres.rectx, rres.recty, rres.rectx, rres.rectf, do_gamma_correct);
+			if(rres.rectx && rres.recty) {
+				/* temporary conversion to byte for drawing */
+				float fx= rect->xmin + offx;
+				float fy= rect->ymin;
+				int profile_from= (do_gamma_correct)? IB_PROFILE_LINEAR_RGB: IB_PROFILE_SRGB;
+				int dither= 0;
+				unsigned char *rect_byte;
 
+				rect_byte= MEM_mallocN(rres.rectx*rres.recty*sizeof(int), "ed_preview_draw_rect");
+
+				IMB_buffer_byte_from_float(rect_byte, rres.rectf,
+					4, dither, IB_PROFILE_SRGB, profile_from, do_predivide, 
+					rres.rectx, rres.recty, rres.rectx, rres.rectx);
+
+				glaDrawPixelsSafe(fx, fy, rres.rectx, rres.recty, rres.rectx, GL_RGBA, GL_UNSIGNED_BYTE, rect_byte);
+
+				MEM_freeN(rect_byte);
+			}
+
 			RE_ReleaseResultImage(re);
 			return 1;
 		}

Modified: trunk/blender/source/blender/editors/screen/glutil.c
===================================================================
--- trunk/blender/source/blender/editors/screen/glutil.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/screen/glutil.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -45,9 +45,6 @@
 #include "BIF_gl.h"
 #include "BIF_glutil.h"
 
-#include "IMB_imbuf.h"
-#include "IMB_imbuf_types.h"
-
 #ifndef GL_CLAMP_TO_EDGE
 #define GL_CLAMP_TO_EDGE                        0x812F
 #endif
@@ -562,27 +559,6 @@
 	glaDrawPixelsTexScaled(x, y, img_w, img_h, format, rect, 1.0f, 1.0f);
 }
 
-/* row_w is unused but kept for completeness */
-void glaDrawPixelsSafe_to32(float fx, float fy, int img_w, int img_h, int UNUSED(row_w), float *rectf, int do_gamma_correct)
-{
-	unsigned char *rect32;
-	int profile_from= (do_gamma_correct)? IB_PROFILE_LINEAR_RGB: IB_PROFILE_SRGB;
-	int predivide= 0;
-	
-	/* copy imgw-imgh to a temporal 32 bits rect */
-	if(img_w<1 || img_h<1) return;
-	
-	rect32= MEM_mallocN(img_w*img_h*sizeof(int), "temp 32 bits");
-	
-	IMB_buffer_byte_from_float(rect32, rectf,
-		4, 0, IB_PROFILE_SRGB, profile_from, predivide, 
-		img_w, img_h, img_w, img_w);
-	
-	glaDrawPixelsSafe(fx, fy, img_w, img_h, img_w, GL_RGBA, GL_UNSIGNED_BYTE, rect32);
-
-	MEM_freeN(rect32);
-}
-
 void glaDrawPixelsSafe(float x, float y, int img_w, int img_h, int row_w, int format, int type, void *rect)
 {
 	float xzoom= glaGetOneFloat(GL_ZOOM_X);

Modified: trunk/blender/source/blender/editors/space_image/image_buttons.c
===================================================================
--- trunk/blender/source/blender/editors/space_image/image_buttons.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/space_image/image_buttons.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -750,7 +750,9 @@
 					uiLayoutSetActive(row, RNA_boolean_get(&imaptr, "use_fields"));
 					uiItemR(row, &imaptr, "field_order", UI_ITEM_R_EXPAND, NULL, ICON_NONE);
 					
-					uiItemR(split, &imaptr, "use_premultiply", 0, NULL, ICON_NONE);
+					row= uiLayoutRow(layout, 0);
+					uiItemR(row, &imaptr, "use_premultiply", 0, NULL, ICON_NONE);
+					uiItemR(row, &imaptr, "use_color_unpremultiply", 0, NULL, ICON_NONE);
 				}
 			}
 

Modified: trunk/blender/source/blender/editors/space_node/space_node.c
===================================================================
--- trunk/blender/source/blender/editors/space_node/space_node.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/editors/space_node/space_node.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -248,12 +248,10 @@
 		case NC_IMAGE:
 			if (wmn->action == NA_EDITED) {
 				if(type==NTREE_COMPOSIT) {
-					Scene *scene= wmn->window->screen->scene;
-					
 					/* note that nodeUpdateID is already called by BKE_image_signal() on all
 					 * scenes so really this is just to know if the images is used in the compo else
 					 * painting on images could become very slow when the compositor is open. */
-					if(nodeUpdateID(scene->nodetree, wmn->reference))
+					if(nodeUpdateID(snode->nodetree, wmn->reference))
 						ED_area_tag_refresh(sa);
 				}
 			}

Modified: trunk/blender/source/blender/imbuf/IMB_imbuf_types.h
===================================================================
--- trunk/blender/source/blender/imbuf/IMB_imbuf_types.h	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/imbuf/IMB_imbuf_types.h	2011-12-30 14:17:11 UTC (rev 43004)
@@ -158,6 +158,7 @@
 #define IB_tiles			(1 << 10)
 #define IB_tilecache		(1 << 11)
 #define IB_premul			(1 << 12)
+#define IB_cm_predivide		(1 << 13)
 
 /*
  * The bit flag is stored in the ImBuf.ftype variable.

Modified: trunk/blender/source/blender/imbuf/intern/divers.c
===================================================================
--- trunk/blender/source/blender/imbuf/intern/divers.c	2011-12-30 12:44:16 UTC (rev 43003)
+++ trunk/blender/source/blender/imbuf/intern/divers.c	2011-12-30 14:17:11 UTC (rev 43004)
@@ -453,7 +453,8 @@
 
 void IMB_rect_from_float(struct ImBuf *ibuf)
 {
-	int predivide= 0, profile_from;
+	int predivide= (ibuf->flags & IB_cm_predivide);
+	int profile_from;
 
 	/* verify we have a float buffer */
 	if(ibuf->rect_float==NULL)
@@ -485,7 +486,8 @@
 {
 	float *rect_float;
 	uchar *rect_byte;
-	int predivide= 0, profile_from;
+	int predivide= (ibuf->flags & IB_cm_predivide);
+	int profile_from;
 
 	/* verify we have a float buffer */
 	if(ibuf->rect_float==NULL || buffer==NULL)
@@ -521,7 +523,8 @@
 
 void IMB_float_from_rect(struct ImBuf *ibuf)
 {
-	int predivide= 0, profile_from;
+	int predivide= (ibuf->flags & IB_cm_predivide);

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list