[Bf-blender-cvs] [d93e7e64303] blender2.8: UI: Perf: Group fill/border/emboss batches together.

Clément Foucault noreply at git.blender.org
Thu Mar 29 16:36:04 CEST 2018


Commit: d93e7e643031448dad7f407ccb285c3b9cf91034
Author: Clément Foucault
Date:   Thu Mar 29 16:35:45 2018 +0200
Branches: blender2.8
https://developer.blender.org/rBd93e7e643031448dad7f407ccb285c3b9cf91034

UI: Perf: Group fill/border/emboss batches together.

This roughly halves the number of drawcalls from widgetbase_draw.

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

M	source/blender/editors/interface/interface_widgets.c
M	source/blender/gpu/shaders/gpu_shader_2D_widget_base_vert.glsl

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

diff --git a/source/blender/editors/interface/interface_widgets.c b/source/blender/editors/interface/interface_widgets.c
index 183ab6cfbac..3e74f881cfd 100644
--- a/source/blender/editors/interface/interface_widgets.c
+++ b/source/blender/editors/interface/interface_widgets.c
@@ -129,7 +129,8 @@ typedef struct uiWidgetBase {
 		float radi, rad;
 		float facxi, facyi;
 		float round_corners[4];
-		float color1[4], color2[4];
+		float color_inner1[4], color_inner2[4];
+		float color_outline[4], color_emboss[4];
 		float shade_dir, clamp, pad[2];
 	} uniform_params;
 } uiWidgetBase;
@@ -225,10 +226,7 @@ static const uint g_shape_preset_hold_action_face[2][3] = {{2, 0, 1}, {3, 5, 4}}
  * TODO: find a better place. Maybe it's own file?
  **/
 static struct {
-	Gwn_Batch *roundbox_inner;
-	Gwn_Batch *roundbox_edges;
-	Gwn_Batch *roundbox_emboss;
-	Gwn_Batch *anti_tria;
+	Gwn_Batch *roundbox;
 
 	Gwn_VertFormat format;
 	uint vflag_id;
@@ -243,99 +241,102 @@ static Gwn_VertFormat *vflag_format(void)
 	return &g_ui_batch_cache.format;
 }
 
-static void set_roundbox_vertex(
+#define INNER 0
+#define OUTLINE 1
+#define EMBOSS 2
+#define NO_AA WIDGET_AA_JITTER
+
+static void set_roundbox_vertex_data(
+        Gwn_VertBufRaw *vflag_step, uint32_t d)
+{
+	uint32_t *data = GWN_vertbuf_raw_step(vflag_step);
+	*data = d;
+}
+
+static uint32_t set_roundbox_vertex(
         Gwn_VertBufRaw *vflag_step,
-        int corner_id, int corner_v, int jit_v, bool inner, bool emboss)
+        int corner_id, int corner_v, int jit_v, bool inner, bool emboss, int color)
 {
 	uint32_t *data = GWN_vertbuf_raw_step(vflag_step);
 	*data  = corner_id;
 	*data |= corner_v << 2;
 	*data |= jit_v << 6;
+	*data |= color << 12;
 	*data |= (inner) ? (1 << 10) : 0; /* is inner vert */
 	*data |= (emboss) ? (1 << 11) : 0; /* is emboss vert */
+	return *data;
 }
 
