Sculpt-dev: fix pbvh draw getting gpu format

out of sync.

GPU_pbvh_update_attribute_names now returns a bool
if the format has changed.
This commit is contained in:
Joseph Eagar 2021-11-17 13:14:10 -08:00
parent 4144366bc1
commit a4ce7b6741
7 changed files with 103 additions and 28 deletions

View File

@ -3295,9 +3295,27 @@ void BKE_sculptsession_update_attr_refs(Object *ob)
ss, ob, scl->domain, scl->proptype, scl->name, scl, true, &scl->params);
}
}
if (ss->bm) {
BKE_sculptsession_bmesh_attr_update_internal(ob);
}
}
if (ss->bm) {
BKE_sculptsession_bmesh_attr_update_internal(ob);
if (ss->pbvh) {
Mesh *me = BKE_object_get_original_mesh(ob);
AttributeDomain domain;
CustomDataLayer *layer = NULL;
BKE_pbvh_get_color_layer(ss->pbvh, me, &layer, &domain);
ss->vcol_domain = domain;
ss->vcol_type = layer->type;
if (ss->bm) {
ss->cd_vcol_offset = layer->offset;
}
else {
ss->vcol = layer->data;
}
}
}

View File

@ -1698,14 +1698,24 @@ static void pbvh_update_draw_buffers(
}
}
GPU_pbvh_update_attribute_names(vdata,
ldata,
GPU_pbvh_need_full_render_get(),
pbvh->flags & PBVH_FAST_DRAW,
pbvh->vcol_type,
pbvh->vcol_domain,
vcol_layer,
render_vcol_layer);
/* rebuild all draw buffers if attribute layout changed */
if (GPU_pbvh_update_attribute_names(vdata,
ldata,
GPU_pbvh_need_full_render_get(),
pbvh->flags & PBVH_FAST_DRAW,
pbvh->vcol_type,
pbvh->vcol_domain,
vcol_layer,
render_vcol_layer)) {
// attribute layout changed; force rebuild
for (int i = 0; i < pbvh->totnode; i++) {
PBVHNode *node = pbvh->nodes + i;
if (node->flag & PBVH_Leaf) {
node->flag |= PBVH_RebuildDrawBuffers | PBVH_UpdateDrawBuffers | PBVH_UpdateRedraw;
}
}
}
if ((update_flag & PBVH_RebuildDrawBuffers) || ELEM(pbvh->type, PBVH_GRIDS, PBVH_BMESH)) {
/* Free buffers uses OpenGL, so not in parallel. */
@ -3318,10 +3328,13 @@ void BKE_pbvh_draw_cb(PBVH *pbvh,
// bad global from gpu_buffers.c
extern bool pbvh_show_orig_co;
void BKE_pbvh_draw_debug_cb(
PBVH *pbvh,
void (*draw_fn)(void *user_data, const float bmin[3], const float bmax[3], PBVHNodeFlags flag, int depth),
void *user_data)
void BKE_pbvh_draw_debug_cb(PBVH *pbvh,
void (*draw_fn)(void *user_data,
const float bmin[3],
const float bmax[3],
PBVHNodeFlags flag,
int depth),
void *user_data)
{
for (int a = 0; a < pbvh->totnode; a++) {
PBVHNode *node = &pbvh->nodes[a];

View File

@ -1544,7 +1544,13 @@ static void pbvh_bmesh_create_leaf_fast_task_cb(void *__restrict userdata,
bool has_visible = false;
n->flag = PBVH_Leaf | PBVH_UpdateTris;
/* Build GPU buffers for new node */
n->flag = PBVH_Leaf | PBVH_UpdateTris | PBVH_UpdateBB | PBVH_UpdateOriginalBB |
PBVH_UpdateTriAreas | PBVH_UpdateColor | PBVH_UpdateVisibility |
PBVH_UpdateDrawBuffers | PBVH_RebuildDrawBuffers | PBVH_UpdateCurvatureDir | PBVH_UpdateTriAreas
| PBVH_UpdateMask | PBVH_UpdateRedraw;
n->bm_faces = BLI_table_gset_new_ex("bm_faces", node->totface);
/* Create vert hash sets */
@ -1591,9 +1597,6 @@ static void pbvh_bmesh_create_leaf_fast_task_cb(void *__restrict userdata,
n->orig_vb = n->vb;
/* Build GPU buffers for new node and update vertex normals */
BKE_pbvh_node_mark_rebuild_draw(n);
BKE_pbvh_node_fully_hidden_set(n, !has_visible);
n->flag |= PBVH_UpdateNormals | PBVH_UpdateCurvatureDir;
}

View File

@ -83,7 +83,8 @@ void DRW_draw_region_engine_info(int xoffset, int *yoffset, int line_height);
void DRW_make_cdlayer_attr_aliases(struct GPUVertFormat *format,
char *base_name,
struct CustomData *data,
struct CustomDataLayer *cl);
struct CustomDataLayer *cl,
bool is_active_render);
void DRW_draw_render_loop_ex(struct Depsgraph *depsgraph,
struct RenderEngineType *engine_type,

View File

@ -243,7 +243,7 @@ static void UNUSED_FUNCTION(add_fancy_edge)(GPUVertBuf *vbo,
GPU_vertbuf_attr_set(vbo, pos_id, (*v_idx)++, co2);
}
#if 0 /* UNUSED */
#if 0 /* UNUSED */
static void add_lat_lon_vert(GPUVertBuf *vbo,
uint pos_id,
uint nor_id,
@ -488,7 +488,8 @@ static void sphere_lat_lon_vert(GPUVertBuf *vbo, int *v_ofs, float lat, float lo
void DRW_make_cdlayer_attr_aliases(GPUVertFormat *format,
char *base_name,
CustomData *data,
CustomDataLayer *cl)
CustomDataLayer *cl,
bool is_active_render)
{
char attr_name[32], attr_safe_name[GPU_MAX_SAFE_ATTR_NAME];
const char *layer_name = cl->name;
@ -506,9 +507,10 @@ void DRW_make_cdlayer_attr_aliases(GPUVertFormat *format,
GPU_vertformat_alias_add(format, attr_name);
/* Active render layer name. */
if (i == CustomData_get_render_layer(data, cl->type)) {
if (is_active_render) {
GPU_vertformat_alias_add(format, base_name);
}
/* Active display layer name. */
if (i == CustomData_get_active_layer(data, cl->type)) {
BLI_snprintf(attr_name, sizeof(attr_name), "a%s", base_name);

View File

@ -110,7 +110,7 @@ void GPU_pbvh_mesh_buffers_update(GPU_PBVH_Buffers *buffers,
const int face_sets_color_default,
const int update_flags);
void GPU_pbvh_update_attribute_names(
bool GPU_pbvh_update_attribute_names(
CustomData *vdata,
CustomData *ldata,
bool need_full_render,

View File

@ -151,7 +151,7 @@ typedef struct ColorRef {
#define MAX_GPU_MCOL 256
static struct {
typedef struct PBVHGPUFormat {
GPUVertFormat format;
uint pos, nor, msk, fset, uv;
uint col[MAX_GPU_MCOL];
@ -167,7 +167,9 @@ static struct {
bool active_vcol_only;
bool need_full_render;
bool fast_mode;
} g_vbo_id = {{0}};
} PBVHGPUFormat;
static PBVHGPUFormat g_vbo_id = {{0}};
#ifdef NEW_ATTR_SYSTEM
static CDLayerType cd_vert_layers[] = {
@ -1387,7 +1389,30 @@ bool GPU_pbvh_need_full_render_get()
return g_vbo_id.need_full_render;
}
void GPU_pbvh_update_attribute_names(CustomData *vdata,
static bool gpu_pbvh_format_equals(PBVHGPUFormat *a, PBVHGPUFormat *b)
{
bool bad = false;
bad |= a->active_vcol_only != b->active_vcol_only;
bad |= a->fast_mode != b->fast_mode;
bad |= a->need_full_render != b->need_full_render;
#ifdef NEW_ATTR_SYSTEM
bad |= a->vertex_attrs_len != b->vertex_attrs_len;
bad |= a->loop_attrs_len != b->loop_attrs_len;
#endif
bad |= a->totcol != b->totcol;
bad |= a->pos != b->pos;
bad |= a->uv != b->uv;
bad |= a->fset != b->fset;
bad |= a->msk != b->msk;
bad |= a->nor != b->nor;
return !bad;
}
bool GPU_pbvh_update_attribute_names(CustomData *vdata,
CustomData *ldata,
bool need_full_render,
bool fast_mode,
@ -1397,6 +1422,7 @@ void GPU_pbvh_update_attribute_names(CustomData *vdata,
CustomDataLayer *render_vcol_layer)
{
const bool active_only = !need_full_render;
PBVHGPUFormat old_format = g_vbo_id;
debug_pass++;
@ -1484,7 +1510,9 @@ void GPU_pbvh_update_attribute_names(CustomData *vdata,
&g_vbo_id.format, "c", GPU_COMP_U16, 4, GPU_FETCH_INT_TO_FLOAT_UNIT);
g_vbo_id.totcol++;
DRW_make_cdlayer_attr_aliases(&g_vbo_id.format, "c", cdata, cl);
bool is_render = cl == render_vcol_layer;
DRW_make_cdlayer_attr_aliases(&g_vbo_id.format, "c", cdata, cl, is_render);
if (cl == active_vcol_layer) {
GPU_vertformat_alias_add(&g_vbo_id.format, "ac");
@ -1526,12 +1554,22 @@ void GPU_pbvh_update_attribute_names(CustomData *vdata,
const int cd_uv_index = CustomData_get_layer_index(ldata, CD_MLOOPUV);
CustomDataLayer *cl = ldata->layers + cd_uv_index;
bool is_render = cl->active == cl->active_rnd;
cl += cl->active;
DRW_make_cdlayer_attr_aliases(&g_vbo_id.format, "u", ldata, cl);
DRW_make_cdlayer_attr_aliases(&g_vbo_id.format, "u", ldata, cl, is_render);
}
#endif
}
if (!gpu_pbvh_format_equals(&old_format, &g_vbo_id)) {
printf("gpu format update detected\n");
return true;
}
return false;
}
static void gpu_flat_vcol_make_vert(float co[3],