From aaf11c44251e53504e13da8b4192deb01b5b18b9 Mon Sep 17 00:00:00 2001 From: codereader Date: Mon, 28 Feb 2022 04:49:24 +0100 Subject: [PATCH] #5846: Fix texture being messed up by 90 degree rotations of brushes. Freezetransform is triggering a second evaluation of the current transformation (which is identity) - this was messing up the texDefTransformed() algorithm since the winding vertices were still at the old position. The face normal ended up being parallel to the face plane. The quick solution here is to ignore identity transforms in Face::transform. --- radiantcore/brush/BrushNode.cpp | 9 +++++++-- test/TextureManipulation.cpp | 17 +++++++++++++++-- 2 files changed, 22 insertions(+), 4 deletions(-) diff --git a/radiantcore/brush/BrushNode.cpp b/radiantcore/brush/BrushNode.cpp index de7c677c15..9c40ed6cfc 100644 --- a/radiantcore/brush/BrushNode.cpp +++ b/radiantcore/brush/BrushNode.cpp @@ -486,7 +486,12 @@ void BrushNode::evaluateTransform() } else { - m_brush.transform(calculateTransform()); + auto transform = calculateTransform(); + + if (transform != Matrix4::getIdentity()) + { + m_brush.transform(transform); + } } } else @@ -562,7 +567,7 @@ void BrushNode::onPostRedo() void BrushNode::_onTransformationChanged() { - m_brush.transformChanged(); + m_brush.transformChanged(); _renderableVertices.queueUpdate(); _renderableComponentsNeedUpdate = true; diff --git a/test/TextureManipulation.cpp b/test/TextureManipulation.cpp index 88e35595c2..9a499d09d1 100644 --- a/test/TextureManipulation.cpp +++ b/test/TextureManipulation.cpp @@ -1,5 +1,6 @@ #include "RadiantTest.h" +#include #include "itransformable.h" #include "ishaders.h" #include "ishaderclipboard.h" @@ -829,14 +830,26 @@ TEST_F(TextureManipulationTest, RotateFuncStaticBrush90) auto& faceAfter = *algorithm::findBrushFaceWithNormal(brush, { 1, 0, 0 }); + std::optional distance; auto old = oldVertices.begin(); for (const auto& vertex : faceAfter.getWinding()) { // Assume the 3D coordinates have changed EXPECT_FALSE(math::isNear(vertex.vertex, old->vertex, 0.01)); - // The texture coordinates should remain unchanged (due to texture lock) - EXPECT_TRUE(math::isNear(vertex.texcoord, old->texcoord, 0.01)); + // The texture coordinates should remain equivalent (due to texture lock) + // The absolute coordinates in UV space might be off by some integer number + // We expect the distance to the previous coordinates to be the same + if (distance.has_value()) + { + EXPECT_TRUE(math::isNear(distance.value(), vertex.texcoord - old->texcoord, 0.01)); + } + else + { + distance = vertex.texcoord - old->texcoord; + } + + ++old; } }