Browse Source

Merge pull request #51402 from tinmanjuggernaut/texture_array_anisotropic

[3.x] Add Anisotropic Filter option for TextureArrays
Rémi Verschelde 4 years ago
parent
commit
54d14a912a

+ 12 - 0
doc/classes/Texture3D.xml

@@ -9,9 +9,21 @@
 	<tutorials>
 	</tutorials>
 	<methods>
+		<method name="create">
+			<return type="void" />
+			<argument index="0" name="width" type="int" />
+			<argument index="1" name="height" type="int" />
+			<argument index="2" name="depth" type="int" />
+			<argument index="3" name="format" type="int" enum="Image.Format" />
+			<argument index="4" name="flags" type="int" default="4" />
+			<description>
+				Creates the Texture3D with specified [code]width[/code], [code]height[/code], and [code]depth[/code]. See [enum Image.Format] for [code]format[/code] options. See [enum TextureLayered.Flags] enumerator for [code]flags[/code] options.
+			</description>
+		</method>
 	</methods>
 	<members>
 		<member name="data" type="Dictionary" setter="_set_data" getter="_get_data" override="true" default="{&quot;depth&quot;: 0,&quot;flags&quot;: 4,&quot;format&quot;: 37,&quot;height&quot;: 0,&quot;layers&quot;: [  ],&quot;width&quot;: 0}" />
+		<member name="flags" type="int" setter="set_flags" getter="get_flags" override="true" default="4" />
 	</members>
 	<constants>
 	</constants>

+ 11 - 0
doc/classes/TextureArray.xml

@@ -21,6 +21,17 @@
 	<tutorials>
 	</tutorials>
 	<methods>
+		<method name="create">
+			<return type="void" />
+			<argument index="0" name="width" type="int" />
+			<argument index="1" name="height" type="int" />
+			<argument index="2" name="depth" type="int" />
+			<argument index="3" name="format" type="int" enum="Image.Format" />
+			<argument index="4" name="flags" type="int" default="7" />
+			<description>
+				Creates the TextureArray with specified [code]width[/code], [code]height[/code], and [code]depth[/code]. See [enum Image.Format] for [code]format[/code] options. See [enum TextureLayered.Flags] enumerator for [code]flags[/code] options.
+			</description>
+		</method>
 	</methods>
 	<constants>
 	</constants>

+ 11 - 15
doc/classes/TextureLayered.xml

@@ -9,17 +9,6 @@
 	<tutorials>
 	</tutorials>
 	<methods>
-		<method name="create">
-			<return type="void" />
-			<argument index="0" name="width" type="int" />
-			<argument index="1" name="height" type="int" />
-			<argument index="2" name="depth" type="int" />
-			<argument index="3" name="format" type="int" enum="Image.Format" />
-			<argument index="4" name="flags" type="int" default="4" />
-			<description>
-				Creates the [Texture3D] or [TextureArray] with specified [code]width[/code], [code]height[/code], and [code]depth[/code]. See [enum Image.Format] for [code]format[/code] options. See [enum Flags] enumerator for [code]flags[/code] options.
-			</description>
-		</method>
 		<method name="get_depth" qualifiers="const">
 			<return type="int" />
 			<description>
@@ -72,14 +61,20 @@
 		</method>
 	</methods>
 	<members>
-		<member name="data" type="Dictionary" setter="_set_data" getter="_get_data" default="{&quot;depth&quot;: 0,&quot;flags&quot;: 4,&quot;format&quot;: 37,&quot;height&quot;: 0,&quot;layers&quot;: [  ],&quot;width&quot;: 0}">
+		<member name="data" type="Dictionary" setter="_set_data" getter="_get_data" default="{&quot;depth&quot;: 0,&quot;flags&quot;: 7,&quot;format&quot;: 37,&quot;height&quot;: 0,&quot;layers&quot;: [  ],&quot;width&quot;: 0}">
 			Returns a dictionary with all the data used by this texture.
 		</member>
-		<member name="flags" type="int" setter="set_flags" getter="get_flags" default="4">
+		<member name="flags" type="int" setter="set_flags" getter="get_flags" default="7">
 			Specifies which [enum Flags] apply to this texture.
 		</member>
 	</members>
 	<constants>
+		<constant name="FLAGS_DEFAULT_TEXTURE_ARRAY" value="7" enum="Flags">
+			Default flags for [TextureArray]. [constant FLAG_MIPMAPS], [constant FLAG_REPEAT] and [constant FLAG_FILTER] are enabled.
+		</constant>
+		<constant name="FLAGS_DEFAULT_TEXTURE_3D" value="4" enum="Flags">
+			Default flags for [Texture3D]. [constant FLAG_FILTER] is enabled.
+		</constant>
 		<constant name="FLAG_MIPMAPS" value="1" enum="Flags">
 			Texture will generate mipmaps on creation.
 		</constant>
@@ -89,8 +84,9 @@
 		<constant name="FLAG_FILTER" value="4" enum="Flags">
 			Use filtering when reading from texture. Filtering smooths out pixels. Turning filtering off is slightly faster and more appropriate when you need access to individual pixels.
 		</constant>
