[Bf-blender-cvs] [55ddb21b7ca] master: Mesh Selection: Port to batch cache request

Clément Foucault noreply at git.blender.org
Fri Jan 11 16:00:34 CET 2019


Commit: 55ddb21b7ca79664922699a383130881b7761f43
Author: Clément Foucault
Date:   Sat Dec 22 23:57:12 2018 +0100
Branches: master
https://developer.blender.org/rB55ddb21b7ca79664922699a383130881b7761f43

Mesh Selection: Port to batch cache request

This makes it more future proof and remove baked id offset inside the vbos.
Instead we add the offset as a uniform. This makes it possible to reuse
the vbos instead of discarding them all the time.

Also using batch request may reduce batches creation time.

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

M	source/blender/draw/intern/draw_cache_impl.h
M	source/blender/draw/intern/draw_cache_impl_mesh.c
M	source/blender/editors/space_view3d/drawobject.c

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

diff --git a/source/blender/draw/intern/draw_cache_impl.h b/source/blender/draw/intern/draw_cache_impl.h
index 385147039d6..dfdbd7f47e7 100644
--- a/source/blender/draw/intern/draw_cache_impl.h
+++ b/source/blender/draw/intern/draw_cache_impl.h
@@ -125,11 +125,11 @@ struct GPUBatch *DRW_mesh_batch_cache_get_edit_loose_edges_nor(struct Mesh *me);
 struct GPUBatch *DRW_mesh_batch_cache_get_edit_loose_verts(struct Mesh *me);
 struct GPUBatch *DRW_mesh_batch_cache_get_edit_facedots(struct Mesh *me);
 /* edit-mesh selection */
-struct GPUBatch *DRW_mesh_batch_cache_get_triangles_with_select_id(struct Mesh *me, bool use_hide, uint select_id_offset);
-struct GPUBatch *DRW_mesh_batch_cache_get_triangles_with_select_mask(struct Mesh *me, bool use_hide);
-struct GPUBatch *DRW_mesh_batch_cache_get_facedots_with_select_id(struct Mesh *me, uint select_id_offset);
-struct GPUBatch *DRW_mesh_batch_cache_get_edges_with_select_id(struct Mesh *me, uint select_id_offset);
-struct GPUBatch *DRW_mesh_batch_cache_get_verts_with_select_id(struct Mesh *me, uint select_id_offset);
+struct GPUBatch *DRW_mesh_batch_cache_get_triangles_with_select_id(struct Mesh *me);
+struct GPUBatch *DRW_mesh_batch_cache_get_triangles_with_select_mask(struct Mesh *me);
+struct GPUBatch *DRW_mesh_batch_cache_get_facedots_with_select_id(struct Mesh *me);
+struct GPUBatch *DRW_mesh_batch_cache_get_edges_with_select_id(struct Mesh *me);
+struct GPUBatch *DRW_mesh_batch_cache_get_verts_with_select_id(struct Mesh *me);
 /* Object mode Wireframe overlays */
 struct GPUBatch *DRW_mesh_batch_cache_get_wireframes_face(struct Mesh *me);
 
diff --git a/source/blender/draw/intern/draw_cache_impl_mesh.c b/source/blender/draw/intern/draw_cache_impl_mesh.c
index be37787ae7c..6e28bd6a916 100644
--- a/source/blender/draw/intern/draw_cache_impl_mesh.c
+++ b/source/blender/draw/intern/draw_cache_impl_mesh.c
@@ -1236,6 +1236,12 @@ static int mesh_render_data_loops_len_get(const MeshRenderData *rdata)
 	return rdata->loop_len;
 }
 
