[Bf-blender-cvs] [0e3a2acbfa6] master: Fix T57457: animated image sequences not working in Eevee.

Brecht Van Lommel noreply at git.blender.org
Mon Feb 18 16:53:13 CET 2019


Commit: 0e3a2acbfa6998b3a1ec967f3c25f7e12e0cf8fb
Author: Brecht Van Lommel
Date:   Mon Feb 18 13:23:49 2019 +0100
Branches: master
https://developer.blender.org/rB0e3a2acbfa6998b3a1ec967f3c25f7e12e0cf8fb

Fix T57457: animated image sequences not working in Eevee.

The dependency graph now handles updating image users to point to the current
frame, and tags images to be refreshed on the GPU. The image editor user is
still updated outside of the dependency graph.

We still do not support multiple image users using a different current frame
in the same image, same as 2.7. This may require adding a GPU image texture
cache to keep memory usage under control. Things like rendering an animation
while the viewport stays fixed at the current frame works though.

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

M	source/blender/blenkernel/BKE_image.h
M	source/blender/blenkernel/intern/image.c
M	source/blender/blenkernel/intern/object_update.c
M	source/blender/blenkernel/intern/scene.c
M	source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
M	source/blender/depsgraph/intern/builder/deg_builder_nodes.h
M	source/blender/depsgraph/intern/builder/deg_builder_relations.cc
M	source/blender/depsgraph/intern/builder/deg_builder_relations.h
M	source/blender/depsgraph/intern/node/deg_node_operation.cc
M	source/blender/depsgraph/intern/node/deg_node_operation.h
M	source/blender/draw/engines/gpencil/gpencil_draw_utils.c
M	source/blender/draw/engines/workbench/workbench_forward.c
M	source/blender/draw/engines/workbench/workbench_materials.c
M	source/blender/draw/intern/draw_manager_data.c
M	source/blender/draw/modes/object_mode.c
M	source/blender/draw/modes/paint_texture_mode.c
M	source/blender/editors/space_image/image_buttons.c
M	source/blender/editors/space_image/space_image.c
M	source/blender/gpu/GPU_texture.h
M	source/blender/gpu/intern/gpu_draw.c
M	source/blender/makesrna/intern/rna_image.c
M	source/blender/nodes/shader/nodes/node_shader_tex_environment.c
M	source/blender/nodes/shader/nodes/node_shader_tex_image.c

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

diff --git a/source/blender/blenkernel/BKE_image.h b/source/blender/blenkernel/BKE_image.h
index ed8dab7aa0d..a6a709c204b 100644
--- a/source/blender/blenkernel/BKE_image.h
+++ b/source/blender/blenkernel/BKE_image.h
@@ -207,10 +207,13 @@ void BKE_image_verify_viewer_views(const struct RenderData *rd, struct Image *im
 
 /* called on frame change or before render */
 void BKE_image_user_frame_calc(struct ImageUser *iuser, int cfra);
-void BKE_image_user_check_frame_calc(struct ImageUser *iuser, int cfra);
 int  BKE_image_user_frame_get(const struct ImageUser *iuser, int cfra, bool *r_is_in_range);
 void BKE_image_user_file_path(struct ImageUser *iuser, struct Image *ima, char *path);
-void BKE_image_update_frame(const struct Main *bmain, int cfra);
+void BKE_image_editors_update_frame(const struct Main *bmain, int cfra);
+
+/* dependency graph update for image user users */
+bool BKE_image_user_id_has_animation(struct ID *id);
+void BKE_image_user_id_eval_animation(struct Depsgraph *depsgrah, struct ID *id);
 
 /* sets index offset for multilayer files */
 struct RenderPass *BKE_image_multilayer_index(struct RenderResult *rr, struct ImageUser *iuser);
diff --git a/source/blender/blenkernel/intern/image.c b/source/blender/blenkernel/intern/image.c
index 948d22f5146..072aaaf2310 100644
--- a/source/blender/blenkernel/intern/image.c
+++ b/source/blender/blenkernel/intern/image.c
@@ -88,6 +88,9 @@
 
 #include "BLI_sys_types.h" // for intptr_t support
 
+#include "DEG_depsgraph.h"
+#include "DEG_depsgraph_query.h"
+
 /* for image user iteration */
 #include "DNA_node_types.h"
 #include "DNA_space_types.h"
@@ -4418,26 +4421,72 @@ void BKE_image_user_frame_calc(ImageUser *iuser, int cfra)
 	}
 }
 
