From fb609b22e4bb807db9688f36cea745577cd73d65 Mon Sep 17 00:00:00 2001
From: Cory Petkovsek <632766+tinmanjuggernaut@users.noreply.github.com>
Date: Mon, 9 Aug 2021 01:55:31 +0800
Subject: [PATCH] Add Anisotropic Filtering option for TextureArrays
---
doc/classes/Texture3D.xml | 12 +++++++++
doc/classes/TextureArray.xml | 11 ++++++++
doc/classes/TextureLayered.xml | 26 ++++++++-----------
.../resource_importer_layered_texture.cpp | 5 ++++
scene/resources/texture.cpp | 19 ++++++++++----
scene/resources/texture.h | 20 ++++++++++++--
6 files changed, 71 insertions(+), 22 deletions(-)
diff --git a/doc/classes/Texture3D.xml b/doc/classes/Texture3D.xml
index dd4141801821..4f53a189c5aa 100644
--- a/doc/classes/Texture3D.xml
+++ b/doc/classes/Texture3D.xml
@@ -9,9 +9,21 @@
+
+
+
+
+
+
+
+
+ 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.
+
+
+
diff --git a/doc/classes/TextureArray.xml b/doc/classes/TextureArray.xml
index 3312b8253ea0..b282d0bf40bb 100644
--- a/doc/classes/TextureArray.xml
+++ b/doc/classes/TextureArray.xml
@@ -21,6 +21,17 @@
+
+
+
+
+
+
+
+
+ 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.
+
+
diff --git a/doc/classes/TextureLayered.xml b/doc/classes/TextureLayered.xml
index 992965d34b36..2fc989cd9dc5 100644
--- a/doc/classes/TextureLayered.xml
+++ b/doc/classes/TextureLayered.xml
@@ -9,17 +9,6 @@
-
-
-
-
-
-
-
-
- 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.
-
-
@@ -72,14 +61,20 @@
-
+
Returns a dictionary with all the data used by this texture.
-
+
Specifies which [enum Flags] apply to this texture.
+
+ Default flags for [TextureArray]. [constant FLAG_MIPMAPS], [constant FLAG_REPEAT] and [constant FLAG_FILTER] are enabled.
+
+
+ Default flags for [Texture3D]. [constant FLAG_FILTER] is enabled.
+
Texture will generate mipmaps on creation.
@@ -89,8 +84,9 @@
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.
-
- Equivalent to [constant FLAG_FILTER].
+
+ 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.
diff --git a/editor/import/resource_importer_layered_texture.cpp b/editor/import/resource_importer_layered_texture.cpp
index b3a3dea3845b..24fb1d26976f 100644
--- a/editor/import/resource_importer_layered_texture.cpp
+++ b/editor/import/resource_importer_layered_texture.cpp
@@ -79,6 +79,7 @@ void ResourceImporterLayeredTexture::get_import_options(List *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;
}
diff --git a/scene/resources/texture.cpp b/scene/resources/texture.cpp
index 19eb28105e8a..f0a2da95318d 100644
--- a/scene/resources/texture.cpp
+++ b/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;
diff --git a/scene/resources/texture.h b/scene/resources/texture.h
index e0334e976d0d..53de7de8bd94 100644
--- a/scene/resources/texture.h
+++ b/scene/resources/texture.h
@@ -460,8 +460,10 @@ class TextureLayered : public Resource {
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 @@ class TextureLayered : public Resource {
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 &p_image, int p_layer);
Ref get_layer_data(int p_layer) const;
void set_data_partial(const Ref &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 @@ class Texture3D : public TextureLayered {
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) {}
};