-static Gwn_Batch *ui_batch_roundbox_inner_get(void)
+static Gwn_Batch *ui_batch_roundbox_get(void)
 {
-	if (g_ui_batch_cache.roundbox_inner == NULL) {
+	if (g_ui_batch_cache.roundbox == NULL) {
+		uint32_t last_data;
 		Gwn_VertBufRaw vflag_step;
 		Gwn_VertBuf *vbo = GWN_vertbuf_create_with_format(vflag_format());
-		GWN_vertbuf_data_alloc(vbo, WIDGET_SIZE_MAX);
+		int vcount = WIDGET_SIZE_MAX; /* inner */
+		vcount += 2; /* restart */
+		vcount += ((WIDGET_SIZE_MAX + 1) * 2) * WIDGET_AA_JITTER; /* outline (edges) */
+		vcount += 2; /* restart */
+		vcount += ((WIDGET_CURVE_RESOLU * 2) * 2) * WIDGET_AA_JITTER; /* emboss */
+		GWN_vertbuf_data_alloc(vbo, vcount);
 		GWN_vertbuf_attr_get_raw_data(vbo, g_ui_batch_cache.vflag_id, &vflag_step);
-		for (int c = 0; c < 4; c++) {
-			for (int a = 0; a < WIDGET_CURVE_RESOLU; a++) {
-				set_roundbox_vertex(&vflag_step, c, a, WIDGET_AA_JITTER, true, false);
+		/* Inner */
+		for (int c1 = 0, c2 = 3; c1 < 2; c1++, c2--) {
+			for (int a1 = 0, a2 = WIDGET_CURVE_RESOLU -1; a2 >= 0; a1++, a2--) {
+				last_data = set_roundbox_vertex(&vflag_step, c1, a1, NO_AA, true, false, INNER);
+				last_data = set_roundbox_vertex(&vflag_step, c2, a2, NO_AA, true, false, INNER);
 			}
 		}
-		g_ui_batch_cache.roundbox_inner = GWN_batch_create_ex(GWN_PRIM_TRI_FAN, vbo, NULL, GWN_BATCH_OWNS_VBO);
-	}
-	return g_ui_batch_cache.roundbox_inner;
-}
-
-static Gwn_Batch *ui_batch_roundbox_edges_get(void)
-{
-	if (g_ui_batch_cache.roundbox_edges == NULL) {
-		Gwn_VertBufRaw vflag_step;
-		Gwn_VertBuf *vbo = GWN_vertbuf_create_with_format(vflag_format());
-		GWN_vertbuf_data_alloc(vbo, ((WIDGET_SIZE_MAX + 1) * 2) * WIDGET_AA_JITTER);
-		GWN_vertbuf_attr_get_raw_data(vbo, g_ui_batch_cache.vflag_id, &vflag_step);
+		/* restart */
+		set_roundbox_vertex_data(&vflag_step, last_data);
+		set_roundbox_vertex(&vflag_step, 0, 0, 0, true, false, OUTLINE);
+		/* Outlines */
 		for (int j = 0; j < WIDGET_AA_JITTER; j++) {
 			for (int c = 0; c < 4; c++) {
 				for (int a = 0; a < WIDGET_CURVE_RESOLU; a++) {
-					set_roundbox_vertex(&vflag_step, c, a, j, true, false);
-					set_roundbox_vertex(&vflag_step, c, a, j, false, false);
+					set_roundbox_vertex(&vflag_step, c, a, j, true, false, OUTLINE);
+					set_roundbox_vertex(&vflag_step, c, a, j, false, false, OUTLINE);
 				}
 			}
 			/* Close the loop. */
-			set_roundbox_vertex(&vflag_step, 0, 0, j, true, false);
-			set_roundbox_vertex(&vflag_step, 0, 0, j, false, false);
+			set_roundbox_vertex(&vflag_step, 0, 0, j, true, false, OUTLINE);
+			last_data = set_roundbox_vertex(&vflag_step, 0, 0, j, false, false, OUTLINE);
 		}
-		g_ui_batch_cache.roundbox_edges = GWN_batch_create_ex(GWN_PRIM_TRI_STRIP, vbo, NULL, GWN_BATCH_OWNS_VBO);
-	}
-	return g_ui_batch_cache.roundbox_edges;
-}
-
-static Gwn_Batch *ui_batch_roundbox_emboss_get(void)
-{
-	if (g_ui_batch_cache.roundbox_emboss == NULL) {
-		Gwn_VertBufRaw vflag_step;
-		Gwn_VertBuf *vbo = GWN_vertbuf_create_with_format(vflag_format());
-		GWN_vertbuf_data_alloc(vbo, ((WIDGET_CURVE_RESOLU * 2) * 2) * WIDGET_AA_JITTER);
-		GWN_vertbuf_attr_get_raw_data(vbo, g_ui_batch_cache.vflag_id, &vflag_step);
+		/* restart */
+		set_roundbox_vertex_data(&vflag_step, last_data);
+		set_roundbox_vertex(&vflag_step, 0, 0, 0, false, false, EMBOSS);
+		/* Emboss */
 		bool rev = false; /* go back and forth : avoid degenerate triangle (beware of backface cull) */
 		for (int j = 0; j < WIDGET_AA_JITTER; j++, rev = !rev) {
 			for (int c = (rev) ? 1 : 0; (rev) ? c >= 0 : c < 2; (rev) ? c-- : c++) {
 				int sta = (rev) ? WIDGET_CURVE_RESOLU - 1 : 0;
 				int end = WIDGET_CURVE_RESOLU;
 				for (int a = sta; (rev) ? a >= 0 : a < end; (rev) ? a-- : a++) {
-					set_roundbox_vertex(&vflag_step, c, a, j, false, false);
-					set_roundbox_vertex(&vflag_step, c, a, j, false, true);
+					set_roundbox_vertex(&vflag_step, c, a, j, false, false, EMBOSS);
+					set_roundbox_vertex(&vflag_step, c, a, j, false, true, EMBOSS);
 				}
 			}
 		}
-		g_ui_batch_cache.roundbox_emboss = GWN_batch_create_ex(GWN_PRIM_TRI_STRIP, vbo, NULL, GWN_BATCH_OWNS_VBO);
+		g_ui_batch_cache.roundbox = GWN_batch_create_ex(GWN_PRIM_TRI_STRIP, vbo, NULL, GWN_BATCH_OWNS_VBO);
 	}
-	return g_ui_batch_cache.roundbox_emboss;
+	return g_ui_batch_cache.roundbox;
 }
 
+#undef INNER
+#undef OUTLINE
+#undef EMBOSS
+#undef NO_AA
+
 void ui_widget_batch_preset_reset(void)
 {
-	if (g_ui_batch_cache.roundbox_inner) {
-		gwn_batch_vao_cache_clear(g_ui_batch_cache.roundbox_inner);
-	}
-	if (g_ui_batch_cache.roundbox_edges) {
-		gwn_batch_vao_cache_clear(g_ui_batch_cache.roundbox_edges);
-	}
-	if (g_ui_batch_cache.roundbox_emboss) {
-		gwn_batch_vao_cache_clear(g_ui_batch_cache.roundbox_emboss);
+	if (g_ui_batch_cache.roundbox) {
+		gwn_batch_vao_cache_clear(g_ui_batch_cache.roundbox);
 	}
 }
 
 void ui_widget_batch_preset_exit(void)
 {
-	GWN_BATCH_DISCARD_SAFE(g_ui_batch_cache.roundbox_inner);
-	GWN_BATCH_DISCARD_SAFE(g_ui_batch_cache.roundbox_edges);
-	GWN_BATCH_DISCARD_SAFE(g_ui_batch_cache.roundbox_emboss);
+	GWN_BATCH_DISCARD_SAFE(g_ui_batch_cache.roundbox);
 }
 
 /* ************************************************* */
@@ -834,22 +835,32 @@ static void widgetbase_outline(uiWidgetBase *wtb, unsigned int pos)
 	widget_draw_vertex_buffer(pos, 0, GL_TRIANGLE_STRIP, triangle_strip, NULL, wtb->totvert * 2 + 2);
 }
 
-static void widgetbase_set_uniform_colors_ubv(uiWidgetBase *wtb, const unsigned char *col1, const unsigned char *col2)
+static void widgetbase_set_uniform_colors_ubv(
+        uiWidgetBase *wtb,
+        const unsigned char *col1, const unsigned char *col2,
+        const unsigned char *outline,
+        const unsigned char *emboss)
 {
-	rgba_float_args_set_ch(wtb->uniform_params.color1, col1[0], col1[1], col1[2], col1[3]);
-	rgba_float_args_set_ch(wtb->uniform_params.color2, col2[0], col2[1], col2[2], col2[3]);
+	rgba_float_args_set_ch(wtb->uniform_params.color_inner1, col1[0], col1[1], col1[2], col1[3]);
+	rgba_float_args_set_ch(wtb->uniform_params.color_inner2, col2[0], col2[1], col2[2], col2[3]);
+	rgba_float_args_set_ch(wtb->uniform_params.color_outline, outline[0], outline[1], outline[2], outline[3]);
+	rgba_float_args_set_ch(wtb->uniform_params.color_emboss, emboss[0], emboss[1], emboss[2], emboss[3]);
 }
 
 static void draw_widgetbase_batch(Gwn_Batch *batch, uiWidgetBase *wtb)
 {
 	GWN_batch_program_set_builtin(batch, GPU_SHADER_2D_WIDGET_BASE);
-	GWN_batch_uniform_4fv_array(batch, "parameters", 7, (float *)&wtb->uniform_params);
+	GWN_batch_uniform_4fv_array(batch, "parameters", 9, (float *)&wtb->uniform_params);
 	GWN_batch_draw(batch);
 }
 
 static void widgetbase_draw(uiWidgetBase *wtb, uiWidgetColors *wcol)
 {
 	int a;
+	unsigned char inner_col1[4] = {0};
+	unsigned char inner_col2[4] = {0};
+	unsigned char emboss_col[4] = {0};
+	unsigned char outline_col[4] = {0};
 	glEnable(GL_BLEND);
 
 	/* backdrop non AA */
@@ -899,49 +910,39 @@ static void widgetbase_draw(uiWidgetBase *wtb, uiWidgetColors *wcol)
 			}
 			else {
 				/* simple fill */
-				widgetbase_set_uniform_colors_ubv(wtb, (unsigned char *)wcol->inner, (unsigned char *)wcol->inner);
-
-				Gwn_Batch *inner_batch = ui_batch_roundbox_inner_get();
-				draw_widgetbase_batch(inner_batch, wtb);
+				inner_col1[0] = inner_col2[0] = (unsigned char)wcol->inner[0];
+				inner_col1[1] = inner_col2[1] = (unsigned char)wcol->inner[1];
+				inner_col1[2] = inner_col2[2] = (unsigned char)wcol->inner[2];
+				inner_col1[3] = inner_col2[3] = (unsigned char)wcol->inner[3];
 			}
 		}
 		else {
-			char col1[4], col2[4];
-			shadecolors4(col1, col2, wcol->inner, wcol->shadetop, wcol->shadedown);
-			widgetbase_set_uniform_colors_ubv(wtb, (unsigned char *)col1, (unsigned char *)col2);
-
-			Gwn_Batch *inner_batch = ui_batch_roundbox_inner_get();
-			draw_widgetbase_batch(inner_batch, wtb);
+			/* gradient fill */
+			shadecolors4((char *)inner_col1, (char *)inner_col2, wcol->inner, wcol->shadetop, wcol->shadedown);
 		}
 	}
 
-	/* for each AA step */
 	if (wtb->draw_outline) {
-		BLI_assert(wtb->totvert != 0);
-		const unsigned char tcol[4] = {wcol->outline[0],
-		                               wcol->outline[1],
-		                               wcol->outline[2],
-		                               wcol->outline[3] / WIDGET_AA_JITTER};
-
-		/* outline */
-		widgetbase_set_uniform_colors_ubv(wtb, tcol, tcol);
-
-		Gwn_Batch *ed

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list