[Bf-blender-cvs] [e997e084868] temp-lanpr-cleanup2: Fix T69822: Switching sculpt objects breaks undo

Campbell Barton noreply at git.blender.org
Wed Nov 13 06:04:01 CET 2019


Commit: e997e084868bc7f7011a7c4473e28f61e1f48f4b
Author: Campbell Barton
Date:   Thu Nov 7 16:52:03 2019 +1100
Branches: temp-lanpr-cleanup2
https://developer.blender.org/rBe997e084868bc7f7011a7c4473e28f61e1f48f4b

Fix T69822: Switching sculpt objects breaks undo

This introduces object mode tagging for data which hasn't yet been
written back to the ID data.

Now when selecting other sculpt objects, the original objects data is
flushed back to the ID before writing a memfile undo step.

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

M	source/blender/blenkernel/BKE_editmesh.h
M	source/blender/blenkernel/BKE_font.h
M	source/blender/blenkernel/BKE_main.h
M	source/blender/blenkernel/BKE_object.h
M	source/blender/blenkernel/BKE_paint.h
M	source/blender/blenkernel/intern/object.c
M	source/blender/blenloader/intern/readfile.c
M	source/blender/editors/armature/editarmature_undo.c
M	source/blender/editors/curve/editcurve_undo.c
M	source/blender/editors/curve/editfont_undo.c
M	source/blender/editors/include/ED_mball.h
M	source/blender/editors/include/ED_util.h
M	source/blender/editors/lattice/editlattice_undo.c
M	source/blender/editors/mesh/editmesh_undo.c
M	source/blender/editors/metaball/editmball_undo.c
M	source/blender/editors/object/object_edit.c
M	source/blender/editors/sculpt_paint/sculpt_undo.c
M	source/blender/editors/undo/ed_undo.c
M	source/blender/editors/undo/memfile_undo.c
M	source/blender/editors/util/ed_util.c
M	source/blender/makesdna/DNA_armature_types.h
M	source/blender/makesdna/DNA_curve_types.h
M	source/blender/makesdna/DNA_lattice_types.h
M	source/blender/makesdna/DNA_meta_types.h

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

diff --git a/source/blender/blenkernel/BKE_editmesh.h b/source/blender/blenkernel/BKE_editmesh.h
index 47c8f31ead3..1b9e318146e 100644
--- a/source/blender/blenkernel/BKE_editmesh.h
+++ b/source/blender/blenkernel/BKE_editmesh.h
@@ -79,6 +79,13 @@ typedef struct BMEditMesh {
 
   /*temp variables for x-mirror editing*/
   int mirror_cdlayer; /* -1 is invalid */
+
+  /**
+   * ID data is older than edit-mode data.
+   * Set #Main.is_memfile_undo_flush_needed when enabling.
+   */
+  char needs_flush_to_id;
+
 } BMEditMesh;
 
 /* editmesh.c */
diff --git a/source/blender/blenkernel/BKE_font.h b/source/blender/blenkernel/BKE_font.h
index e440d617f7a..3dd2a551a93 100644
--- a/source/blender/blenkernel/BKE_font.h
+++ b/source/blender/blenkernel/BKE_font.h
@@ -61,6 +61,12 @@ typedef struct EditFont {
   int len, pos;
   int selstart, selend;
 
+  /**
+   * ID data is older than edit-mode data.
+   * Set #Main.is_memfile_undo_flush_needed when enabling.
+   */
+  char needs_flush_to_id;
+
 } EditFont;
 
 bool BKE_vfont_is_builtin(struct VFont *vfont);
