From 1816d1f992c45f6decf26a3afa2e8ba71964defc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Foucault?= Date: Thu, 15 Mar 2018 13:55:20 +0100 Subject: Mesh: Batch cache: Fix sculpt update issue. Old solution was to create a new vbo and copy it to the location of the old vbo hoping for the batches to update their vaos before drawing. The issue is that the new VAO caching is not updating the VAOs at all unless the shader interface changes. So unless we expand gawain to support updating of vertex buffers (in a better way than the current "dynamic" buffer) we need to delete every batch linked to the vbo we want to recreate. This solution might have performance implications. --- source/blender/draw/intern/draw_cache_impl_mesh.c | 59 +++++++++++++++++------ 1 file changed, 44 insertions(+), 15 deletions(-) (limited to 'source/blender/draw/intern') diff --git a/source/blender/draw/intern/draw_cache_impl_mesh.c b/source/blender/draw/intern/draw_cache_impl_mesh.c index b44c5b8a20b..f7a82c6d0c5 100644 --- a/source/blender/draw/intern/draw_cache_impl_mesh.c +++ b/source/blender/draw/intern/draw_cache_impl_mesh.c @@ -1665,6 +1665,46 @@ void DRW_mesh_batch_cache_dirty(Mesh *me, int mode) } } +/** + * This only clear the batches associated to the given vertex buffer. + **/ +static void mesh_batch_cache_clear_selective(Mesh *me, Gwn_VertBuf *vert) +{ + MeshBatchCache *cache = me->batch_cache; + if (!cache) { + return; + } + + BLI_assert(vert != NULL); + + if (cache->pos_with_normals == vert) { + GWN_BATCH_DISCARD_SAFE(cache->triangles_with_normals); + GWN_BATCH_DISCARD_SAFE(cache->triangles_with_weights); + GWN_BATCH_DISCARD_SAFE(cache->triangles_with_vert_colors); + GWN_BATCH_DISCARD_SAFE(cache->triangles_with_select_id); + GWN_BATCH_DISCARD_SAFE(cache->triangles_with_select_mask); + GWN_BATCH_DISCARD_SAFE(cache->points_with_normals); + if (cache->shaded_triangles) { + for (int i = 0; i < cache->mat_len; ++i) { + GWN_BATCH_DISCARD_SAFE(cache->shaded_triangles[i]); + } + } + MEM_SAFE_FREE(cache->shaded_triangles); + if (cache->texpaint_triangles) { + for (int i = 0; i < cache->mat_len; ++i) { + GWN_BATCH_DISCARD_SAFE(cache->texpaint_triangles[i]); + } + } + MEM_SAFE_FREE(cache->texpaint_triangles); + GWN_BATCH_DISCARD_SAFE(cache->texpaint_triangles_single); + } + /* TODO: add the other ones if needed. */ + else { + /* Does not match any vertbuf in the batch cache! */ + BLI_assert(0); + } +} + static void mesh_batch_cache_clear(Mesh *me) { MeshBatchCache *cache = me->batch_cache; @@ -3878,21 +3918,10 @@ void DRW_mesh_cache_sculpt_coords_ensure(Mesh *me) if (me->batch_cache) { MeshBatchCache *cache = mesh_batch_cache_get(me); if (cache && cache->pos_with_normals && cache->is_sculpt_points_tag) { - - const int datatype = MR_DATATYPE_VERT | MR_DATATYPE_LOOPTRI | MR_DATATYPE_LOOP | MR_DATATYPE_POLY; - MeshRenderData *rdata = mesh_render_data_create(me, datatype); - - Gwn_VertBuf *pos_with_normals = cache->pos_with_normals; - cache->pos_with_normals = NULL; - GWN_vertbuf_clear(pos_with_normals); - Gwn_VertBuf *vbo = mesh_batch_cache_get_tri_pos_and_normals(rdata, cache); - *pos_with_normals = *vbo; - GWN_vertformat_copy(&pos_with_normals->format, &vbo->format); - - free(vbo); - cache->pos_with_normals = pos_with_normals; - - mesh_render_data_free(rdata); + /* XXX Force update of all the batches that contains the pos_with_normals buffer. + * TODO(fclem): Ideally, Gawain should provide a way to update a buffer without destroying it. */ + mesh_batch_cache_clear_selective(me, cache->pos_with_normals); + GWN_VERTBUF_DISCARD_SAFE(cache->pos_with_normals); } cache->is_sculpt_points_tag = false; } -- cgit v1.2.3