-		<constant name="FLAGS_DEFAULT" value="4" enum="Flags">
-			Equivalent to [constant FLAG_FILTER].
+		<constant name="FLAG_ANISOTROPIC_FILTER" value="8" enum="Flags">
+			Uses anisotropic mipmap filtering. Generates smaller versions of the same texture with different aspect ratios.
+			This results in better-looking textures when viewed from oblique angles.
 		</constant>
 	</constants>
 </class>

+ 5 - 0
editor/import/resource_importer_layered_texture.cpp

@@ -79,6 +79,7 @@ void ResourceImporterLayeredTexture::get_import_options(List<ImportOption> *r_op
 	r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "flags/repeat", PROPERTY_HINT_ENUM, "Disabled,Enabled,Mirrored"), 0));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "flags/filter"), true));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "flags/mipmaps"), p_preset == PRESET_COLOR_CORRECT ? 0 : 1));
+	r_options->push_back(ImportOption(PropertyInfo(Variant::BOOL, "flags/anisotropic"), false));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "flags/srgb", PROPERTY_HINT_ENUM, "Disable,Enable"), p_preset == PRESET_3D ? 1 : 0));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "slices/horizontal", PROPERTY_HINT_RANGE, "1,256,1"), p_preset == PRESET_COLOR_CORRECT ? 16 : 8));
 	r_options->push_back(ImportOption(PropertyInfo(Variant::INT, "slices/vertical", PROPERTY_HINT_RANGE, "1,256,1"), p_preset == PRESET_COLOR_CORRECT ? 1 : 8));
