[Bf-blender-cvs] [e8dc82311d1] master: Fix T96145: GPencil eval data not updated correctly

Falk David noreply at git.blender.org
Thu Mar 3 16:01:44 CET 2022


Commit: e8dc82311d1a7012adaacc93bcc5e92c0fd7adbf
Author: Falk David
Date:   Thu Mar 3 15:48:53 2022 +0100
Branches: master
https://developer.blender.org/rBe8dc82311d1a7012adaacc93bcc5e92c0fd7adbf

Fix T96145: GPencil eval data not updated correctly

 When removing a modifier, changing the layer transform or updating
 the parent of a grease pencil object that has a multi-user datablock
 and animation data, the eval data is not updated properly (after a
 frame change). This can also cause memory leaks.

 The fix makes sure that we free and reset any runtime copy
 (`ob->runtime.gpd_eval`) in `BKE_gpencil_prepare_eval_data`.

 Note: As far as we can tell, `ob->runtime.gpd_orig` is unused and could
 be removed. The assignment in `BKE_gpencil_prepare_eval_data`
 seemed to be unnecessary.

Co-authored-by: @yann-lty

Reviewed By: antoniov

Maniphest Tasks: T96145

Differential Revision: https://developer.blender.org/D14236

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

M	source/blender/blenkernel/intern/gpencil_modifier.c

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

diff --git a/source/blender/blenkernel/intern/gpencil_modifier.c b/source/blender/blenkernel/intern/gpencil_modifier.c
index 3d9043e6800..bc3aa88d096 100644
--- a/source/blender/blenkernel/intern/gpencil_modifier.c
+++ b/source/blender/blenkernel/intern/gpencil_modifier.c
@@ -682,31 +682,41 @@ void BKE_gpencil_prepare_eval_data(Depsgraph *depsgraph, Scene *scene, Object *o
     }
   }
 
-  const bool is_multiedit = (bool)GPENCIL_MULTIEDIT_SESSIONS_ON(gpd_eval);
-  const bool is_curve_edit = (bool)GPENCIL_CURVE_EDIT_SESSIONS_ON(gpd_eval);
+  DEG_debug_print_eval(depsgraph, __func__, gpd_eval->id.name, gpd_eval);
+
+  /* Delete any previously created runtime copy. */
+  if (ob->runtime.gpd_eval != NULL) {
+    /* Make sure to clear the pointer in case the runtime eval data points to the same data block.
+     * This can happen when the gpencil data block was not tagged for a depsgraph update after last
+     * call to this function. */
+    if (gpd_eval == ob->runtime.gpd_eval) {
+      gpd_eval = NULL;
+    }
+    BKE_gpencil_eval_delete(ob->runtime.gpd_eval);
+    ob->runtime.gpd_eval = NULL;
+    ob->data = gpd_eval;
+  }
+
+  const bool is_multiedit = (bool)GPENCIL_MULTIEDIT_SESSIONS_ON(gpd_orig);
+  const bool is_curve_edit = (bool)GPENCIL_CURVE_EDIT_SESSIONS_ON(gpd_orig);
   const bool do_modifiers = (bool)((!is_multiedit) && (!is_curve_edit) &&
-                                   (ob->greasepencil_modifiers.first != NULL) &&
+                                   (ob_orig->greasepencil_modifiers.first != NULL) &&
                                    (!GPENCIL_SIMPLIFY_MODIF(scene)));
   if ((!do_modifiers) && (!do_parent) && (!do_transform)) {
+    BLI_assert(ob->data != NULL);
     return;
   }
-  DEG_debug_print_eval(depsgraph, __func__, gpd_eval->id.name, gpd_eval);
 
   /* If only one user, don't need a new copy, just update data of the frame. */
   if (gpd_orig->id.us == 1) {
-    ob->runtime.gpd_eval = NULL;
+    BLI_assert(ob->data != NULL);
     gpencil_copy_activeframe_to_eval(depsgraph, scene, ob, ob_orig->data, gpd_eval);
     return;
   }
 
-  /* Copy full Datablock to evaluated version. */
-  ob->runtime.gpd_orig = gpd_orig;
-  if (ob->runtime.gpd_eval != NULL) {
-    BKE_gpencil_eval_delete(ob->runtime.gpd_eval);
-    ob->runtime.gpd_eval = NULL;
-    ob->data = ob->runtime.gpd_orig;
-  }
-  ob->runtime.gpd_eval = gpencil_copy_for_eval(ob->runtime.gpd_orig);
+  /* Copy full datablock to evaluated version. */
+  ob->runtime.gpd_eval = gpencil_copy_for_eval(gpd_orig);
+  /* Overwrite ob->data with gpd_eval here. */
   gpencil_assign_object_eval(ob);
   BKE_gpencil_update_orig_pointers(ob_orig, ob);
 }



More information about the Bf-blender-cvs mailing list