Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
Diffstat (limited to 'source/blender/editors/sculpt_paint/sculpt_undo.c')
-rw-r--r--source/blender/editors/sculpt_paint/sculpt_undo.c81
1 files changed, 75 insertions, 6 deletions
diff --git a/source/blender/editors/sculpt_paint/sculpt_undo.c b/source/blender/editors/sculpt_paint/sculpt_undo.c
index 044d5b3c0b0..d1896f47c52 100644
--- a/source/blender/editors/sculpt_paint/sculpt_undo.c
+++ b/source/blender/editors/sculpt_paint/sculpt_undo.c
@@ -79,8 +79,7 @@ static void update_cb(PBVHNode *node, void *rebuild)
BKE_pbvh_node_mark_update(node);
BKE_pbvh_node_mark_update_mask(node);
if (*((bool *)rebuild)) {
- BKE_pbvh_node_mark_rebuild_draw(node);
- BKE_pbvh_node_mark_visibility_update(node);
+ BKE_pbvh_node_mark_update_visibility(node);
}
BKE_pbvh_node_fully_hidden_set(node, 0);
}
@@ -332,6 +331,15 @@ static bool sculpt_undo_restore_mask(bContext *C, SculptUndoNode *unode)
return true;
}
+static bool sculpt_undo_restore_face_sets(bContext *C, SculptUndoNode *unode)
+{
+ ViewLayer *view_layer = CTX_data_view_layer(C);
+ Object *ob = OBACT(view_layer);
+ SculptSession *ss = ob->sculpt;
+ memcpy(ss->face_sets, unode->face_sets, ss->totpoly * sizeof(int));
+ return false;
+}
+
static void sculpt_undo_bmesh_restore_generic_task_cb(
void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
{
@@ -533,6 +541,30 @@ static void sculpt_undo_restore_list(bContext *C, Depsgraph *depsgraph, ListBase
BKE_sculpt_update_object_for_edit(depsgraph, ob, false, need_mask);
return;
}
+ else if (unode->type == SCULPT_UNDO_FACE_SETS) {
+
+ sculpt_undo_restore_face_sets(C, unode);
+
+ rebuild = true;
+ BKE_pbvh_search_callback(ss->pbvh, NULL, NULL, update_cb, &rebuild);
+
+ BKE_sculpt_update_object_for_edit(depsgraph, ob, true, need_mask);
+
+ sculpt_visibility_sync_all_face_sets_to_vertices(ss);
+ BKE_pbvh_update_vertex_data(ss->pbvh, PBVH_UpdateVisibility);
+
+ if (BKE_pbvh_type(ss->pbvh) == PBVH_FACES) {
+ BKE_mesh_flush_hidden_from_verts(ob->data);
+ }
+
+ if (!BKE_sculptsession_use_pbvh_draw(ob, v3d)) {
+ DEG_id_tag_update(&ob->id, ID_RECALC_SHADING);
+ DEG_id_tag_update(&ob->id, ID_RECALC_GEOMETRY);
+ }
+
+ unode->applied = true;
+ return;
+ }
}
BKE_sculpt_update_object_for_edit(depsgraph, ob, false, need_mask);
@@ -584,6 +616,8 @@ static void sculpt_undo_restore_list(bContext *C, Depsgraph *depsgraph, ListBase
update_mask = true;
}
break;
+ case SCULPT_UNDO_FACE_SETS:
+ break;
case SCULPT_UNDO_DYNTOPO_BEGIN:
case SCULPT_UNDO_DYNTOPO_END:
@@ -619,10 +653,16 @@ static void sculpt_undo_restore_list(bContext *C, Depsgraph *depsgraph, ListBase
};
BKE_pbvh_search_callback(ss->pbvh, NULL, NULL, update_cb_partial, &data);
BKE_pbvh_update_bounds(ss->pbvh, PBVH_UpdateBB | PBVH_UpdateOriginalBB | PBVH_UpdateRedraw);
+
if (update_mask) {
BKE_pbvh_update_vertex_data(ss->pbvh, PBVH_UpdateMask);
}
+ if (update_visibility) {
+ sculpt_visibility_sync_all_vertex_to_face_sets(ss);
+ BKE_pbvh_update_visibility(ss->pbvh);
+ }
+
if (BKE_sculpt_multires_active(scene, ob)) {
if (rebuild) {
multires_mark_as_modified(depsgraph, ob, MULTIRES_HIDDEN_MODIFIED);
@@ -642,10 +682,6 @@ static void sculpt_undo_restore_list(bContext *C, Depsgraph *depsgraph, ListBase
BKE_sculptsession_free_deformMats(ss);
}
- if (update_visibility) {
- BKE_pbvh_update_visibility(ss->pbvh);
- }
-
if (BKE_pbvh_type(ss->pbvh) == PBVH_FACES && update_visibility) {
Mesh *mesh = ob->data;
BKE_mesh_flush_hidden_from_verts(mesh);
@@ -714,6 +750,10 @@ static void sculpt_undo_free_list(ListBase *lb)
CustomData_free(&unode->geom_pdata, unode->geom_totpoly);
}
+ if (unode->face_sets) {
+ MEM_freeN(unode->face_sets);
+ }
+
MEM_freeN(unode);
unode = unode_next;
@@ -828,6 +868,7 @@ static SculptUndoNode *sculpt_undo_alloc_node(Object *ob, PBVHNode *node, Sculpt
case SCULPT_UNDO_DYNTOPO_SYMMETRIZE:
BLI_assert(!"Dynamic topology should've already been handled");
case SCULPT_UNDO_GEOMETRY:
+ case SCULPT_UNDO_FACE_SETS:
break;
}
@@ -939,6 +980,27 @@ static SculptUndoNode *sculpt_undo_geometry_push(Object *ob, SculptUndoType type
return unode;
}
+static SculptUndoNode *sculpt_undo_face_sets_push(Object *ob, SculptUndoType type)
+{
+ UndoSculpt *usculpt = sculpt_undo_get_nodes();
+ SculptSession *ss = ob->sculpt;
+
+ SculptUndoNode *unode = usculpt->nodes.first;
+
+ unode = MEM_callocN(sizeof(*unode), __func__);
+
+ BLI_strncpy(unode->idname, ob->id.name, sizeof(unode->idname));
+ unode->type = type;
+ unode->applied = true;
+
+ unode->face_sets = MEM_callocN(ss->totpoly * sizeof(int), "sculpt face sets");
+ memcpy(unode->face_sets, ss->face_sets, ss->totpoly * sizeof(int));
+
+ BLI_addtail(&usculpt->nodes, unode);
+
+ return unode;
+}
+
static SculptUndoNode *sculpt_undo_bmesh_push(Object *ob, PBVHNode *node, SculptUndoType type)
{
UndoSculpt *usculpt = sculpt_undo_get_nodes();
@@ -1022,6 +1084,7 @@ static SculptUndoNode *sculpt_undo_bmesh_push(Object *ob, PBVHNode *node, Sculpt
case SCULPT_UNDO_DYNTOPO_END:
case SCULPT_UNDO_DYNTOPO_SYMMETRIZE:
case SCULPT_UNDO_GEOMETRY:
+ case SCULPT_UNDO_FACE_SETS:
break;
}
}
@@ -1051,6 +1114,11 @@ SculptUndoNode *sculpt_undo_push_node(Object *ob, PBVHNode *node, SculptUndoType
BLI_thread_unlock(LOCK_CUSTOM1);
return unode;
}
+ else if (type == SCULPT_UNDO_FACE_SETS) {
+ unode = sculpt_undo_face_sets_push(ob, type);
+ BLI_thread_unlock(LOCK_CUSTOM1);
+ return unode;
+ }
else if ((unode = sculpt_undo_get_node(node))) {
BLI_thread_unlock(LOCK_CUSTOM1);
return unode;
@@ -1091,6 +1159,7 @@ SculptUndoNode *sculpt_undo_push_node(Object *ob, PBVHNode *node, SculptUndoType
case SCULPT_UNDO_DYNTOPO_SYMMETRIZE:
BLI_assert(!"Dynamic topology should've already been handled");
case SCULPT_UNDO_GEOMETRY:
+ case SCULPT_UNDO_FACE_SETS:
break;
}