[Bf-blender-cvs] [0597429] soc-2013-paint: Support for drawing the stencil layer in the viewport.

Antony Riakiotakis noreply at git.blender.org
Fri Apr 25 22:33:20 CEST 2014


Commit: 05974290063c75e4405c36c86082e42bb8d81847
Author: Antony Riakiotakis
Date:   Fri Apr 25 23:31:17 2014 +0300
https://developer.blender.org/rB05974290063c75e4405c36c86082e42bb8d81847

Support for drawing the stencil layer in the viewport.

This should give much better preview of which part is paintable.
Unfortunately only supported in blender internal for now.

===================================================================

M	source/blender/blenloader/intern/readfile.c
M	source/blender/editors/sculpt_paint/paint_image_proj.c
M	source/blender/editors/space_view3d/drawmesh.c
M	source/blender/gpu/intern/gpu_buffers.c

===================================================================

diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index 654b7a7..1d2f630 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -5159,6 +5159,10 @@ static void lib_link_scene(FileData *fd, Main *main)
 				sce->toolsettings->sculpt->gravity_object =
 						newlibadr_us(fd, sce->id.lib, sce->toolsettings->sculpt->gravity_object);
 
+			if (sce->toolsettings->imapaint.stencil)
+				sce->toolsettings->imapaint.stencil =
+				        newlibadr_us(fd, sce->id.lib, sce->toolsettings->imapaint.stencil);
+
 			sce->toolsettings->skgen_template = newlibadr(fd, sce->id.lib, sce->toolsettings->skgen_template);
 			
 			for (base = sce->base.first; base; base = next) {
diff --git a/source/blender/editors/sculpt_paint/paint_image_proj.c b/source/blender/editors/sculpt_paint/paint_image_proj.c
index 7eff47a..482ab12 100644
--- a/source/blender/editors/sculpt_paint/paint_image_proj.c
+++ b/source/blender/editors/sculpt_paint/paint_image_proj.c
@@ -3296,6 +3296,10 @@ static void project_paint_begin(ProjPaintState *ps)
 			slot_last = slot;
 		}
 
