瀏覽代碼

Enforce calling RenderingDevice code from rendering thread in TextureRD classes

clayjohn 1 年之前
父節點
當前提交
83241ab139
共有 2 個文件被更改,包括 108 次插入87 次删除
  1. 99 87
      scene/resources/texture_rd.cpp
  2. 9 0
      scene/resources/texture_rd.h

+ 99 - 87
scene/resources/texture_rd.cpp

@@ -74,27 +74,7 @@ void Texture2DRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	ERR_FAIL_NULL(RS::get_singleton());
 
 	if (p_texture_rd_rid.is_valid()) {
-		ERR_FAIL_NULL(RD::get_singleton());
-		ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
-
-		RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
-		ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_2D);
-		ERR_FAIL_COND(tf.depth > 1);
-		ERR_FAIL_COND(tf.array_layers > 1);
-
-		size.width = tf.width;
-		size.height = tf.height;
-
-		texture_rd_rid = p_texture_rd_rid;
-
-		if (texture_rid.is_valid()) {
-			RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid));
-		} else {
-			texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid);
-		}
-
-		notify_property_list_changed();
-		emit_changed();
+		RS::get_singleton()->call_on_render_thread(callable_mp(this, &Texture2DRD::_set_texture_rd_rid).bind(p_texture_rd_rid));
 	} else if (texture_rid.is_valid()) {
 		RS::get_singleton()->free(texture_rid);
 		texture_rid = RID();
@@ -105,6 +85,30 @@ void Texture2DRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	}
 }
 
+void Texture2DRD::_set_texture_rd_rid(RID p_texture_rd_rid) {
+	ERR_FAIL_NULL(RD::get_singleton());
+	ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
+
+	RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
+	ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_2D);
+	ERR_FAIL_COND(tf.depth > 1);
+	ERR_FAIL_COND(tf.array_layers > 1);
+
+	size.width = tf.width;
+	size.height = tf.height;
+
+	texture_rd_rid = p_texture_rd_rid;
+
+	if (texture_rid.is_valid()) {
+		RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid));
+	} else {
+		texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid);
+	}
+
+	notify_property_list_changed();
+	emit_changed();
+}
+
 RID Texture2DRD::get_texture_rd_rid() const {
 	return texture_rd_rid;
 }
@@ -173,48 +177,7 @@ void TextureLayeredRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	ERR_FAIL_NULL(RS::get_singleton());
 
 	if (p_texture_rd_rid.is_valid()) {
-		ERR_FAIL_NULL(RD::get_singleton());
-		ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
-
-		RS::TextureLayeredType rs_layer_type;
-		RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
-		ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_2D_ARRAY);
-		ERR_FAIL_COND(tf.depth > 1);
-		switch (layer_type) {
-			case LAYERED_TYPE_2D_ARRAY: {
-				ERR_FAIL_COND(tf.array_layers <= 1);
-				rs_layer_type = RS::TEXTURE_LAYERED_2D_ARRAY;
-			} break;
-			case LAYERED_TYPE_CUBEMAP: {
-				ERR_FAIL_COND(tf.array_layers != 6);
-				rs_layer_type = RS::TEXTURE_LAYERED_CUBEMAP;
-			} break;
-			case LAYERED_TYPE_CUBEMAP_ARRAY: {
-				ERR_FAIL_COND((tf.array_layers == 0) || ((tf.array_layers % 6) != 0));
-				rs_layer_type = RS::TEXTURE_LAYERED_CUBEMAP_ARRAY;
-			} break;
-			default: {
-				ERR_FAIL_MSG("Unknown layer type selected");
-			} break;
-		}
-
-		size.width = tf.width;
-		size.height = tf.height;
-		layers = tf.array_layers;
-		mipmaps = tf.mipmaps;
-
-		texture_rd_rid = p_texture_rd_rid;
-
-		if (texture_rid.is_valid()) {
-			RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid, rs_layer_type));
-		} else {
-			texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid, rs_layer_type);
-		}
-
-		image_format = RS::get_singleton()->texture_get_format(texture_rid);
-
-		notify_property_list_changed();
-		emit_changed();
+		RS::get_singleton()->call_on_render_thread(callable_mp(this, &TextureLayeredRD::_set_texture_rd_rid).bind(p_texture_rd_rid));
 	} else if (texture_rid.is_valid()) {
 		RS::get_singleton()->free(texture_rid);
 		texture_rid = RID();
@@ -228,6 +191,51 @@ void TextureLayeredRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	}
 }
 