-void BKE_image_user_check_frame_calc(ImageUser *iuser, int cfra)
+/* goes over all ImageUsers, and sets frame numbers if auto-refresh is set */
+static void image_editors_update_frame(struct Image *UNUSED(ima), struct ImageUser *iuser, void *customdata)
 {
-	if ((iuser->flag & IMA_ANIM_ALWAYS) || (iuser->flag & IMA_NEED_FRAME_RECALC)) {
-		BKE_image_user_frame_calc(iuser, cfra);
+	int cfra = *(int *)customdata;
 
+	if ((iuser->flag & IMA_ANIM_ALWAYS) ||
+	    (iuser->flag & IMA_NEED_FRAME_RECALC))
+	{
+		BKE_image_user_frame_calc(iuser, cfra);
 		iuser->flag &= ~IMA_NEED_FRAME_RECALC;
 	}
 }
 
-/* goes over all ImageUsers, and sets frame numbers if auto-refresh is set */
-static void image_update_frame(struct Image *UNUSED(ima), struct ImageUser *iuser, void *customdata)
+void BKE_image_editors_update_frame(const Main *bmain, int cfra)
 {
-	int cfra = *(int *)customdata;
+	/* This only updates images used by the user interface. For others the
+	 * dependency graph will call BKE_image_user_id_eval_animation. */
+	wmWindowManager *wm = bmain->wm.first;
+	BKE_image_walk_id_all_users(&wm->id, &cfra, image_editors_update_frame);
+}
+
+static void image_user_id_has_animation(struct Image *ima, struct ImageUser *UNUSED(iuser), void *customdata)
+{
+	if (ima && BKE_image_is_animated(ima)) {
+		*(bool *)customdata = true;
+	}
+}
+
+bool BKE_image_user_id_has_animation(ID *id)
+{
+	bool has_animation = false;
+	BKE_image_walk_id_all_users(id, &has_animation, image_user_id_has_animation);
+	return has_animation;
+}
+
+static void image_user_id_eval_animation(struct Image *ima, struct ImageUser *iuser, void *customdata)
+{
+	if (ima && BKE_image_is_animated(ima)) {
+		Depsgraph *depsgraph = (Depsgraph *)customdata;
+
+		if ((iuser->flag & IMA_ANIM_ALWAYS) ||
+		    (iuser->flag & IMA_NEED_FRAME_RECALC) ||
+		    (DEG_get_mode(depsgraph) == DAG_EVAL_RENDER))
+		{
+			int framenr = iuser->framenr;
+			float cfra = DEG_get_ctime(depsgraph);
+
+			BKE_image_user_frame_calc(iuser, cfra);
+			iuser->flag &= ~IMA_NEED_FRAME_RECALC;
 
-	BKE_image_user_check_frame_calc(iuser, cfra);
+			if (iuser->framenr != framenr) {
+				/* Note: a single texture and refresh doesn't really work when
+				 * multiple image users may use different frames, this is to
+				 * be improved with perhaps a GPU texture cache. */
+				ima->gpuflag |= IMA_GPU_REFRESH;
+			}
+		}
+	}
 }
 
-void BKE_image_update_frame(const Main *bmain, int cfra)
+void BKE_image_user_id_eval_animation(Depsgraph *depsgraph, ID *id)
 {
-	BKE_image_walk_all_users(bmain, &cfra, image_update_frame);
+	/* This is called from the dependency graph to update the image
+	 * users in datablocks. It computes the current frame number
+	 * and tags the image to be refreshed. */
+	BKE_image_walk_id_all_users(id, depsgraph, image_user_id_eval_animation);
 }
 
 void BKE_image_user_file_path(ImageUser *iuser, Image *ima, char *filepath)
@@ -4605,11 +4654,7 @@ bool BKE_image_has_packedfile(Image *ima)
 	return (BLI_listbase_is_empty(&ima->packedfiles) == false);
 }
 
