Commit: 26fc6c71c411e9ba3650a8f5dbb16167a528f984
Author: Clément Foucault
Date:   Wed Mar 1 14:07:04 2017 +0100
Branches: blender2.8
https://developer.blender.org/rB26fc6c71c411e9ba3650a8f5dbb16167a528f984

Edit Mode overlays: separate multiple shaders for loose edges and verts

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

M       source/blender/blenkernel/BKE_mesh_render.h
M       source/blender/blenkernel/intern/mesh_render.c
M       source/blender/draw/intern/draw_cache.c
M       source/blender/draw/intern/draw_cache.h
M       source/blender/draw/intern/draw_mode_pass.c
M       source/blender/draw/intern/draw_mode_pass.h
M       source/blender/draw/modes/edit_mesh_mode.c
M       source/blender/editors/space_view3d/drawobject.c
M       source/blender/gpu/CMakeLists.txt
M       source/blender/gpu/GPU_shader.h
M       source/blender/gpu/intern/gpu_shader.c
A       source/blender/gpu/shaders/gpu_shader_edit_overlay_geom_edge.glsl
R083    source/blender/gpu/shaders/gpu_shader_edit_overlay_geom.glsl    
source/blender/gpu/shaders/gpu_shader_edit_overlay_geom_tri.glsl
A       source/blender/gpu/shaders/gpu_shader_edit_overlay_geom_vert.glsl

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

diff --git a/source/blender/blenkernel/BKE_mesh_render.h 
b/source/blender/blenkernel/BKE_mesh_render.h
index f4e322fca6..0370426d41 100644
--- a/source/blender/blenkernel/BKE_mesh_render.h
+++ b/source/blender/blenkernel/BKE_mesh_render.h
@@ -40,6 +40,8 @@ struct Batch *BKE_mesh_batch_cache_get_all_triangles(struct 
Mesh *me);
 struct Batch *BKE_mesh_batch_cache_get_triangles_with_normals(struct Mesh *me);
 struct Batch *BKE_mesh_batch_cache_get_all_verts(struct Mesh *me);
 struct Batch *BKE_mesh_batch_cache_get_fancy_edges(struct Mesh *me);
-struct Batch *BKE_mesh_batch_cache_get_overlay_edges(struct Mesh *me);
+struct Batch *BKE_mesh_batch_cache_get_overlay_triangles(struct Mesh *me);
+struct Batch *BKE_mesh_batch_cache_get_overlay_loose_edges(struct Mesh *me);
+struct Batch *BKE_mesh_batch_cache_get_overlay_loose_verts(struct Mesh *me);
 
 #endif /* __BKE_MESH_RENDER_H__ */