@@ -187,6 +188,7 @@ Error ResourceImporterLayeredTexture::import(const String &p_source_file, const
 	int repeat = p_options["flags/repeat"];
 	bool filter = p_options["flags/filter"];
 	bool mipmaps = p_options["flags/mipmaps"];
+	bool anisotropic = p_options["flags/anisotropic"];
 	int srgb = p_options["flags/srgb"];
 	int hslices = p_options["slices/horizontal"];
 	int vslices = p_options["slices/vertical"];
@@ -211,6 +213,9 @@ Error ResourceImporterLayeredTexture::import(const String &p_source_file, const
 	if (mipmaps || compress_mode == COMPRESS_VIDEO_RAM) {
 		tex_flags |= Texture::FLAG_MIPMAPS;
 	}
+	if (anisotropic) {
+		tex_flags |= Texture::FLAG_ANISOTROPIC_FILTER;
+	}
 	if (srgb == 1) {
 		tex_flags |= Texture::FLAG_CONVERT_TO_LINEAR;
 	}

+ 14 - 5
scene/resources/texture.cpp

@@ -78,7 +78,7 @@ void Texture::_bind_methods() {
 	ClassDB::bind_method(D_METHOD("get_data"), &Texture::get_data);
 
 	ADD_GROUP("Flags", "");
-	ADD_PROPERTY(PropertyInfo(Variant::INT, "flags", PROPERTY_HINT_FLAGS, "Mipmaps,Repeat,Filter,Anisotropic Linear,Convert to Linear,Mirrored Repeat,Video Surface"), "set_flags", "get_flags");
+	ADD_PROPERTY(PropertyInfo(Variant::INT, "flags", PROPERTY_HINT_FLAGS, "Mipmaps,Repeat,Filter,Anisotropic Filter,Convert to Linear,Mirrored Repeat,Video Surface"), "set_flags", "get_flags");
 	ADD_GROUP("", "");
 
 	BIND_ENUM_CONSTANT(FLAGS_DEFAULT);
@@ -2381,7 +2381,6 @@ void TextureLayered::_bind_methods() {
 	ClassDB::bind_method(D_METHOD("get_height"), &TextureLayered::get_height);
 	ClassDB::bind_method(D_METHOD("get_depth"), &TextureLayered::get_depth);
 
-	ClassDB::bind_method(D_METHOD("create", "width", "height", "depth", "format", "flags"), &TextureLayered::create, DEFVAL(FLAGS_DEFAULT));
 	ClassDB::bind_method(D_METHOD("set_layer_data", "image", "layer"), &TextureLayered::set_layer_data);
 	ClassDB::bind_method(D_METHOD("get_layer_data", "layer"), &TextureLayered::get_layer_data);
 	ClassDB::bind_method(D_METHOD("set_data_partial", "image", "x_offset", "y_offset", "layer", "mipmap"), &TextureLayered::set_data_partial, DEFVAL(0));
@@ -2389,19 +2388,21 @@ void TextureLayered::_bind_methods() {
 	ClassDB::bind_method(D_METHOD("_set_data", "data"), &TextureLayered::_set_data);
 	ClassDB::bind_method(D_METHOD("_get_data"), &TextureLayered::_get_data);
 
-	ADD_PROPERTY(PropertyInfo(Variant::INT, "flags", PROPERTY_HINT_FLAGS, "Mipmaps,Repeat,Filter"), "set_flags", "get_flags");
+	ADD_PROPERTY(PropertyInfo(Variant::INT, "flags", PROPERTY_HINT_FLAGS, "Mipmaps,Repeat,Filter,Anisotropic Filter"), "set_flags", "get_flags");
 	ADD_PROPERTY(PropertyInfo(Variant::DICTIONARY, "data", PROPERTY_HINT_NONE, "", PROPERTY_USAGE_NOEDITOR), "_set_data", "_get_data");
 
+	BIND_ENUM_CONSTANT(FLAGS_DEFAULT_TEXTURE_ARRAY);
+	BIND_ENUM_CONSTANT(FLAGS_DEFAULT_TEXTURE_3D);
 	BIND_ENUM_CONSTANT(FLAG_MIPMAPS);
 	BIND_ENUM_CONSTANT(FLAG_REPEAT);
 	BIND_ENUM_CONSTANT(FLAG_FILTER);
-	BIND_ENUM_CONSTANT(FLAGS_DEFAULT);
+	BIND_ENUM_CONSTANT(FLAG_ANISOTROPIC_FILTER);
 }
 
 TextureLayered::TextureLayered(bool p_3d) {
 	is_3d = p_3d;
+	flags = p_3d ? FLAGS_DEFAULT_TEXTURE_3D : FLAGS_DEFAULT_TEXTURE_ARRAY;
 	format = Image::FORMAT_MAX;
-	flags = FLAGS_DEFAULT;
 
 	width = 0;
 	height = 0;
@@ -2416,6 +2417,14 @@ TextureLayered::~TextureLayered() {
 	}
 }
 
+void Texture3D::_bind_methods() {
+	ClassDB::bind_method(D_METHOD("create", "width", "height", "depth", "format", "flags"), &Texture3D::create, DEFVAL(FLAGS_DEFAULT_TEXTURE_3D));
+}
+
+void TextureArray::_bind_methods() {
+	ClassDB::bind_method(D_METHOD("create", "width", "height", "depth", "format", "flags"), &TextureArray::create, DEFVAL(FLAGS_DEFAULT_TEXTURE_ARRAY));
+}
+
 RES ResourceFormatLoaderTextureLayered::load(const String &p_path, const String &p_original_path, Error *r_error) {
 	if (r_error) {
 		*r_error = ERR_CANT_OPEN;

+ 18 - 2
scene/resources/texture.h

@@ -460,8 +460,10 @@ public:
 		FLAG_MIPMAPS = VisualServer::TEXTURE_FLAG_MIPMAPS,
 		FLAG_REPEAT = VisualServer::TEXTURE_FLAG_REPEAT,
 		FLAG_FILTER = VisualServer::TEXTURE_FLAG_FILTER,
+		FLAG_ANISOTROPIC_FILTER = VisualServer::TEXTURE_FLAG_ANISOTROPIC_FILTER,
 		FLAG_CONVERT_TO_LINEAR = VisualServer::TEXTURE_FLAG_CONVERT_TO_LINEAR,
-		FLAGS_DEFAULT = FLAG_FILTER,
+		FLAGS_DEFAULT_TEXTURE_ARRAY = FLAG_MIPMAPS | FLAG_REPEAT | FLAG_FILTER,
+		FLAGS_DEFAULT_TEXTURE_3D = FLAG_FILTER,
 	};
 
 	enum CompressMode {
@@ -501,7 +503,7 @@ public:
 	uint32_t get_height() const;
 	uint32_t get_depth() const;
 
-	void create(uint32_t p_width, uint32_t p_height, uint32_t p_depth, Image::Format p_format, uint32_t p_flags = FLAGS_DEFAULT);
+	void create(uint32_t p_width, uint32_t p_height, uint32_t p_depth, Image::Format p_format, uint32_t p_flags = FLAGS_DEFAULT_TEXTURE_ARRAY);
 	void set_layer_data(const Ref<Image> &p_image, int p_layer);
 	Ref<Image> get_layer_data(int p_layer) const;
 	void set_data_partial(const Ref<Image> &p_image, int p_x_ofs, int p_y_ofs, int p_z, int p_mipmap = 0);
@@ -518,7 +520,14 @@ VARIANT_ENUM_CAST(TextureLayered::Flags)
 class Texture3D : public TextureLayered {
 	GDCLASS(Texture3D, TextureLayered);
 
+protected:
+	static void _bind_methods();
+
 public:
+	void create(uint32_t p_width, uint32_t p_height, uint32_t p_depth, Image::Format p_format, uint32_t p_flags = FLAGS_DEFAULT_TEXTURE_3D) {
+		TextureLayered::create(p_width, p_height, p_depth, p_format, p_flags);
+	}
+
 	Texture3D() :
 			TextureLayered(true) {}
 };
@@ -526,7 +535,14 @@ public:
 class TextureArray : public TextureLayered {
 	GDCLASS(TextureArray, TextureLayered);
 
+protected:
+	static void _bind_methods();
+
 public:
+	void create(uint32_t p_width, uint32_t p_height, uint32_t p_depth, Image::Format p_format, uint32_t p_flags = FLAGS_DEFAULT_TEXTURE_ARRAY) {
+		TextureLayered::create(p_width, p_height, p_depth, p_format, p_flags);
+	}
+
 	TextureArray() :
 			TextureLayered(false) {}
 };