-/**
- * Checks the image buffer changes (not keyframed values)
- *
- * to see if we need to call #BKE_image_user_check_frame_calc
- */
+/* Checks the image buffer changes with time (not keyframed values). */
 bool BKE_image_is_animated(Image *image)
 {
 	return ELEM(image->source, IMA_SRC_MOVIE, IMA_SRC_SEQUENCE);
diff --git a/source/blender/blenkernel/intern/object_update.c b/source/blender/blenkernel/intern/object_update.c
index b82ff00c656..9ab25f01f7b 100644
--- a/source/blender/blenkernel/intern/object_update.c
+++ b/source/blender/blenkernel/intern/object_update.c
@@ -152,8 +152,6 @@ void BKE_object_handle_data_update(
         Scene *scene,
         Object *ob)
 {
-	float ctime = BKE_scene_frame_get(scene);
-
 	DEG_debug_print_eval(depsgraph, __func__, ob->id.name, ob);
 
 	/* includes all keys and modifiers */
@@ -209,12 +207,6 @@ void BKE_object_handle_data_update(
 		case OB_LATTICE:
 			BKE_lattice_modifiers_calc(depsgraph, scene, ob);
 			break;
-
-		case OB_EMPTY:
-			if (ob->empty_drawtype == OB_EMPTY_IMAGE && ob->data)
-				if (BKE_image_is_animated(ob->data))
-					BKE_image_user_check_frame_calc(ob->iuser, (int)ctime);
-			break;
 	}
 
 	/* particles */
diff --git a/source/blender/blenkernel/intern/scene.c b/source/blender/blenkernel/intern/scene.c
index 9f665fee8b6..b055c3695bc 100644
--- a/source/blender/blenkernel/intern/scene.c
+++ b/source/blender/blenkernel/intern/scene.c
@@ -1524,7 +1524,7 @@ void BKE_scene_graph_update_for_newframe(Depsgraph *depsgraph,
 	/* Update animated image textures for particles, modifiers, gpu, etc,
 	 * call this at the start so modifiers with textures don't lag 1 frame.
 	 */
-	BKE_image_update_frame(bmain, scene->r.cfra);
+	BKE_image_editors_update_frame(bmain, scene->r.cfra);
 	BKE_sound_set_cfra(scene->r.cfra);
 	DEG_graph_relations_update(depsgraph, bmain, scene, view_layer);
 	/* Update animated cache files for modifiers.
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
index 524462793fc..59c024e8a3e 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
+++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.cc
@@ -73,6 +73,7 @@ extern "C" {
 #include "BKE_gpencil.h"
 #include "BKE_gpencil_modifier.h"
 #include "BKE_idcode.h"
+#include "BKE_image.h"
 #include "BKE_key.h"
 #include "BKE_lattice.h"
 #include "BKE_mask.h"
@@ -825,11 +826,13 @@ void DepsgraphNodeBuilder::build_object_pointcache(Object *object)
 }
 
 /**
- * Build graph nodes for AnimData block
+ * Build graph nodes for AnimData block and any animated images used.
  * \param id: ID-Block which hosts the AnimData
  */
 void DepsgraphNodeBuilder::build_animdata(ID *id)
 {
+	build_animation_images(id);
+
 	AnimData *adt = BKE_animdata_from_id(id);
 	if (adt == NULL) {
 		return;
@@ -886,6 +889,20 @@ void DepsgraphNodeBuilder::build_animdata_nlastrip_targets(ListBase *strips)
 	}
 }
 
+/**
+ * Build graph nodes to update the current frame in image users.
+ */
+void DepsgraphNodeBuilder::build_animation_images(ID *id)
+{
+	if (BKE_image_user_id_has_animation(id)) {
+		ID *id_cow = get_cow_id(id);
+		add_operation_node(id,
+		                   NodeType::ANIMATION,
+		                   OperationCode::IMAGE_ANIMATION,
+		                   function_bind(BKE_image_user_id_eval_animation, _1, id_cow));
+	}
+}
+
 void DepsgraphNodeBuilder::build_action(bAction *action)
 {
 	if (built_map_.checkIsBuiltAndTag(action)) {
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
index 3b55131d7e2..ce3c6995fe7 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
+++ b/source/blender/depsgraph/intern/builder/deg_builder_nodes.h
@@ -187,6 +187,7 @@ struct DepsgraphNodeBuilder {
 	void build_particle_settings(ParticleSettings *part);
 	void build_animdata(ID *id);
 	void build_animdata_nlastrip_targets(ListBase *strips);
+	void build_animation_images(ID *id);
 	void build_action(bAction *action);
 	void build_driver(ID *id, FCurve *fcurve, int driver_index);
 	void build_driver_variables(ID *id, FCurve *fcurve);
diff --git a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
index 2b77f8c2587..e3b2614ca05 100644
--- a/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
+++ b/source/blender/depsgraph/intern/builder/deg_builder_relations.cc
@@ -72,6 +72,7 @@ extern "C" {
 #include "BKE_effect.h"
 #include "BKE_collision.h"
 #include "BKE_fcurve.h"
+#include "BKE_image.h"
 #include "BKE_key.h"
 #include "BKE_material.h"
 #include "BKE_mball.h"
@@ -1199,6 +1200,8 @@ void DepsgraphRelationBuilder::build_constraints(ID *id,
 
 void DepsgraphRelationBuilder::build_animdata(ID *id)
 {
+	/* Images. */
+	build_animation_images(id);
 	/* Animation curves and NLA. */
 	build_animdata_curves(id);
 	/* Drivers. */
@@ -1391,6 +1394,18 @@ void DepsgraphRelationBuilder::build_animdata_drivers(ID *id)
 	}
 }
 
+void DepsgraphRelationBuilder::build_animation_images(ID *id)
+{
+	/* TODO: can we check for existance of node for performance? */
+	if (BKE_image_user_id_has_animation(id)) {
+		OperationKey image_animation_key(id,
+		                                 NodeType::ANIMATION,
+		                                 OperationCode::IMAGE_ANIMATION);
+		TimeSourceKey time_src_key;
+		add_relatio

@@ Diff output truncated at 10240 characters. @@



More information about the Bf-blender-cvs mailing list