diff --git a/source/blender/blenkernel/BKE_main.h b/source/blender/blenkernel/BKE_main.h
index 1b2e8bcbf42..c48a9cad443 100644
--- a/source/blender/blenkernel/BKE_main.h
+++ b/source/blender/blenkernel/BKE_main.h
@@ -80,6 +80,11 @@ typedef struct Main {
   char recovered;                  /* indicate the main->name (file) is the recovered one */
   /** All current ID's exist in the last memfile undo step. */
   char is_memfile_undo_written;
+  /**
+   * An ID needs it's data to be flushed back.
+   * use "needs_flush_to_id" in edit data to flag data which needs updating.
+   */
+  char is_memfile_undo_flush_needed;
 
   BlendThumbnail *blen_thumb;
 
diff --git a/source/blender/blenkernel/BKE_object.h b/source/blender/blenkernel/BKE_object.h
index ffdcb9cd2c0..d76c55f0815 100644
--- a/source/blender/blenkernel/BKE_object.h
+++ b/source/blender/blenkernel/BKE_object.h
@@ -99,6 +99,8 @@ bool BKE_object_is_mode_compat(const struct Object *ob, eObjectMode object_mode)
 
 bool BKE_object_data_is_in_editmode(const struct ID *id);
 
+char *BKE_object_data_editmode_flush_ptr_get(struct ID *id);
+
 void BKE_object_update_select_id(struct Main *bmain);
 
 typedef enum eObjectVisibilityResult {
diff --git a/source/blender/blenkernel/BKE_paint.h b/source/blender/blenkernel/BKE_paint.h
index 4413ad2a70f..48f9e1fd95e 100644
--- a/source/blender/blenkernel/BKE_paint.h
+++ b/source/blender/blenkernel/BKE_paint.h
@@ -306,6 +306,13 @@ typedef struct SculptSession {
 
   /* This flag prevents PBVH from being freed when creating the vp_handle for texture paint. */
   bool building_vp_handle;
+
+  /**
+   * ID data is older than sculpt-mode data.
+   * Set #Main.is_memfile_undo_flush_needed when enabling.
+   */
+  char needs_flush_to_id;
+
 } SculptSession;
 
 void BKE_sculptsession_free(struct Object *ob);
diff --git a/source/blender/blenkernel/intern/object.c b/source/blender/blenkernel/intern/object.c
index 773e2d19b22..b50e152527e 100644
--- a/source/blender/blenkernel/intern/object.c
+++ b/source/blender/blenkernel/intern/object.c
@@ -81,6 +81,7 @@
 #include "BKE_curve.h"
 #include "BKE_displist.h"
 #include "BKE_effect.h"
+#include "BKE_font.h"
 #include "BKE_fcurve.h"
 #include "BKE_gpencil_modifier.h"
 #include "BKE_icons.h"
@@ -629,6 +630,54 @@ bool BKE_object_data_is_in_editmode(const ID *id)
   }
 }
 
+char *BKE_object_data_editmode_flush_ptr_get(struct ID *id)
+{
+  const short type = GS(id->name);
+  switch (type) {
+    case ID_ME: {
+      BMEditMesh *em = ((Mesh *)id)->edit_mesh;
+      if (em != NULL) {
+        return &em->needs_flush_to_id;
+      }
+      break;
+    }
+    case ID_CU: {
+      if (((Curve *)id)->vfont != NULL) {
+        EditFont *ef = ((Curve *)id)->editfont;
+        if (ef != NULL) {
+          return &ef->needs_flush_to_id;
+        }
+      }
+      else {
+        EditNurb *editnurb = ((Curve *)id)->editnurb;
+        if (editnurb) {
+          return &editnurb->needs_flush_to_id;
+        }
+      }
+      break;
+    }
+    case ID_MB: {
+      MetaBall *mb = (MetaBall *)id;
+      return &mb->needs_flush_to_id;
+    }
+    case ID_LT: {
+      EditLatt *editlatt = ((Lattice *)id)->editlatt;
+      if (editlatt) {
+        return &editlatt->needs_flush_to_id;
+      }
+      break;
+    }
+    case ID_AR: {
+      bArmature *arm = (bArmature *)id;
+      return &arm->needs_flush_to_id;
+    }
+    default:
+      BLI_assert(0);
+      return NULL;
+  }
+  return NULL;
+}
+
 bool BKE_object_is_in_wpaint_select_vert(const Object *ob)
 {
   if (ob->type == OB_MESH) {
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index e77b17ec7da..d45c43ceca6 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -3863,6 +3863,8 @@ static void direct_link_armature(FileData *fd, bArmature *arm)
   link_list(fd, &arm->bonebase);
   arm->bonehash = NULL;
   arm->edbo = NULL;
+  /* Must always be cleared (armatures don't have their own edit-data). */
+  arm->needs_flush_to_id = 0;
 
   arm->adt = newdataadr(fd, arm->adt);
   direct_link_animdata(fd, arm->adt);
@@ -4080,6 +4082,8 @@ static void direct_link_mball(FileData *fd, MetaBall *mb)
 
   BLI_listbase_clear(&mb->disp);
   mb->editelems = NULL;
+  /* Must always be cleared (meta's don't have their own edit-data). */
+  mb->needs_flush_to_id = 0;
   /*  mb->edit_elems.first= mb->edit_elems.last= NULL;*/
   mb->lastelem = NULL;
   mb->batch_cache = NULL;
diff --git a/source/blender/editors/armature/editarmature_undo.c b/source/blender/editors/armature/editarmature_undo.c
index 4a82a8fccee..4e3ab11a9f7 100644
--- a/source/blender/editors/armature/editarmature_undo.c
+++ b/source/blender/editors/armature/editarmature_undo.c
@@ -32,6 +32,7 @@
 
 #include "BKE_context.h"
 #include "BKE_layer.h"
+#include "BKE_main.h"
 #include "BKE_undo_system.h"
 
 #include "DEG_depsgraph.h"
@@ -142,9 +143,7 @@ static bool armature_undosys_poll(bContext *C)
   return editarm_object_from_context(C) != NULL;
 }
 
-static bool armature_undosys_step_encode(struct bContext *C,
-                                         struct Main *UNUSED(bmain),
-                                         UndoStep *us_p)
+static bool armature_undosys_step_encode(struct bContext *C, struct Main *bmain, UndoStep *us_p)
 {
   ArmatureUndoStep *us = (ArmatureUndoStep *)us_p;
 
@@ -165,17 +164,18 @@ static bool armature_undosys_step_encode(struct bContext *C,
     elem->obedit_ref.ptr = ob;
     bArmature *arm = elem->obedit_ref.ptr->data;
     undoarm_from_editarm(&elem->data, arm);
+    arm->needs_flush_to_id = 1;
     us->step.data_size += elem->data.undo_size;
   }
   MEM_freeN(objects);
+
+  bmain->is_memfile_undo_flush_needed = true;
+
   return true;
 }
 
-static void armature_undosys_step_decode(struct bContext *C,
-                                         struct Main *UNUSED(bmain),
-                                         UndoStep *us_p,
-                                         int UNUSED(dir),
-                                         bool UNUSED(is_final))
+static void armature_undosys_step_decode(
+    struct bContext *C, struct Main *bmain, UndoStep *us_p, int UNUSED(dir), bool UNUSED(is_final))
 {
   ArmatureUndoStep *us = (ArmatureUndoStep *)us_p;
 
@@ -198,6 +198,7 @@ static void armature_undosys_step_decode(struct bContext *C,
       continue;
     }
     undoarm_to_editarm(&elem->data, arm);
+    arm->needs_flush_to_id = 1;
     DEG_id_tag_update(&obedit->id, ID_RECALC_GEOMETRY);
   }
 
@@ -205,6 +206,8 @@ static void armature_undosys_step_decode(struct bContext *C,
   ED_undo_object_set_active_or_warn(
       CTX_data_view_layer(C), us->elems[0].obedit_ref.ptr, us_p->name, &LOG);
 
+  bmain->is_memfile_undo_flush_needed = true;
+
   WM_event_add_notifier(C, NC_GEOM | ND_DATA, NULL);
 }
 
diff --git a/source/blender/editors/curve/editcurve_undo.c b/source/blender/editors/curve/editcurve_undo.c
index f21b4f06246..ff3a1386fd9 100644
--- a/source/blender/editors/curve/editcurve_undo.c
+++ b/source/blender/editors/curve/editcurve_undo.c
@@ -208,9 +208,7 @@ static bool curve_undosys_poll(bContext *C)
   return (obedit != NULL);
 }
 