+void TextureLayeredRD::_set_texture_rd_rid(RID p_texture_rd_rid) {
+	ERR_FAIL_NULL(RD::get_singleton());
+	ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
+
+	RS::TextureLayeredType rs_layer_type;
+	RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
+	ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_2D_ARRAY);
+	ERR_FAIL_COND(tf.depth > 1);
+	switch (layer_type) {
+		case LAYERED_TYPE_2D_ARRAY: {
+			ERR_FAIL_COND(tf.array_layers <= 1);
+			rs_layer_type = RS::TEXTURE_LAYERED_2D_ARRAY;
+		} break;
+		case LAYERED_TYPE_CUBEMAP: {
+			ERR_FAIL_COND(tf.array_layers != 6);
+			rs_layer_type = RS::TEXTURE_LAYERED_CUBEMAP;
+		} break;
+		case LAYERED_TYPE_CUBEMAP_ARRAY: {
+			ERR_FAIL_COND((tf.array_layers == 0) || ((tf.array_layers % 6) != 0));
+			rs_layer_type = RS::TEXTURE_LAYERED_CUBEMAP_ARRAY;
+		} break;
+		default: {
+			ERR_FAIL_MSG("Unknown layer type selected");
+		} break;
+	}
+
+	size.width = tf.width;
+	size.height = tf.height;
+	layers = tf.array_layers;
+	mipmaps = tf.mipmaps;
+
+	texture_rd_rid = p_texture_rd_rid;
+
+	if (texture_rid.is_valid()) {
+		RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid, rs_layer_type));
+	} else {
+		texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid, rs_layer_type);
+	}
+
+	image_format = RS::get_singleton()->texture_get_format(texture_rid);
+
+	notify_property_list_changed();
+	emit_changed();
+}
+
 RID TextureLayeredRD::get_texture_rd_rid() const {
 	return texture_rd_rid;
 }
@@ -291,30 +299,7 @@ void Texture3DRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	ERR_FAIL_NULL(RS::get_singleton());
 
 	if (p_texture_rd_rid.is_valid()) {
-		ERR_FAIL_NULL(RD::get_singleton());
-		ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
-
-		RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
-		ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_3D);
-		ERR_FAIL_COND(tf.array_layers > 1);
-
-		size.x = tf.width;
-		size.y = tf.height;
-		size.z = tf.depth;
-		mipmaps = tf.mipmaps;
-
-		texture_rd_rid = p_texture_rd_rid;
-
-		if (texture_rid.is_valid()) {
-			RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid));
-		} else {
-			texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid);
-		}
-
-		image_format = RS::get_singleton()->texture_get_format(texture_rid);
-
-		notify_property_list_changed();
-		emit_changed();
+		RS::get_singleton()->call_on_render_thread(callable_mp(this, &Texture3DRD::_set_texture_rd_rid).bind(p_texture_rd_rid));
 	} else if (texture_rid.is_valid()) {
 		RS::get_singleton()->free(texture_rid);
 		texture_rid = RID();
@@ -327,6 +312,33 @@ void Texture3DRD::set_texture_rd_rid(RID p_texture_rd_rid) {
 	}
 }
 
+void Texture3DRD::_set_texture_rd_rid(RID p_texture_rd_rid) {
+	ERR_FAIL_NULL(RD::get_singleton());
+	ERR_FAIL_COND(!RD::get_singleton()->texture_is_valid(p_texture_rd_rid));
+
+	RD::TextureFormat tf = RD::get_singleton()->texture_get_format(p_texture_rd_rid);
+	ERR_FAIL_COND(tf.texture_type != RD::TEXTURE_TYPE_3D);
+	ERR_FAIL_COND(tf.array_layers > 1);
+
+	size.x = tf.width;
+	size.y = tf.height;
+	size.z = tf.depth;
+	mipmaps = tf.mipmaps;
+
+	texture_rd_rid = p_texture_rd_rid;
+
+	if (texture_rid.is_valid()) {
+		RS::get_singleton()->texture_replace(texture_rid, RS::get_singleton()->texture_rd_create(p_texture_rd_rid));
+	} else {
+		texture_rid = RS::get_singleton()->texture_rd_create(p_texture_rd_rid);
+	}
+
+	image_format = RS::get_singleton()->texture_get_format(texture_rid);
+
+	notify_property_list_changed();
+	emit_changed();
+}
+
 RID Texture3DRD::get_texture_rd_rid() const {
 	return texture_rd_rid;
 }

+ 9 - 0
scene/resources/texture_rd.h

@@ -60,6 +60,9 @@ public:
 	void set_texture_rd_rid(RID p_texture_rd_rid);
 	RID get_texture_rd_rid() const;
 
+	// Internal function that should only be called from the rendering thread.
+	void _set_texture_rd_rid(RID p_texture_rd_rid);
+
 	Texture2DRD();
 	~Texture2DRD();
 };
@@ -94,6 +97,9 @@ public:
 	void set_texture_rd_rid(RID p_texture_rd_rid);
 	RID get_texture_rd_rid() const;
 
+	// Internal function that should only be called from the rendering thread.
+	void _set_texture_rd_rid(RID p_texture_rd_rid);
+
 	TextureLayeredRD(LayeredType p_layer_type);
 	~TextureLayeredRD();
 };
@@ -146,6 +152,9 @@ public:
 	void set_texture_rd_rid(RID p_texture_rd_rid);
 	RID get_texture_rd_rid() const;
 
+	// Internal function that should only be called from the rendering thread.
+	void _set_texture_rd_rid(RID p_texture_rd_rid);
+
 	Texture3DRD();
 	~Texture3DRD();
 };