diff --git a/source/blender/blenkernel/intern/mesh_render.c 
b/source/blender/blenkernel/intern/mesh_render.c
index 2e9ea90792..9488b80f20 100644
--- a/source/blender/blenkernel/intern/mesh_render.c
+++ b/source/blender/blenkernel/intern/mesh_render.c
@@ -123,15 +123,11 @@ typedef struct MeshRenderData {
 
 enum {
        MR_DATATYPE_VERT       = 1 << 0,
-       MR_DATATYPE_LOOSE_VERT = 1 << 1,
-       MR_DATATYPE_EDGE       = 1 << 2,
-       MR_DATATYPE_LOOSE_EDGE = 1 << 3,
-       MR_DATATYPE_LOOPTRI    = 1 << 4,
-       MR_DATATYPE_LOOP       = 1 << 5,
-       MR_DATATYPE_POLY       = 1 << 6,
-       MR_DATATYPE_ACTIVE     = 1 << 7,
-       MR_DATATYPE_CREASE     = 1 << 8,
-       MR_DATATYPE_BWEIGHT    = 1 << 9,
+       MR_DATATYPE_EDGE       = 1 << 1,
+       MR_DATATYPE_LOOPTRI    = 1 << 2,
+       MR_DATATYPE_LOOP       = 1 << 3,
+       MR_DATATYPE_POLY       = 1 << 4,
+       MR_DATATYPE_OVERLAY    = 1 << 5,
 };
 
 static MeshRenderData *mesh_render_data_create(Mesh *me, const int types)
@@ -146,11 +142,11 @@ static MeshRenderData *mesh_render_data_create(Mesh *me, 
const int types)
                mrdata->edit_bmesh = embm;
 
                int bm_ensure_types = 0;
-               if (types & (MR_DATATYPE_VERT | MR_DATATYPE_LOOSE_VERT)) {
+               if (types & (MR_DATATYPE_VERT)) {
                        mrdata->totvert = bm->totvert;
                        bm_ensure_types |= BM_VERT;
                }
-               if (types & (MR_DATATYPE_EDGE | MR_DATATYPE_LOOSE_EDGE)) {
+               if (types & (MR_DATATYPE_EDGE)) {
                        mrdata->totedge = bm->totedge;
                        bm_ensure_types |= BM_EDGE;
                }
@@ -166,72 +162,56 @@ static MeshRenderData *mesh_render_data_create(Mesh *me, 
const int types)
                        mrdata->totpoly = bm->totface;
                        bm_ensure_types |= BM_FACE;
                }
-               if (types & MR_DATATYPE_ACTIVE) {
+               if (types & MR_DATATYPE_OVERLAY) {
                        mrdata->efa_act = BM_mesh_active_face_get(bm, false, 
true);
                        mrdata->eed_act = BM_mesh_active_edge_get(bm);
                        mrdata->eve_act = BM_mesh_active_vert_get(bm);
-               }
-               if (types & MR_DATATYPE_CREASE) {
                        mrdata->crease_ofs = CustomData_get_offset(&bm->edata, 
CD_CREASE);
-               }
-               if (types & MR_DATATYPE_BWEIGHT) {
                        mrdata->bweight_ofs = CustomData_get_offset(&bm->edata, 
CD_BWEIGHT);
                }
                BM_mesh_elem_index_ensure(bm, bm_ensure_types);
                BM_mesh_elem_table_ensure(bm, bm_ensure_types & ~BM_LOOP);
-               if (types & MR_DATATYPE_LOOSE_VERT) {
-                       mrdata->types |= MR_DATATYPE_VERT;
-                       mrdata->totlvert = 0;
-                       /* XXX slow, looping twice */
+               if (types & MR_DATATYPE_OVERLAY) {
+                       mrdata->totlvert = mrdata->totledge = 0;
+
+                       int *lverts = mrdata->loose_verts = 
MEM_mallocN(mrdata->totvert * sizeof(int), "Loose Vert");
+                       int *ledges = mrdata->loose_edges = 
MEM_mallocN(mrdata->totedge * sizeof(int), "Loose Edges");
+
                        for (int i = 0; i < mrdata->totvert; ++i) {
                                BMVert *bv = BM_vert_at_index(bm, i);
-                               if (BM_vert_edge_count_ex(bv, 1) == 0) {
+
+                               /* Loose vert */
+                               if (bv->e == NULL) {
+                                       lverts[mrdata->totlvert] = 
BM_elem_index_get(bv);
                                        mrdata->totlvert++;
+                                       continue;
                                }
-                       }
 
-                       int *lverts = mrdata->loose_verts = 
MEM_mallocN(mrdata->totlvert * sizeof(int), "Loose Vert");
-
-                       int li = 0;
-                       if (mrdata->totlvert > 0) {
-                               for (int i = 0; i < mrdata->totvert; ++i) {
-                                       BMVert *bv = BM_vert_at_index(bm, i);
-                                       if (BM_vert_edge_count_ex(bv, 1) == 0) {
-                                               lverts[li++] = i;
+                               /* Find Loose Edges */
+                               BMEdge *e_iter, *e_first;
+                               e_first = e_iter = bv->e;
+                               do {
+                                       if (e_iter->l == NULL) {
+                                               BMVert *other_vert = 
BM_edge_other_vert(e_iter, bv);
+
+                                               /* Verify we do not add the 
same edge twice */
+                                               if 
(BM_elem_index_get(other_vert) > i) {
+                                                       
ledges[mrdata->totledge] = BM_elem_index_get(e_iter);
+                                                       mrdata->totledge++;
+                                               }
                                        }
-                               }
-                       }
-               }
-               if (types & MR_DATATYPE_LOOSE_EDGE) {
-                       mrdata->types |= MR_DATATYPE_EDGE;
-                       mrdata->totledge = 0;
-                       /* XXX slow, looping twice */
-                       for (int i = 0; i < mrdata->totedge; ++i) {
-                               BMEdge *bv = BM_edge_at_index(bm, i);
-                               if (BM_edge_is_wire(bv)) {
-                                       mrdata->totledge++;
-                               }
-                       }
-
-                       int *ledges = mrdata->loose_edges = 
MEM_mallocN(mrdata->totledge * sizeof(int), "Loose Egde");
-
-                       int li = 0;
-                       if (mrdata->totledge > 0) {
-                               for (int i = 0; i < mrdata->totedge; ++i) {
-                                       BMEdge *bv = BM_edge_at_index(bm, i);
-                                       if (BM_edge_is_wire(bv)) {
-                                               ledges[li++] = i;
-                                       }
-                               }
+                               } while ((e_iter = BM_DISK_EDGE_NEXT(e_iter, 
bv)) != e_first);
                        }
+                       mrdata->loose_verts = MEM_reallocN(mrdata->loose_verts, 
mrdata->totlvert * sizeof(int));
+                       mrdata->loose_edges = MEM_reallocN(mrdata->loose_edges, 
mrdata->totledge * sizeof(int));
                }
        }
        else {
-               if (types & (MR_DATATYPE_VERT | MR_DATATYPE_LOOSE_VERT)) {
+               if (types & (MR_DATATYPE_VERT)) {
                        mrdata->totvert = me->totvert;
                        mrdata->mvert = CustomData_get_layer(&me->vdata, 
CD_MVERT);
                }
-               if (types & (MR_DATATYPE_EDGE | MR_DATATYPE_LOOSE_EDGE)) {
+               if (types & (MR_DATATYPE_EDGE)) {
                        mrdata->totedge = me->totedge;
                        mrdata->medge = CustomData_get_layer(&me->edata, 
CD_MEDGE);
                }
@@ -248,16 +228,6 @@ static MeshRenderData *mesh_render_data_create(Mesh *me, 
const int types)
                        mrdata->totpoly = me->totpoly;
                        mrdata->mpoly = CustomData_get_layer(&me->pdata, 
CD_MPOLY);
                }
-               if (types & MR_DATATYPE_LOOSE_VERT) {
-                       mrdata->types |= MR_DATATYPE_VERT;
-                       mrdata->totlvert = 0;
-                       /* TODO */
-               }
-               if (types & MR_DATATYPE_LOOSE_EDGE) {
-                       mrdata->types |= MR_DATATYPE_EDGE;
-                       mrdata->totledge = 0;
-                       /* TODO */
-               }
        }
 
        return mrdata;
@@ -300,7 +270,7 @@ static int mesh_render_data_verts_num_get(const 
MeshRenderData *mrdata)
 
 static int mesh_render_data_loose_verts_num_get(const MeshRenderData *mrdata)
 {
-       BLI_assert(mrdata->types & MR_DATATYPE_LOOSE_VERT);
+       BLI_assert(mrdata->types & MR_DATATYPE_OVERLAY);
        return mrdata->totlvert;
 }
 
@@ -312,7 +282,7 @@ static int mesh_render_data_edges_num_get(const 
MeshRenderData *mrdata)
 
 static int mesh_render_data_loose_edges_num_get(const MeshRenderData *mrdata)
 {
-       BLI_assert(mrdata->types & MR_DATATYPE_LOOSE_EDGE);
+       BLI_assert(mrdata->types & MR_DATATYPE_OVERLAY);
        return mrdata->totledge;
 }
 
@@ -547,6 +517,171 @@ static bool mesh_render_data_looptri_cos_nors_smooth_get(
        }
 }
 
+/* First 2 bytes are bit flags
+ * 3rd is for sharp edges
+ * 4rd is for creased edges */
+enum {
+       VFLAG_VERTEX_ACTIVE   = 1 << 0,
+       VFLAG_VERTEX_SELECTED = 1 << 1,
+       VFLAG_FACE_ACTIVE     = 1 << 2,
+       VFLAG_FACE_SELECTED   = 1 << 3,
+};
+
+enum {
+       VFLAG_EDGE_EXISTS   = 1 << 0,
+       VFLAG_EDGE_ACTIVE   = 1 << 1,
+       VFLAG_EDGE_SELECTED = 1 << 2,
+       VFLAG_EDGE_SEAM     = 1 << 3,
+       VFLAG_EDGE_SHARP    = 1 << 4,
+       /* Beware to not go over 1 << 7
+        * (see gpu_shader_edit_overlay_geom.glsl) */
+};
+
+static unsigned char mesh_render_data_looptri_flag(MeshRenderData *mrdata, 
const int f)
+{
+       unsigned char fflag = 0;
+
+       if (mrdata->edit_bmesh) {
+               BMFace *bf = mrdata->edit_bmesh->looptris[f][0]->f;
+
+               if (bf == mrdata->efa_act)
+                       fflag |= VFLAG_FACE_ACTIVE;
+
+               if (BM_elem_flag_test(bf, BM_ELEM_SELECT))
+                       fflag |= VFLAG_FACE_SELECTED;
+       }
+
+       return fflag;
+}
+
+static unsigned char *mesh_render_data_edge_flag(
+        MeshRenderData *mrdata, const int v1, const int v2, const int e)
+{
+       static unsigned char eflag[4];
+       memset(eflag, 0, sizeof(char) * 4);
+
+       /* if edge exists */
+       if (mrdata->edit_bmesh) {
+               BMesh *bm = mrdata->edit_bmesh->bm;
+               BMEdge *be = NULL;
+
+               if (e != -1) be = BM_edge_at_index(bm, e);
+               else         be = BM_edge_exists(BM_vert_at_index(bm, v1),
+                                                BM_vert_at_index(bm, v2));
+
+               if (be != NULL) {
+
+                       eflag[1] |= VFLAG_EDGE_EXISTS;
+
+                       if (be == mrdata->eed_act)
+                               eflag[1] |= VFLAG_EDGE_ACTIVE;
+
+                       if (BM_elem_flag_test(be, BM_ELEM_SELECT))
+                               eflag[1] |= VFLAG_EDGE_SELECTED;
+
+                       if (BM_elem_flag_test(be, BM_ELEM_SEAM))
+                               eflag[1] |= VFLAG_EDGE_SEAM;
+
+                       if (!BM_elem_flag_test(be, BM_ELEM_SMOOTH))
+                               eflag[1] |= VFLAG_EDGE_SHARP;
+
+                       /* Use a byte for value range */
+                       if (mrdata->crease_ofs != -1) {
+                               float crease = BM_ELEM_CD_GET_FLOAT(be, 
mrdata->crease_ofs);
+                               if (crease > 0) {
+                                       eflag[2] = (char)(crease * 255.0f);
+                               }
+                       }
+
+                       /* Use a byte for value range */
+                       if (mrdata->bweight_ofs != -1) {
+                               float bweight = BM_ELEM_CD_GET_FLOAT(be, 
mrdata->bweight_ofs);
+                               if (bweight > 0) {
+                                       eflag[3] = (char)(bweight * 255.0f);
+                               }
+                       }
+               }
+       }
+       else if ((e == -1) && mesh_render_data_edge_exists(mrdata, v1, v2)) {
+               eflag[1] |= VFLAG_EDGE_EXISTS;
+       }
+
+       return eflag;
+}
+
+static unsigned char mesh_render_data_vertex_flag(MeshRenderData *mrdata, 
const int v)
+{
+
+       unsigned char vflag = 0;
+
+       if (mrdata->edit_bmesh) {
+               BMesh *bm = mrdata->edit_bmesh->bm;
+               BMVert *bv = BM_vert_at_index(bm, v);
+
+               /* Current vertex */
+               if (bv == mrdata->eve_act)
+                       vflag |= VFLAG_VERTEX_ACTIVE;
+
+               if (BM_elem_flag_test(bv, BM_ELEM_SELECT))
+                       vflag |= VFLAG_VERTEX_SELECTED;
+       }
+
+       return vflag;
+}
+
+static void add_overlay_tri(
+        MeshRenderData *mrdata, VertexBuffer *vbo, const unsigned int pos_id, 
const unsigned int edgeMod_id,
+        const int v1, const int v2, const int v3, const int f, const int 
base_vert_idx)
+{
+       const float *pos = mesh_render_data_vert_co(mrdata, v1);
+       unsigned char *eflag = mesh_render_data_edge_flag(mrdata, v2, v3, -1);
+       unsigned char  fflag = mesh_render_data_looptri_flag(mrdata, f);
+       unsigned char  vflag = mesh_render_

@@ Diff output truncated at 10240 characters. @@

_______________________________________________
Bf-blender-cvs mailing list
[email protected]
https://lists.blender.org/mailman/listinfo/bf-blender-cvs

Reply via email to