[Bf-blender-cvs] [1693a5efe91] master: Fix T66378: Missing animation update when switching view layer

Sergey Sharybin noreply at git.blender.org
Fri Jul 26 10:32:42 CEST 2019


Commit: 1693a5efe91999b60b3dc0bdff727473b3bd00bb
Author: Sergey Sharybin
Date:   Wed Jul 24 12:40:33 2019 +0200
Branches: master
https://developer.blender.org/rB1693a5efe91999b60b3dc0bdff727473b3bd00bb

Fix T66378: Missing animation update when switching view layer

Current frame is stored in a scene, and scene might have multiple view
layers. The inactive view layers were not informed about scene's frame
being changed, so when user switched back to view after changing scene
frame it was in an inconsistent state between current scene frame and
animation.

Now we tag scene for time changes, so dependency graph can catch up
and do proper update.

Currently tagging is from quite generic place. Probably better approach
would be to tag from where frame is actually being assigned. Downside
of this is that it's easy to miss some places.

Reviewers: brecht, mont29

Reviewed By: brecht

Maniphest Tasks: T66378

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

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

M	source/blender/depsgraph/intern/depsgraph.cc
M	source/blender/depsgraph/intern/depsgraph.h
M	source/blender/depsgraph/intern/depsgraph_eval.cc
M	source/blender/depsgraph/intern/depsgraph_tag.cc
M	source/blender/depsgraph/intern/eval/deg_eval_flush.cc
M	source/blender/editors/screen/screen_edit.c
M	source/blender/makesdna/DNA_ID.h

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

diff --git a/source/blender/depsgraph/intern/depsgraph.cc b/source/blender/depsgraph/intern/depsgraph.cc
index d8a9b41206b..6d3aed65a14 100644
--- a/source/blender/depsgraph/intern/depsgraph.cc
+++ b/source/blender/depsgraph/intern/depsgraph.cc
@@ -68,6 +68,7 @@ template<typename T> static void remove_from_vector(vector<T> *vector, const T &
 Depsgraph::Depsgraph(Scene *scene, ViewLayer *view_layer, eEvaluationMode mode)
     : time_source(NULL),
       need_update(true),
+      need_update_time(false),
       scene(scene),
       view_layer(view_layer),
       mode(mode),
diff --git a/source/blender/depsgraph/intern/depsgraph.h b/source/blender/depsgraph/intern/depsgraph.h
index f194a44346b..507d2d9ec08 100644
--- a/source/blender/depsgraph/intern/depsgraph.h
+++ b/source/blender/depsgraph/intern/depsgraph.h
@@ -160,6 +160,10 @@ struct Depsgraph {
   /* Nodes which have been tagged as "directly modified". */
   GSet *entry_tags;
 
+  /* Special entry tag for time source. Allows to tag invisible dependency graphs for update when
+   * scene frame changes, so then when dependency graph becomes visible it is on a proper state. */
+  bool need_update_time;
+
   /* Convenience Data ................... */
 
   /* XXX: should be collected after building (if actually needed?) */
diff --git a/source/blender/depsgraph/intern/depsgraph_eval.cc b/source/blender/depsgraph/intern/depsgraph_eval.cc
index 6f3262174b4..f519fe76724 100644
--- a/source/blender/depsgraph/intern/depsgraph_eval.cc
+++ b/source/blender/depsgraph/intern/depsgraph_eval.cc
@@ -61,6 +61,7 @@ void DEG_evaluate_on_refresh(Depsgraph *graph)
     BKE_scene_frame_set(deg_graph->scene_cow, deg_graph->ctime);
   }
   DEG::deg_evaluate_on_refresh(deg_graph);
+  deg_graph->need_update_time = false;
 }
 
 /* Frame-change happened for root scene that graph belongs to. */
@@ -79,6 +80,7 @@ void DEG_evaluate_on_framechange(Main *bmain, Depsgraph *graph, float ctime)
   }
   /* Perform recalculation updates. */
   DEG::deg_evaluate_on_refresh(deg_graph);
+  deg_graph->need_update_time = false;
 }
 
 bool DEG_needs_eval(Depsgraph *graph)
