diff --git a/doc/changelog.dox b/doc/changelog.dox index 5ebad732e..760bf2ada 100644 --- a/doc/changelog.dox +++ b/doc/changelog.dox @@ -82,7 +82,8 @@ See also: @ref Trade::PbrClearCoatMaterialData convenience accessor APIs similar to @ref Trade::PhongMaterialData. See [mosra/magnum#459](https://github.com/mosra/magnum/pull/459). - Added @ref Trade::PhongMaterialData::hasSpecularTexture(), - @ref Trade::PhongMaterialData::specularTextureSwizzle() and + @ref Trade::PhongMaterialData::specularTextureSwizzle(), + @ref Trade::PhongMaterialData::normalTextureScale() and @ref Trade::PhongMaterialData::normalTextureSwizzle() to make new features added for PBR materials recognizable also in classic Phong workflows. diff --git a/src/Magnum/Trade/Implementation/materialAttributeProperties.hpp b/src/Magnum/Trade/Implementation/materialAttributeProperties.hpp index 2b81b7725..9e42b5725 100644 --- a/src/Magnum/Trade/Implementation/materialAttributeProperties.hpp +++ b/src/Magnum/Trade/Implementation/materialAttributeProperties.hpp @@ -65,6 +65,7 @@ _c(GlossinessTextureMatrix,Matrix3x3) _c(GlossinessTextureCoordinates,UnsignedInt) _c(SpecularGlossinessTexture,UnsignedInt) _c(NormalTexture,UnsignedInt) +_c(NormalTextureScale,Float) _ct(NormalTextureSwizzle,TextureSwizzle,MaterialTextureSwizzle) _c(NormalTextureMatrix,Matrix3x3) _c(NormalTextureCoordinates,UnsignedInt) diff --git a/src/Magnum/Trade/MaterialData.h b/src/Magnum/Trade/MaterialData.h index 990cae23e..1928e31f1 100644 --- a/src/Magnum/Trade/MaterialData.h +++ b/src/Magnum/Trade/MaterialData.h @@ -598,6 +598,9 @@ enum class MaterialAttribute: UnsignedInt { /** * Tangent-space normal map texture index, * @ref MaterialAttributeType::UnsignedInt. + * + * If @ref MaterialAttribute::NormalTextureScale is present as well, these + * two are multiplied together. * @see @ref PhongMaterialData::normalTexture(), * @ref PbrMetallicRoughnessMaterialData::hasNormalRoughnessMetallicTexture(), * @ref PbrMetallicRoughnessMaterialData::normalTexture(), @@ -605,6 +608,17 @@ enum class MaterialAttribute: UnsignedInt { */ NormalTexture, + /** + * Normal texture scale, @ref MaterialAttributeType::Float. + * + * Scales the texture defined by @ref MaterialAttribute::NormalTexture. + * @see @ref PhongMaterialData::normalTextureScale(), + * @ref PbrMetallicRoughnessMaterialData::normalTextureScale(), + * @ref PbrSpecularGlossinessMaterialData::normalTextureScale(), + * @ref PbrClearCoatMaterialData::normalTextureScale() + */ + NormalTextureScale, + /** * Normal texture swizzle, @ref MaterialAttributeType::TextureSwizzle. * diff --git a/src/Magnum/Trade/PbrClearCoatMaterialData.cpp b/src/Magnum/Trade/PbrClearCoatMaterialData.cpp index 0ff45bbd3..ec9a6bf09 100644 --- a/src/Magnum/Trade/PbrClearCoatMaterialData.cpp +++ b/src/Magnum/Trade/PbrClearCoatMaterialData.cpp @@ -81,6 +81,12 @@ UnsignedInt PbrClearCoatMaterialData::normalTexture() const { return attribute(MaterialAttribute::NormalTexture); } +Float PbrClearCoatMaterialData::normalTextureScale() const { + CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), + "Trade::PbrClearCoatMaterialData::normalTextureScale(): the layer doesn't have a normal texture", {}); + return attributeOr(MaterialAttribute::NormalTextureScale, 1.0f); +} + MaterialTextureSwizzle PbrClearCoatMaterialData::normalTextureSwizzle() const { CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), "Trade::PbrClearCoatMaterialData::normalTextureSwizzle(): the layer doesn't have a normal texture", {}); diff --git a/src/Magnum/Trade/PbrClearCoatMaterialData.h b/src/Magnum/Trade/PbrClearCoatMaterialData.h index 0a43f179f..454d27488 100644 --- a/src/Magnum/Trade/PbrClearCoatMaterialData.h +++ b/src/Magnum/Trade/PbrClearCoatMaterialData.h @@ -148,6 +148,16 @@ class MAGNUM_TRADE_EXPORT PbrClearCoatMaterialData: public MaterialLayerData(MaterialAttribute::NormalTexture); } +Float PbrMetallicRoughnessMaterialData::normalTextureScale() const { + CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), + "Trade::PbrMetallicRoughnessMaterialData::normalTextureScale(): the material doesn't have a normal texture", {}); + return attributeOr(MaterialAttribute::NormalTextureScale, 1.0f); +} + MaterialTextureSwizzle PbrMetallicRoughnessMaterialData::normalTextureSwizzle() const { CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), "Trade::PbrMetallicRoughnessMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture", {}); diff --git a/src/Magnum/Trade/PbrMetallicRoughnessMaterialData.h b/src/Magnum/Trade/PbrMetallicRoughnessMaterialData.h index 3e271a08a..def41bfaf 100644 --- a/src/Magnum/Trade/PbrMetallicRoughnessMaterialData.h +++ b/src/Magnum/Trade/PbrMetallicRoughnessMaterialData.h @@ -401,6 +401,16 @@ class MAGNUM_TRADE_EXPORT PbrMetallicRoughnessMaterialData: public MaterialData */ UnsignedInt normalTexture() const; + /** + * @brief Normal texture scale + * + * Convenience access to the @ref MaterialAttribute::NormalTextureScale + * attribute. If not present, the default is @cpp 1.0f @ce. + * Available only if @ref MaterialAttribute::NormalTexture is present. + * @see @ref hasAttribute() + */ + Float normalTextureScale() const; + /** * @brief Normal texture coordinate transformation matrix * diff --git a/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.cpp b/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.cpp index 16a6e608e..238b01843 100644 --- a/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.cpp +++ b/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.cpp @@ -176,6 +176,12 @@ UnsignedInt PbrSpecularGlossinessMaterialData::normalTexture() const { return attribute(MaterialAttribute::NormalTexture); } +Float PbrSpecularGlossinessMaterialData::normalTextureScale() const { + CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), + "Trade::PbrSpecularGlossinessMaterialData::normalTextureScale(): the material doesn't have a normal texture", {}); + return attributeOr(MaterialAttribute::NormalTextureScale, 1.0f); +} + MaterialTextureSwizzle PbrSpecularGlossinessMaterialData::normalTextureSwizzle() const { CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), "Trade::PbrSpecularGlossinessMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture", {}); diff --git a/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.h b/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.h index edc5c4bad..dd21276a4 100644 --- a/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.h +++ b/src/Magnum/Trade/PbrSpecularGlossinessMaterialData.h @@ -296,6 +296,16 @@ class MAGNUM_TRADE_EXPORT PbrSpecularGlossinessMaterialData: public MaterialData */ UnsignedInt normalTexture() const; + /** + * @brief Normal texture scale + * + * Convenience access to the @ref MaterialAttribute::NormalTextureScale + * attribute. If not present, the default is @cpp 1.0f @ce. + * Available only if @ref MaterialAttribute::NormalTexture is present. + * @see @ref hasAttribute() + */ + Float normalTextureScale() const; + /** * @brief Normal texture swizzle * diff --git a/src/Magnum/Trade/PhongMaterialData.cpp b/src/Magnum/Trade/PhongMaterialData.cpp index 4f1dc3d5c..8e8a5f929 100644 --- a/src/Magnum/Trade/PhongMaterialData.cpp +++ b/src/Magnum/Trade/PhongMaterialData.cpp @@ -241,6 +241,12 @@ UnsignedInt PhongMaterialData::normalTexture() const { return attribute(MaterialAttribute::NormalTexture); } +Float PhongMaterialData::normalTextureScale() const { + CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), + "Trade::PhongMaterialData::normalTextureScale(): the material doesn't have a normal texture", {}); + return attributeOr(MaterialAttribute::NormalTextureScale, 1.0f); +} + MaterialTextureSwizzle PhongMaterialData::normalTextureSwizzle() const { CORRADE_ASSERT(hasAttribute(MaterialAttribute::NormalTexture), "Trade::PhongMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture", {}); diff --git a/src/Magnum/Trade/PhongMaterialData.h b/src/Magnum/Trade/PhongMaterialData.h index fe24f7530..695f6daa0 100644 --- a/src/Magnum/Trade/PhongMaterialData.h +++ b/src/Magnum/Trade/PhongMaterialData.h @@ -480,6 +480,17 @@ class MAGNUM_TRADE_EXPORT PhongMaterialData: public MaterialData { */ UnsignedInt normalTexture() const; + /** + * @brief Normal texture scale + * @m_since_latest + * + * Convenience access to the @ref MaterialAttribute::NormalTextureScale + * attribute. If not present, the default is @cpp 1.0f @ce. + * Available only if @ref MaterialAttribute::NormalTexture is present. + * @see @ref hasAttribute() + */ + Float normalTextureScale() const; + /** * @brief Normal texture swizzle * @m_since_latest diff --git a/src/Magnum/Trade/Test/MaterialDataTest.cpp b/src/Magnum/Trade/Test/MaterialDataTest.cpp index 3a50546b4..2dff7a542 100644 --- a/src/Magnum/Trade/Test/MaterialDataTest.cpp +++ b/src/Magnum/Trade/Test/MaterialDataTest.cpp @@ -2731,6 +2731,7 @@ void MaterialDataTest::pbrMetallicRoughnessAccessTextured() { {MaterialAttribute::RoughnessTextureMatrix, Matrix3::scaling({1.0f, 1.0f})}, {MaterialAttribute::RoughnessTextureCoordinates, 4u}, {MaterialAttribute::NormalTexture, 3u}, + {MaterialAttribute::NormalTextureScale, 0.35f}, {MaterialAttribute::NormalTextureSwizzle, MaterialTextureSwizzle::BA}, {MaterialAttribute::NormalTextureMatrix, Matrix3::scaling({1.0f, 0.5f})}, {MaterialAttribute::NormalTextureCoordinates, 5u}, @@ -2767,6 +2768,7 @@ void MaterialDataTest::pbrMetallicRoughnessAccessTextured() { CORRADE_COMPARE(data.roughnessTextureMatrix(), Matrix3::scaling({1.0f, 1.0f})); CORRADE_COMPARE(data.roughnessTextureCoordinates(), 4); CORRADE_COMPARE(data.normalTexture(), 3); + CORRADE_COMPARE(data.normalTextureScale(), 0.35f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::BA); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3::scaling({1.0f, 0.5f})); CORRADE_COMPARE(data.normalTextureCoordinates(), 5); @@ -2816,6 +2818,7 @@ void MaterialDataTest::pbrMetallicRoughnessAccessTexturedDefaults() { CORRADE_COMPARE(data.roughnessTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.roughnessTextureCoordinates(), 0); CORRADE_COMPARE(data.normalTexture(), 4); + CORRADE_COMPARE(data.normalTextureScale(), 1.0f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::RGB); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.normalTextureCoordinates(), 0); @@ -3246,6 +3249,7 @@ void MaterialDataTest::pbrMetallicRoughnessAccessInvalidTextures() { data.roughnessTextureMatrix(); data.roughnessTextureCoordinates(); data.normalTexture(); + data.normalTextureScale(); data.normalTextureSwizzle(); data.normalTextureMatrix(); data.normalTextureCoordinates(); @@ -3269,6 +3273,7 @@ void MaterialDataTest::pbrMetallicRoughnessAccessInvalidTextures() { "Trade::PbrMetallicRoughnessMaterialData::roughnessTextureMatrix(): the material doesn't have a roughness texture\n" "Trade::PbrMetallicRoughnessMaterialData::roughnessTextureCoordinates(): the material doesn't have a roughness texture\n" "Trade::MaterialData::attribute(): attribute NormalTexture not found in layer 0\n" + "Trade::PbrMetallicRoughnessMaterialData::normalTextureScale(): the material doesn't have a normal texture\n" "Trade::PbrMetallicRoughnessMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture\n" "Trade::PbrMetallicRoughnessMaterialData::normalTextureMatrix(): the material doesn't have a normal texture\n" "Trade::PbrMetallicRoughnessMaterialData::normalTextureCoordinates(): the material doesn't have a normal texture\n" @@ -3336,6 +3341,7 @@ void MaterialDataTest::pbrSpecularGlossinessAccessTextured() { {MaterialAttribute::GlossinessTextureMatrix, Matrix3::scaling({1.0f, 1.0f})}, {MaterialAttribute::GlossinessTextureCoordinates, 4u}, {MaterialAttribute::NormalTexture, 3u}, + {MaterialAttribute::NormalTextureScale, 0.35f}, {MaterialAttribute::NormalTextureSwizzle, MaterialTextureSwizzle::BA}, {MaterialAttribute::NormalTextureMatrix, Matrix3::scaling({1.0f, 0.5f})}, {MaterialAttribute::NormalTextureCoordinates, 5u}, @@ -3369,6 +3375,7 @@ void MaterialDataTest::pbrSpecularGlossinessAccessTextured() { CORRADE_COMPARE(data.glossinessTextureMatrix(), Matrix3::scaling({1.0f, 1.0f})); CORRADE_COMPARE(data.glossinessTextureCoordinates(), 4); CORRADE_COMPARE(data.normalTexture(), 3); + CORRADE_COMPARE(data.normalTextureScale(), 0.35f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::BA); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3::scaling({1.0f, 0.5f})); CORRADE_COMPARE(data.normalTextureCoordinates(), 5); @@ -3415,6 +3422,7 @@ void MaterialDataTest::pbrSpecularGlossinessAccessTexturedDefaults() { CORRADE_COMPARE(data.glossinessTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.glossinessTextureCoordinates(), 0); CORRADE_COMPARE(data.normalTexture(), 4); + CORRADE_COMPARE(data.normalTextureScale(), 1.0f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::RGB); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.normalTextureCoordinates(), 0); @@ -3628,6 +3636,7 @@ void MaterialDataTest::pbrSpecularGlossinessAccessInvalidTextures() { data.glossinessTextureMatrix(); data.glossinessTextureCoordinates(); data.normalTexture(); + data.normalTextureScale(); data.normalTextureSwizzle(); data.normalTextureMatrix(); data.normalTextureCoordinates(); @@ -3651,6 +3660,7 @@ void MaterialDataTest::pbrSpecularGlossinessAccessInvalidTextures() { "Trade::PbrSpecularGlossinessMaterialData::glossinessTextureMatrix(): the material doesn't have a glossiness texture\n" "Trade::PbrSpecularGlossinessMaterialData::glossinessTextureCoordinates(): the material doesn't have a glossiness texture\n" "Trade::MaterialData::attribute(): attribute NormalTexture not found in layer 0\n" + "Trade::PbrSpecularGlossinessMaterialData::normalTextureScale(): the material doesn't have a normal texture\n" "Trade::PbrSpecularGlossinessMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture\n" "Trade::PbrSpecularGlossinessMaterialData::normalTextureMatrix(): the material doesn't have a normal texture\n" "Trade::PbrSpecularGlossinessMaterialData::normalTextureCoordinates(): the material doesn't have a normal texture\n" @@ -3716,6 +3726,7 @@ void MaterialDataTest::phongAccessTextured() { {MaterialAttribute::SpecularTextureMatrix, Matrix3::scaling({1.0f, 1.0f})}, {MaterialAttribute::SpecularTextureCoordinates, 4u}, {MaterialAttribute::NormalTexture, 0u}, + {MaterialAttribute::NormalTextureScale, 0.5f}, {MaterialAttribute::NormalTextureSwizzle, MaterialTextureSwizzle::GB}, {MaterialAttribute::NormalTextureMatrix, Matrix3::scaling({1.0f, 0.5f})}, {MaterialAttribute::NormalTextureCoordinates, 5u} @@ -3738,6 +3749,7 @@ void MaterialDataTest::phongAccessTextured() { CORRADE_COMPARE(data.specularTextureMatrix(), Matrix3::scaling({1.0f, 1.0f})); CORRADE_COMPARE(data.specularTextureCoordinates(), 4); CORRADE_COMPARE(data.normalTexture(), 0); + CORRADE_COMPARE(data.normalTextureScale(), 0.5f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::GB); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3::scaling({1.0f, 0.5f})); CORRADE_COMPARE(data.normalTextureCoordinates(), 5); @@ -3771,6 +3783,7 @@ void MaterialDataTest::phongAccessTexturedDefaults() { CORRADE_COMPARE(data.specularTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.specularTextureCoordinates(), 0); CORRADE_COMPARE(data.normalTexture(), 1); + CORRADE_COMPARE(data.normalTextureScale(), 1.0f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::RGB); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.normalTextureCoordinates(), 0); @@ -3847,6 +3860,7 @@ void MaterialDataTest::phongAccessInvalidTextures() { data.specularTextureMatrix(); data.specularTextureCoordinates(); data.normalTexture(); + data.normalTextureScale(); data.normalTextureSwizzle(); data.normalTextureMatrix(); data.normalTextureCoordinates(); @@ -3862,6 +3876,7 @@ void MaterialDataTest::phongAccessInvalidTextures() { "Trade::PhongMaterialData::specularTextureMatrix(): the material doesn't have a specular texture\n" "Trade::PhongMaterialData::specularTextureCoordinates(): the material doesn't have a specular texture\n" "Trade::MaterialData::attribute(): attribute NormalTexture not found in layer 0\n" + "Trade::PhongMaterialData::normalTextureScale(): the material doesn't have a normal texture\n" "Trade::PhongMaterialData::normalTextureSwizzle(): the material doesn't have a normal texture\n" "Trade::PhongMaterialData::normalTextureMatrix(): the material doesn't have a normal texture\n" "Trade::PhongMaterialData::normalTextureCoordinates(): the material doesn't have a normal texture\n"); @@ -4157,10 +4172,11 @@ void MaterialDataTest::pbrClearCoatAccessTextured() { {MaterialAttribute::RoughnessTextureMatrix, Matrix3::translation({2.0f, 1.5f})}, {MaterialAttribute::RoughnessTextureCoordinates, 6u}, {MaterialAttribute::NormalTexture, 3u}, + {MaterialAttribute::NormalTextureScale, 0.5f}, {MaterialAttribute::NormalTextureSwizzle, MaterialTextureSwizzle::B}, {MaterialAttribute::NormalTextureMatrix, Matrix3::translation({0.0f, 0.5f})}, {MaterialAttribute::NormalTextureCoordinates, 7u}, - }, {0, 10}}; + }, {0, 11}}; CORRADE_VERIFY(data.hasTextureTransformation()); CORRADE_VERIFY(data.hasTextureCoordinates()); @@ -4170,6 +4186,7 @@ void MaterialDataTest::pbrClearCoatAccessTextured() { CORRADE_COMPARE(data.roughnessTextureMatrix(), Matrix3::translation({2.0f, 1.5f})); CORRADE_COMPARE(data.roughnessTextureCoordinates(), 6u); CORRADE_COMPARE(data.normalTexture(), 3u); + CORRADE_COMPARE(data.normalTextureScale(), 0.5f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::B); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3::translation({0.0f, 0.5f})); CORRADE_COMPARE(data.normalTextureCoordinates(), 7u); @@ -4190,6 +4207,7 @@ void MaterialDataTest::pbrClearCoatAccessTexturedDefaults() { CORRADE_COMPARE(data.roughnessTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.roughnessTextureCoordinates(), 0u); CORRADE_COMPARE(data.normalTexture(), 3u); + CORRADE_COMPARE(data.normalTextureScale(), 1.0f); CORRADE_COMPARE(data.normalTextureSwizzle(), MaterialTextureSwizzle::RGB); CORRADE_COMPARE(data.normalTextureMatrix(), Matrix3{}); CORRADE_COMPARE(data.normalTextureCoordinates(), 0u); @@ -4246,6 +4264,7 @@ void MaterialDataTest::pbrClearCoatAccessInvalidTextures() { data.roughnessTextureMatrix(); data.roughnessTextureCoordinates(); data.normalTexture(); + data.normalTextureScale(); data.normalTextureSwizzle(); data.normalTextureMatrix(); data.normalTextureCoordinates(); @@ -4255,6 +4274,7 @@ void MaterialDataTest::pbrClearCoatAccessInvalidTextures() { "Trade::PbrClearCoatMaterialData::roughnessTextureMatrix(): the layer doesn't have a roughness texture\n" "Trade::PbrClearCoatMaterialData::roughnessTextureCoordinates(): the layer doesn't have a roughness texture\n" "Trade::MaterialData::attribute(): attribute NormalTexture not found in layer ClearCoat\n" + "Trade::PbrClearCoatMaterialData::normalTextureScale(): the layer doesn't have a normal texture\n" "Trade::PbrClearCoatMaterialData::normalTextureSwizzle(): the layer doesn't have a normal texture\n" "Trade::PbrClearCoatMaterialData::normalTextureMatrix(): the layer doesn't have a normal texture\n" "Trade::PbrClearCoatMaterialData::normalTextureCoordinates(): the layer doesn't have a normal texture\n");