-static bool curve_undosys_step_encode(struct bContext *C,
-                                      struct Main *UNUSED(bmain),
-                                      UndoStep *us_p)
+static bool curve_undosys_step_encode(struct bContext *C, struct Main *bmain, UndoStep *us_p)
 {
   CurveUndoStep *us = (CurveUndoStep *)us_p;
 
@@ -226,13 +224,18 @@ static bool curve_undosys_step_encode(struct bContext *C,
 
   for (uint i = 0; i < objects_len; i++) {
     Object *ob = objects[i];
+    Curve *cu = ob->data;
     CurveUndoStep_Elem *elem = &us->elems[i];
 
     elem->obedit_ref.ptr = ob;
     undocurve_from_editcurve(&elem->data, ob->data, ob->shapenr);
+    cu->editnurb->needs_flush_to_id = 1;
     us->step.data_size += elem->data.undo_size;
   }
   MEM_freeN(objects);
+
+  bmain->is_memfile_undo_flush_needed = true;
+
   return true;
 }
 
@@ -260,6 +263,7 @@ static void curve_undosys_step_decode(
       continue;
     }
     undocurve_to_editcurve(bmain, &elem->data, obedit->data, &obedit->shapenr);
+    cu->editnurb->needs_flush_to_id = 1;
     DEG_id_tag_update(&obedit->id, ID_RECALC_GEOMETRY);
   }
 
@@ -267,6 +271,8 @@ static void curve_undosys_step_decode(
   ED_undo_object_set_active_or_warn(
       CTX_data_view_layer(C), us->elems[0].obedit_ref.ptr, us_p->name, &LOG);
 
+  bmain->is_memfile_undo_flush_needed = true;
+
   WM_event_add_notifier(C, NC_GEOM | ND_DATA, NULL);
 }
 
diff --git a/source/blender/editors/curve/editfont_undo.c b/source/blender/editors/curve/editfont_undo.c
index ae858ec4c24..26c0e5cf6c9 100644
--- a/source/blender/editors/curve/editfont_undo.c
+++ b/source/blender/editors/curve/editfont_undo.c
@@ -32,6 +32,7 @@
 
 #include "BKE_context.h"
 #include "BKE_font.h"
+#include "BKE_main.h"
 #include "BKE_undo_system.h"
 
 #include "DEG_depsgraph.h"
@@ -341,23 +342,21 @@ static bool font_undosys_poll(bContext *C)
   return editfont_object_from_context(C) != NULL;
 }
 
-static bool font_undosys_step_encode(struct bContext *C

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list