[Bf-blender-cvs] [9a45c9d] master: Fix T41109: Reloading image that has been modified outside Blender does not update image in Image Texture nodes

Sergey Sharybin noreply at git.blender.org
Fri Jul 18 15:37:39 CEST 2014


Commit: 9a45c9dadf435ac6c1329372dc08f21b1af242c6
Author: Sergey Sharybin
Date:   Fri Jul 18 19:28:33 2014 +0600
https://developer.blender.org/rB9a45c9dadf435ac6c1329372dc08f21b1af242c6

Fix T41109: Reloading image that has been modified outside Blender does not update image in Image Texture nodes

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

M	intern/cycles/blender/blender_shader.cpp
M	intern/cycles/render/image.cpp
M	intern/cycles/render/image.h
M	source/blender/blenkernel/intern/depsgraph.c
M	source/blender/editors/space_image/image_ops.c

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

diff --git a/intern/cycles/blender/blender_shader.cpp b/intern/cycles/blender/blender_shader.cpp
index 51d8a4d..193eb69 100644
--- a/intern/cycles/blender/blender_shader.cpp
+++ b/intern/cycles/blender/blender_shader.cpp
@@ -572,6 +572,13 @@ static ShaderNode *add_node(Scene *scene, BL::BlendData b_data, BL::Scene b_scen
 
 			image->animated = b_image_node.image_user().use_auto_refresh();
 			image->use_alpha = b_image.use_alpha();
+
+			/* TODO(sergey): Does not work properly when we change builtin type. */
+			if (b_image.is_updated()) {
+				scene->image_manager->tag_reload_image(image->filename,
+				                                       image->builtin_data,
+				                                       (InterpolationType)b_image_node.interpolation());
+			}
 		}
 		image->color_space = ImageTextureNode::color_space_enum[(int)b_image_node.color_space()];
 		image->projection = ImageTextureNode::projection_enum[(int)b_image_node.projection()];
@@ -602,6 +609,13 @@ static ShaderNode *add_node(Scene *scene, BL::BlendData b_data, BL::Scene b_scen
 			}
 
 			env->use_alpha = b_image.use_alpha();
+
+			/* TODO(sergey): Does not work properly when we change builtin type. */
+			if (b_image.is_updated()) {
+				scene->image_manager->tag_reload_image(env->filename,
+				                                       env->builtin_data,
+				                                       INTERPOLATION_LINEAR);
+			}
 		}
 		env->color_space = EnvironmentTextureNode::color_space_enum[(int)b_env_node.color_space()];
 		env->projection = EnvironmentTextureNode::projection_enum[(int)b_env_node.projection()];
diff --git a/intern/cycles/render/image.cpp b/intern/cycles/render/image.cpp
index 8369df5..f84396a 100644
--- a/intern/cycles/render/image.cpp
+++ b/intern/cycles/render/image.cpp
@@ -313,6 +313,32 @@ void ImageManager::remove_image(const string& filename, void *builtin_data, Inte
 	}
 }
 
+/* TODO(sergey): Deduplicate with the iteration above, but make it pretty,
+ * without bunch of arguments passing around making code readability even
+ * more cluttered.
+ */
+void ImageManager::tag_reload_image(const string& filename, void *builtin_data, InterpolationType interpolation)
+{
+	size_t slot;
+
+	for(slot = 0; slot < images.size(); slot++) {
+		if(images[slot] && image_equals(images[slot], filename, builtin_data, interpolation)) {
+			images[slot]->need_load = true;
+			break;
+		}
+	}
+
+	if(slot == images.size()) {
+		/* see if it's in a float texture slot */
+		for(slot = 0; slot < float_images.size(); slot++) {
+			if(float_images[slot] && image_equals(float_images[slot], filename, builtin_data, interpolation)) {
+				images[slot]->need_load = true;
+				break;
+			}
+		}
+	}
+}
+
 bool ImageManager::file_load_image(Image *img, device_vector<uchar4>& tex_img)
 {
 	if(img->filename == "")
diff --git a/intern/cycles/render/image.h b/intern/cycles/render/image.h
index 50ea346..535f0ff 100644
--- a/intern/cycles/render/image.h
+++ b/intern/cycles/render/image.h
@@ -59,6 +59,7 @@ public:
 		bool& is_float, bool& is_linear, InterpolationType interpolation, bool use_alpha);
 	void remove_image(int slot);
 	void remove_image(const string& filename, void *builtin_data, InterpolationType interpolation);
+	void tag_reload_image(const string& filename, void *builtin_data, InterpolationType interpolation);
 	bool is_float_image(const string& filename, void *builtin_data, bool& is_linear);
 
 	void device_update(Device *device, DeviceScene *dscene, Progress& progress);
diff --git a/source/blender/blenkernel/intern/depsgraph.c b/source/blender/blenkernel/intern/depsgraph.c
index 24b5806..95e608a 100644
--- a/source/blender/blenkernel/intern/depsgraph.c
+++ b/source/blender/blenkernel/intern/depsgraph.c
@@ -2502,6 +2502,23 @@ static void dag_id_flush_update(Main *bmain, Scene *sce, ID *id)
 			}
 		}
 
+		/* Not pretty to iterate all the nodes here, but it's as good as it
+		 * could be with the current depsgraph design/
+		 */
+		if (idtype == ID_IM) {
+			FOREACH_NODETREE(bmain, ntree, parent_id) {
+				if (ntree->type == NTREE_SHADER) {
+					bNode *node;
+					for (node = ntree->nodes.first; node; node = node->next) {
+						if (node->id == id) {
+							lib_id_recalc_tag(bmain, &ntree->id);
+							break;
+						}
+					}
+				}
+			} FOREACH_NODETREE_END
+		}
+
 		if (idtype == ID_MSK) {
 			if (sce->nodetree) {
 				bNode *node;
diff --git a/source/blender/editors/space_image/image_ops.c b/source/blender/editors/space_image/image_ops.c
index 7c021cf..4ae05d8 100644
--- a/source/blender/editors/space_image/image_ops.c
+++ b/source/blender/editors/space_image/image_ops.c
@@ -48,6 +48,7 @@
 
 #include "BKE_colortools.h"
 #include "BKE_context.h"
+#include "BKE_depsgraph.h"
 #include "BKE_icons.h"
 #include "BKE_image.h"
 #include "BKE_global.h"
@@ -1866,6 +1867,7 @@ static int image_reload_exec(bContext *C, wmOperator *UNUSED(op))
 	
 	// XXX other users?
 	BKE_image_signal(ima, (sima) ? &sima->iuser : NULL, IMA_SIGNAL_RELOAD);
+	DAG_id_tag_update(&ima->id, 0);
 
 	WM_event_add_notifier(C, NC_IMAGE | NA_EDITED, ima);




More information about the Bf-blender-cvs mailing list