+		/* don't allow using the same inage for painting and stencilling */
+		if (slot->ima == ps->stencil_ima)
+			continue;
+
 		*tf = tf_base + face_index;
 
 		if (ps->do_layer_clone) {
diff --git a/source/blender/editors/space_view3d/drawmesh.c b/source/blender/editors/space_view3d/drawmesh.c
index 70371c3..8f3b516 100644
--- a/source/blender/editors/space_view3d/drawmesh.c
+++ b/source/blender/editors/space_view3d/drawmesh.c
@@ -216,12 +216,13 @@ static Material *give_current_material_or_def(Object *ob, int matnr)
 
 static struct TextureDrawState {
 	Object *ob;
+	Image *stencil;
 	bool use_game_mat;
 	int is_lit, is_tex;
 	int color_profile;
 	bool use_backface_culling;
 	unsigned char obcol[4];
-} Gtexdraw = {NULL, false, 0, 0, 0, false, {0, 0, 0, 0}};
+} Gtexdraw = {NULL, NULL, false, 0, 0, 0, false, {0, 0, 0, 0}};
 
 static bool set_draw_settings_cached(int clearcache, MTFace *texface, Material *ma, struct TextureDrawState gtexdraw)
 {
@@ -248,6 +249,18 @@ static bool set_draw_settings_cached(int clearcache, MTFace *texface, Material *
 		c_badtex = false;
 		c_has_texface = -1;
 		c_ma = NULL;
+
+		/* load the stencil texture here */
+		if ((Gtexdraw.ob->mode & OB_MODE_TEXTURE_PAINT) && (Gtexdraw.stencil != NULL)) {
+			glActiveTexture(GL_TEXTURE1);
+			if (GPU_verify_image(Gtexdraw.stencil, NULL, 0, 1, 0, false)) {
+				glEnable(GL_TEXTURE_2D);
+				glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_COMBINE);
+				glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB, GL_MODULATE);
+				glTexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA, GL_MODULATE);
+			}
+			glActiveTexture(GL_TEXTURE0);
+		}
 	}
 	else {
 		textured = gtexdraw.is_tex;
@@ -350,6 +363,7 @@ static void draw_textured_begin(Scene *scene, View3D *v3d, RegionView3D *rv3d, O
 	unsigned char obcol[4];
 	bool is_tex, solidtex;
 	Mesh *me = ob->data;
+	ImagePaintSettings *imapaint = &scene->toolsettings->imapaint;
 
 	/* XXX scene->obedit warning */
 
@@ -379,6 +393,7 @@ static void draw_textured_begin(Scene *scene, View3D *v3d, RegionView3D *rv3d, O
 	else is_tex = false;
 
 	Gtexdraw.ob = ob;
+	Gtexdraw.stencil = (imapaint->flag & IMAGEPAINT_PROJECT_LAYER_STENCIL) ? imapaint->stencil : NULL;
 	Gtexdraw.is_tex = is_tex;
 
 	Gtexdraw.color_profile = BKE_scene_check_color_management_enabled(scene);
@@ -397,6 +412,14 @@ static void draw_textured_end(void)
 	/* switch off textures */
 	GPU_set_tpage(NULL, 0, 0);
 
+	if(Gtexdraw.ob->mode & OB_MODE_TEXTURE_PAINT) {
+		glActiveTexture(GL_TEXTURE1);
+		GPU_set_tpage(NULL, 0, 0);
+		glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
+		glBindTexture(GL_TEXTURE_2D, 0);
+		glActiveTexture(GL_TEXTURE0);
+	}
+
 	glShadeModel(GL_FLAT);
 	glDisable(GL_CULL_FACE);
 	glLightModeli(GL_LIGHT_MODEL_TWO_SIDE, GL_FALSE);
diff --git a/source/blender/gpu/intern/gpu_buffers.c b/source/blender/gpu/intern/gpu_buffers.c
index c3b804f..86837f0 100644
--- a/source/blender/gpu/intern/gpu_buffers.c
+++ b/source/blender/gpu/intern/gpu_buffers.c
@@ -64,13 +64,16 @@
 typedef enum {
 	GPU_BUFFER_VERTEX_STATE = 1,
 	GPU_BUFFER_NORMAL_STATE = 2,
-	GPU_BUFFER_TEXCOORD_STATE = 4,
-	GPU_BUFFER_COLOR_STATE = 8,
-	GPU_BUFFER_ELEMENT_STATE = 16,
+	GPU_BUFFER_TEXCOORD_STATE_UNIT_0 = 4,
+	GPU_BUFFER_TEXCOORD_STATE_UNIT_1 = 8,
+	GPU_BUFFER_COLOR_STATE = 16,
+	GPU_BUFFER_ELEMENT_STATE = 32,
 } GPUBufferState;
 
 #define MAX_GPU_ATTRIB_DATA 32
 
+#define BUFFER_OFFSET(n) ((GLubyte *)NULL + (n))
+
 /* -1 - undefined, 0 - vertex arrays, 1 - VBOs */
 static int useVBOs = -1;
 static GPUBufferState GLStates = 0;
@@ -845,6 +848,8 @@ static void GPU_buffer_copy_uv_texpaint(DerivedMesh *dm, float *varray, int *ind
 
 	int totmaterial = dm->totmat;
 	MTFace **mtface_base;
+	MTFace *stencil_base;
+	int stencil;
 	MFace *f;
 
 	/* should have been checked for before, reassert */
@@ -863,6 +868,9 @@ static void GPU_buffer_copy_uv_texpaint(DerivedMesh *dm, float *varray, int *ind
 			mtface_base[i] = CustomData_get_layer(&dm->faceData, CD_MTFACE);
 	}
 
+	stencil = CustomData_get_stencil_layer(&dm->faceData, CD_MTFACE);
+	stencil_base = CustomData_get_layer_n(&dm->faceData, CD_MTFACE, stencil);
+
 	totface = dm->getNumTessFaces(dm);
 
 	for (i = 0; i < totface; i++, f++) {
@@ -871,21 +879,26 @@ static void GPU_buffer_copy_uv_texpaint(DerivedMesh *dm, float *varray, int *ind
 
 		/* v1 v2 v3 */
 		copy_v2_v2(&varray[start], mtface_base[mat_i][i].uv[0]);
-		copy_v2_v2(&varray[start + 2], mtface_base[mat_i][i].uv[1]);
-		copy_v2_v2(&varray[start + 4], mtface_base[mat_i][i].uv[2]);
-		index[mat_orig_to_new[f->mat_nr]] += 6;
+		copy_v2_v2(&varray[start + 2], stencil_base[i].uv[0]);
+		copy_v2_v2(&varray[start + 4], mtface_base[mat_i][i].uv[1]);
+		copy_v2_v2(&varray[start + 6], stencil_base[i].uv[1]);
+		copy_v2_v2(&varray[start + 8], mtface_base[mat_i][i].uv[2]);
+		copy_v2_v2(&varray[start + 10], stencil_base[i].uv[2]);
+		index[mat_orig_to_new[mat_i]] += 12;
 
 		if (f->v4) {
 			/* v3 v4 v1 */
-			copy_v2_v2(&varray[start + 6], mtface_base[mat_i][i].uv[2]);
-			copy_v2_v2(&varray[start + 8], mtface_base[mat_i][i].uv[3]);
-			copy_v2_v2(&varray[start + 10], mtface_base[mat_i][i].uv[0]);
-			index[mat_orig_to_new[f->mat_nr]] += 6;
+			copy_v2_v2(&varray[start + 12], mtface_base[mat_i][i].uv[2]);
+			copy_v2_v2(&varray[start + 14], stencil_base[i].uv[2]);
+			copy_v2_v2(&varray[start + 16], mtface_base[mat_i][i].uv[3]);
+			copy_v2_v2(&varray[start + 18], stencil_base[i].uv[3]);
+			copy_v2_v2(&varray[start + 20], mtface_base[mat_i][i].uv[0]);
+			copy_v2_v2(&varray[start + 22], stencil_base[i].uv[0]);
+			index[mat_orig_to_new[mat_i]] += 12;
 		}
 	}
 
-	if (mtface_base)
-		MEM_freeN(mtface_base);
+	MEM_freeN(mtface_base);
 }
 
 
@@ -994,7 +1007,7 @@ const GPUBufferTypeSettings gpu_buffer_type_settings[] = {
 	{GPU_buffer_copy_normal, GL_ARRAY_BUFFER_ARB, 3},
 	{GPU_buffer_copy_mcol, GL_ARRAY_BUFFER_ARB, 3},
 	{GPU_buffer_copy_uv, GL_ARRAY_BUFFER_ARB, 2},
-    {GPU_buffer_copy_uv_texpaint, GL_ARRAY_BUFFER_ARB, 2},
+    {GPU_buffer_copy_uv_texpaint, GL_ARRAY_BUFFER_ARB, 4},
 	{GPU_buffer_copy_edge, GL_ELEMENT_ARRAY_BUFFER_ARB, 2},
 	{GPU_buffer_copy_uvedge, GL_ELEMENT_ARRAY_BUFFER_ARB, 4}
 };
@@ -1035,7 +1048,7 @@ static int gpu_buffer_size_from_type(DerivedMesh *dm, GPUBufferType type)
 		case GPU_BUFFER_UV:
 			return sizeof(float) * 2 * dm->drawObject->tot_triangle_point;
 		case GPU_BUFFER_UV_TEXPAINT:
-			return sizeof(float) * 2 * dm->drawObject->tot_triangle_point;
+			return sizeof(float) * 4 * dm->drawObject->tot_triangle_point;
 		case GPU_BUFFER_EDGE:
 			return sizeof(int) * 2 * dm->drawObject->totedge;
 		case GPU_BUFFER_UVEDGE:
@@ -1140,7 +1153,7 @@ void GPU_uv_setup(DerivedMesh *dm)
 		glTexCoordPointer(2, GL_FLOAT, 0, dm->drawObject->uv->pointer);
 	}
 
-	GLStates |= GPU_BUFFER_TEXCOORD_STATE;
+	GLStates |= GPU_BUFFER_TEXCOORD_STATE_UNIT_0;
 }
 
 void GPU_texpaint_uv_setup(DerivedMesh *dm)
@@ -1151,13 +1164,21 @@ void GPU_texpaint_uv_setup(DerivedMesh *dm)
 	glEnableClientState(GL_TEXTURE_COORD_ARRAY);
 	if (useVBOs) {
 		glBindBufferARB(GL_ARRAY_BUFFER_ARB, dm->drawObject->uv->id);
-		glTexCoordPointer(2, GL_FLOAT, 0, 0);
+		glTexCoordPointer(2, GL_FLOAT, 4 * sizeof(float), 0);
+		glClientActiveTexture(GL_TEXTURE1);
+		glEnableClientState(GL_TEXTURE_COORD_ARRAY);
+		glTexCoordPointer(2, GL_FLOAT, 4 * sizeof(float), BUFFER_OFFSET(2 * sizeof(float)));
+		glClientActiveTexture(GL_TEXTURE0);
 	}
 	else {
-		glTexCoordPointer(2, GL_FLOAT, 0, dm->drawObject->uv->pointer);
+		glTexCoordPointer(2, GL_FLOAT, 4 * sizeof(float), dm->drawObject->uv->pointer);
+		glClientActiveTexture(GL_TEXTURE1);
+		glEnableClientState(GL_TEXTURE_COORD_ARRAY);
+		glTexCoordPointer(2, GL_FLOAT, 4 * sizeof(float), (char *)dm->drawObject->uv->pointer + 2 * sizeof(float));
+		glClientActiveTexture(GL_TEXTURE0);
 	}
 
-	GLStates |= GPU_BUFFER_TEXCOORD_STATE;
+	GLStates |= GPU_BUFFER_TEXCOORD_STATE_UNIT_0 | GPU_BUFFER_TEXCOORD_STATE_UNIT_1;
 }
 
 
@@ -1318,8 +1339,13 @@ void GPU_buffer_unbind(void)
 		glDisableClientState(GL_VERTEX_ARRAY);
 	if (GLStates & GPU_BUFFER_NORMAL_STATE)
 		glDisableClientState(GL_NORMAL_ARRAY);
-	if (GLStates & GPU_BUFFER_TEXCOORD_STATE)
+	if (GLStates & GPU_BUFFER_TEXCOORD_STATE_UNIT_0)
 		glDisableClientState(GL_TEXTURE_COORD_ARRAY);
+	if (GLStates & GPU_BUFFER_TEXCOORD_STATE_UNIT_1) {
+		glClientActiveTexture(GL_TEXTURE1);
+		glDisableClientState(GL_TEXTURE_COORD_ARRAY);
+		glClientActiveTexture(GL_TEXTURE0);
+	}
 	if (GLStates & GPU_BUFFER_COLOR_STATE)
 		glDisableClientState(GL_COLOR_ARRAY);
 	if (GLStates & GPU_BUFFER_ELEMENT_STATE) {
@@ -1328,8 +1354,8 @@ void GPU_buffer_unbind(void)
 		}
 	}
 	GLStates &= ~(GPU_BUFFER_VERTEX_STATE | GPU_BUFFER_NORMAL_STATE |
-	              GPU_BUFFER_TEXCOORD_STATE | GPU_BUFFER_COLOR_STATE |
-	              GPU_BUFFER_ELEMENT_STATE);
+	              GPU_BUFFER_TEXCOORD_STATE_UNIT_0 | GPU_BUFFER_TEXCOORD_STATE_UNIT_1 |
+	              GPU_BUFFER_COLOR_STATE | GPU_BUFFER_ELEMENT_STATE);
 
 	for (i = 0; i < MAX_GPU_ATTRIB_DATA; i++) {
 		if (attribData[i].index != -1) {




More information about the Bf-blender-cvs mailing list