+static int mesh_render_data_loops_len_get_maybe_mapped(const MeshRenderData *rdata)
+{
+	BLI_assert(rdata->types & MR_DATATYPE_LOOP);
+	return ((rdata->mapped.use == false) ? rdata->loop_len : rdata->mapped.loop_len);
+}
+
 static int mesh_render_data_polys_len_get(const MeshRenderData *rdata)
 {
 	BLI_assert(rdata->types & MR_DATATYPE_POLY);
@@ -1952,7 +1958,7 @@ static bool drw_mesh_weight_state_compare(const struct DRW_MeshWeightState *a, c
 }
 
 static void drw_mesh_weight_state_extract(
-        Object *ob, Mesh *me, ToolSettings *ts, bool paint_mode,
+        Object *ob, Mesh *me, const ToolSettings *ts, bool paint_mode,
         struct DRW_MeshWeightState *wstate)
 {
 	/* Extract complete vertex weight group selection state and mode flags. */
@@ -2022,6 +2028,12 @@ typedef struct MeshBatchCache {
 		GPUVertBuf *data_ledges;
 		GPUVertBuf *data_lverts;
 		GPUVertBuf *lnor;
+		/* Selection */
+		GPUVertBuf *loop_pos;
+		GPUVertBuf *loop_vert_idx;
+		GPUVertBuf *loop_edge_idx;
+		GPUVertBuf *loop_face_idx;
+		GPUVertBuf *facedots_idx;
 	} edit;
 
 	/* Index Buffers:
@@ -2038,6 +2050,10 @@ typedef struct MeshBatchCache {
 		/* Contains indices to unique edit vertices to not
 		 * draw the same vert multiple times (because of tesselation). */
 		GPUIndexBuf *edit_verts_points;
+		/* Edit mode selection. */
+		GPUIndexBuf *edit_loops_points; /* verts */
+		GPUIndexBuf *edit_loops_lines; /* edges */
+		GPUIndexBuf *edit_loops_tris; /* faces */
 	} ibo;
 
 	struct {
@@ -2053,6 +2069,11 @@ typedef struct MeshBatchCache {
 		GPUBatch *edit_triangles_lnor;
 		GPUBatch *edit_loose_edges_nor;
 		GPUBatch *edit_facedots;
+		/* Edit selection */
+		GPUBatch *edit_selection_verts;
+		GPUBatch *edit_selection_edges;
+		GPUBatch *edit_selection_faces;
+		GPUBatch *edit_selection_facedots;
 		/* Common display / Other */
 		GPUBatch *all_verts;
 		GPUBatch *all_edges;
@@ -2729,460 +2750,327 @@ static void mesh_create_pos_and_nor_tess(MeshRenderData *rdata, GPUVertBuf *vbo,
 	}
 }
 
-static GPUVertBuf *mesh_batch_cache_get_tri_pos_and_normals_ex(
-        MeshRenderData *rdata, const bool use_hide,
-        GPUVertBuf **r_vbo)
+BLI_INLINE void mesh_edit_add_select_index(GPUVertBufRaw *buf, GPUVertCompType comp, uint index)
 {
-	BLI_assert(rdata->types & (MR_DATATYPE_VERT | MR_DATATYPE_LOOPTRI | MR_DATATYPE_LOOP | MR_DATATYPE_POLY));
-
-	if (*r_vbo == NULL) {
-		*r_vbo = GPU_vertbuf_create(GPU_USAGE_STATIC);
-		mesh_create_pos_and_nor_tess(rdata, *r_vbo, use_hide);
+	/* We don't need to sanitize the value because the elements
+	 * with these undefined values will never get drawn. */
+	switch (comp) {
+		case GPU_COMP_U32:
+			*((uint *)GPU_vertbuf_raw_step(buf)) = index;
+			break;
+		case GPU_COMP_U16:
+			*((ushort *)GPU_vertbuf_raw_step(buf)) = (ushort)index;
+			break;
+		case GPU_COMP_U8:
+			*((uchar *)GPU_vertbuf_raw_step(buf)) = (uchar)index;
+			break;
+		default:
+			BLI_assert(0);
+			break;
 	}
-	return *r_vbo;
 }
 
-static GPUVertBuf *mesh_batch_cache_get_tri_pos_and_normals_edit(
-        MeshRenderData *rdata, MeshBatchCache *cache, bool use_hide)
-{
-	return mesh_batch_cache_get_tri_pos_and_normals_ex(
-	        rdata, use_hide,
-	        use_hide ? &cache->pos_with_normals_visible_only_edit : &cache->pos_with_normals_edit);
-}
+#define SELECT_COMP_FORMAT(el_len) (el_len > 0xFF ? (el_len > 0xFFFF ? GPU_COMP_U32 : GPU_COMP_U16) : GPU_COMP_U8)
 
-/* DEPRECATED Need to be ported */
-static GPUVertBuf *mesh_batch_cache_get_facedot_pos_with_normals_and_flag(
-        MeshRenderData *rdata, MeshBatchCache *cache)
-{
-	BLI_assert(rdata->types & (MR_DATATYPE_VERT | MR_DATATYPE_LOOP | MR_DATATYPE_POLY));
-
-	if (cache->edit.pos_nor_data_facedots == NULL) {
-		cache->edit.pos_nor_data_facedots = GPU_vertbuf_create(GPU_USAGE_STATIC);
-		mesh_create_edit_facedots(rdata, cache->edit.pos_nor_data_facedots);
-	}
-
-	return cache->edit.pos_nor_data_facedots;
-}
-
-static GPUVertBuf *mesh_batch_cache_get_edges_visible(
-        MeshRenderData *rdata, MeshBatchCache *cache)
+static void mesh_create_edit_select_id(
+        MeshRenderData *rdata,
+        GPUVertBuf *vbo_pos, GPUVertBuf *vbo_verts, GPUVertBuf *vbo_edges, GPUVertBuf *vbo_faces)
 {
-	BLI_assert(rdata->types & (MR_DATATYPE_VERT | MR_DATATYPE_EDGE));
-
-	if (cache->ed_edge_pos == NULL) {
-		static GPUVertFormat format = { 0 };
-		static struct { uint pos, data; } attr_id;
-		if (format.attr_len == 0) {
-			attr_id.pos = GPU_vertformat_attr_add(&format, "pos", GPU_COMP_F32, 3, GPU_FETCH_FLOAT);
-		}
-
-		const int vbo_len_capacity = mesh_render_data_edges_len_get_maybe_mapped(rdata) * 2;
-		int vidx = 0;
-
-		GPUVertBuf *vbo = cache->ed_edge_pos = GPU_vertbuf_create_with_format(&format);
-		GPU_vertbuf_data_alloc(vbo, vbo_len_capacity);
-
-		if (rdata->mapped.use == false) {
-			if (rdata->edit_bmesh) {
-				BMesh *bm = rdata->edit_bmesh->bm;
-				BMIter iter;
-				BMEdge *eed;
+	const int vert_len = mesh_render_data_verts_len_get_maybe_mapped(rdata);
+	const int edge_len = mesh_render_data_edges_len_get_maybe_mapped(rdata);
+	const int poly_len = mesh_render_data_polys_len_get_maybe_mapped(rdata);
+	const int lvert_len = mesh_render_data_loose_verts_len_get_maybe_mapped(rdata);
+	const int ledge_len = mesh_render_data_loose_edges_len_get_maybe_mapped(rdata);
+	const int loop_len = mesh_render_data_loops_len_get_maybe_mapped(rdata);
+	const int tot_loop_len = loop_len + ledge_len * 2 + lvert_len;
+
+	/* Choose the most compact vertex format. */
+	GPUVertCompType vert_comp = SELECT_COMP_FORMAT(vert_len);
+	GPUVertCompType edge_comp = SELECT_COMP_FORMAT(edge_len);
+	GPUVertCompType face_comp = SELECT_COMP_FORMAT(poly_len);
+
+	GPUVertFormat format_vert = { 0 }, format_edge = { 0 }, format_face = { 0 }, format_pos = { 0 };
+	struct { uint vert, edge, face, pos; } attr_id;
+	attr_id.vert = GPU_vertformat_attr_add(&format_vert, "color", vert_comp, 1, GPU_FETCH_INT);
+	attr_id.edge = GPU_vertformat_attr_add(&format_edge, "color", edge_comp, 1, GPU_FETCH_INT);
+	attr_id.face = GPU_vertformat_attr_add(&format_face, "color", face_comp, 1, GPU_FETCH_INT);
+	attr_id.pos  = GPU_vertformat_attr_add(&format_pos, "pos", GPU_COMP_F32, 3, GPU_FETCH_FLOAT);
+
+	GPUVertBufRaw raw_verts, raw_edges, raw_faces, raw_pos;
+	if (DRW_TEST_ASSIGN_VBO(vbo_pos)) {
+		GPU_vertbuf_init_with_format(vbo_pos, &format_pos);
+		GPU_vertbuf_data_alloc(vbo_pos, tot_loop_len);
+		GPU_vertbuf_attr_get_raw_data(vbo_pos, attr_id.pos, &raw_pos);
+	}
+	if (DRW_TEST_ASSIGN_VBO(vbo_verts)) {
+		GPU_vertbuf_init_with_format(vbo_verts, &format_vert);
+		GPU_vertbuf_data_alloc(vbo_verts, tot_loop_len);
+		GPU_vertbuf_attr_get_raw_data(vbo_verts, attr_id.vert, &raw_verts);
+	}
+	if (DRW_TEST_ASSIGN_VBO(vbo_edges)) {
+		GPU_vertbuf_init_with_format(vbo_edges, &format_edge);
+		GPU_vertbuf_data_alloc(vbo_edges, tot_loop_len);
+		GPU_vertbuf_attr_get_raw_data(vbo_edges, attr_id.edge, &raw_edges);
+	}
+	if (DRW_TEST_ASSIGN_VBO(vbo_faces)) {
+		GPU_vertbuf_init_with_format(vbo_faces, &format_face);
+		GPU_vertbuf_data_alloc(vbo_faces, tot_loop_len);
+		GPU_vertbuf_attr_get_raw_data(vbo_faces, attr_id.face, &raw_faces);
+	}
+
+	if (rdata->edit_bmesh && rdata->mapped.use == false) {
+		BMesh *bm = rdata->edit_bmesh->bm;
+		BMIter iter_efa, iter_loop, iter_edge, iter_vert;
+		BMFace *efa;
+		BMEdge *eed;
+		BMVert *eve;
+		BMLoop *loop;
 
-				BM_ITER_MESH (eed, &iter, bm, BM_EDGES_OF_MESH) {
-					if (!BM_elem_flag_test(eed, BM_ELEM_HIDDEN)) {
-						GPU_vertbuf_attr_set(vbo, attr_id.pos, vidx, eed->v1->co);
-						vidx += 1;
-						GPU_vertbuf_attr_set(vbo, attr_id.pos, vidx, eed->v2->co);
-						vidx += 1;
-					}
+		/* Face Loops */
+		BM_ITER_MESH (efa, &iter_efa, bm, BM_FACES_OF_MESH) {
+			int fidx = BM_elem_index_get(efa);
+			BM_ITER_ELEM (loop, &iter_loop, efa, BM_LOOPS_OF_FACE) {
+				if (vbo_pos) {
+					copy_v3_v3(GPU_vertbuf_raw_step(&raw_pos), loop->v->co);
 				}
-			}
-			else {
-				/* not yet done! */
-				BLI_assert(0);
-			}
-		}
-		else {
-			BMesh *bm = rdata->edit_bmesh->bm;
-			const MVert *mvert = rdata->mapped.me_cage->mvert;
-			const MEdge *medge = rdata->mapped.me_cage->medge;
-			const int *e_origindex = rdata->mapped.e_origindex;
-			for (int i = 0; i < rdata-

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list