diff --git a/source/blender/depsgraph/intern/depsgraph_tag.cc b/source/blender/depsgraph/intern/depsgraph_tag.cc
index 583191490d2..f9105b53536 100644
--- a/source/blender/depsgraph/intern/depsgraph_tag.cc
+++ b/source/blender/depsgraph/intern/depsgraph_tag.cc
@@ -229,6 +229,9 @@ void depsgraph_tag_to_component_opcode(const ID *id,
     case ID_RECALC_PARAMETERS:
       *component_type = NodeType::PARAMETERS;
       break;
+    case ID_RECALC_TIME:
+      BLI_assert(!"Should be handled outside of this function");
+      break;
     case ID_RECALC_ALL:
     case ID_RECALC_PSYS_ALL:
       BLI_assert(!"Should not happen");
@@ -360,6 +363,12 @@ static void graph_id_tag_update_single_flag(Main *bmain,
     }
     return;
   }
+  else if (tag == ID_RECALC_TIME) {
+    if (graph != NULL) {
+      graph->need_update_time = true;
+    }
+    return;
+  }
   /* Get description of what is to be tagged. */
   NodeType component_type;
   OperationCode operation_code;
@@ -664,6 +673,8 @@ const char *DEG_update_tag_as_string(IDRecalcFlag flag)
       return "AUDIO";
     case ID_RECALC_PARAMETERS:
       return "PARAMETERS";
+    case ID_RECALC_TIME:
+      return "TIME";
     case ID_RECALC_ALL:
       return "ALL";
   }
diff --git a/source/blender/depsgraph/intern/eval/deg_eval_flush.cc b/source/blender/depsgraph/intern/eval/deg_eval_flush.cc
index 83fcf4c6ea1..e54adcd8655 100644
--- a/source/blender/depsgraph/intern/eval/deg_eval_flush.cc
+++ b/source/blender/depsgraph/intern/eval/deg_eval_flush.cc
@@ -39,6 +39,7 @@
 
 extern "C" {
 #include "DNA_object_types.h"
+#include "DNA_scene_types.h"
 
 #include "DRW_engine.h"
 } /* extern "C" */
@@ -53,6 +54,7 @@ extern "C" {
 #include "intern/node/deg_node_factory.h"
 #include "intern/node/deg_node_id.h"
 #include "intern/node/deg_node_operation.h"
+#include "intern/node/deg_node_time.h"
 
 #include "intern/eval/deg_eval_copy_on_write.h"
 
@@ -348,9 +350,16 @@ void deg_graph_flush_updates(Main *bmain, Depsgraph *graph)
   BLI_assert(bmain != NULL);
   BLI_assert(graph != NULL);
   /* Nothing to update, early out. */
-  if (BLI_gset_len(graph->entry_tags) == 0) {
+  if (BLI_gset_len(graph->entry_tags) == 0 && !graph->need_update_time) {
     return;
   }
+  if (graph->need_update_time) {
+    const Scene *scene_orig = graph->scene;
+    const float ctime = scene_orig->r.cfra + scene_orig->r.subframe;
+    DEG::TimeSourceNode *time_source = graph->find_time_source();
+    graph->ctime = ctime;
+    time_source->tag_update(graph, DEG::DEG_UPDATE_SOURCE_TIME);
+  }
   /* Reset all flags, get ready for the flush. */
   flush_prepare(graph);
   /* Starting from the tagged "entry" nodes, flush outwards. */
diff --git a/source/blender/editors/screen/screen_edit.c b/source/blender/editors/screen/screen_edit.c
index e59477fbe6e..dddc33e3ad0 100644
--- a/source/blender/editors/screen/screen_edit.c
+++ b/source/blender/editors/screen/screen_edit.c
@@ -1457,6 +1457,8 @@ void ED_update_for_newframe(Main *bmain, Depsgraph *depsgraph)
 {
   Scene *scene = DEG_get_input_scene(depsgraph);
 
+  DEG_id_tag_update_ex(bmain, &scene->id, ID_RECALC_TIME);
+
 #ifdef DURIAN_CAMERA_SWITCH
   void *camera = BKE_scene_camera_switch_find(scene);
   if (camera && scene->camera != camera) {
diff --git a/source/blender/makesdna/DNA_ID.h b/source/blender/makesdna/DNA_ID.h
index cad1af8eb50..dc4164169f9 100644
--- a/source/blender/makesdna/DNA_ID.h
+++ b/source/blender/makesdna/DNA_ID.h
@@ -616,6 +616,10 @@ typedef enum IDRecalcFlag {
 
   ID_RECALC_PARAMETERS = (1 << 21),
 
+  /* Makes it so everything what depends on time.
+   * Basically, the same what changing frame in a timeline will do. */
+  ID_RECALC_TIME = (1 << 22),
+
   /***************************************************************************
    * Pseudonyms, to have more semantic meaning in the actual code without
    * using too much low-level and implementation specific tags. */



More information about the Bf-blender-cvs mailing list