From e15fad72ed2b0e7a374e185d08b8399ad2f7c1a5 Mon Sep 17 00:00:00 2001 From: Bruno Van de Velde Date: Sat, 21 Sep 2024 16:43:38 +0200 Subject: [PATCH] Setting and getting view of CanvasSFML was broken once the canvas size was reduced (because the render texture would have a larger size than the canvas) --- changelog.md | 2 + .../Renderer/SFML-Graphics/CanvasSFML.hpp | 3 +- .../Renderer/SFML-Graphics/CanvasSFML.cpp | 48 ++++++++++++++++--- tests/Widgets/Canvas.cpp | 4 +- 4 files changed, 48 insertions(+), 9 deletions(-) diff --git a/changelog.md b/changelog.md index 9f185cdf7..de5938765 100644 --- a/changelog.md +++ b/changelog.md @@ -5,6 +5,8 @@ TGUI 1.6 (TBD) - Added addMultipleItems to ListBox and ComboBox - Added getItemByIndex, getIndexById and getIdByIndex to ComboBox - Fixed crash on exit when tool tip was visible +- Fixed wrong arrow sizes for horizontal spin button +- Fixed view not being usable in CanvasSFML TGUI 1.5 (25 August 2024) diff --git a/include/TGUI/Backend/Renderer/SFML-Graphics/CanvasSFML.hpp b/include/TGUI/Backend/Renderer/SFML-Graphics/CanvasSFML.hpp index b01c157a8..c46a1dd44 100644 --- a/include/TGUI/Backend/Renderer/SFML-Graphics/CanvasSFML.hpp +++ b/include/TGUI/Backend/Renderer/SFML-Graphics/CanvasSFML.hpp @@ -158,7 +158,7 @@ TGUI_MODULE_EXPORT namespace tgui /// /// @return The default view of the canvas ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// - TGUI_NODISCARD const sf::View& getDefaultView() const; + TGUI_NODISCARD sf::View getDefaultView() const; ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /// @brief Get the viewport of the currently applied view, applied to this canvas @@ -247,6 +247,7 @@ TGUI_MODULE_EXPORT namespace tgui ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// protected: + sf::View m_view; sf::RenderTexture m_renderTexture; Vector2u m_usedTextureSize; }; diff --git a/src/Backend/Renderer/SFML-Graphics/CanvasSFML.cpp b/src/Backend/Renderer/SFML-Graphics/CanvasSFML.cpp index 641468341..a027659ba 100644 --- a/src/Backend/Renderer/SFML-Graphics/CanvasSFML.cpp +++ b/src/Backend/Renderer/SFML-Graphics/CanvasSFML.cpp @@ -41,14 +41,16 @@ namespace tgui ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// CanvasSFML::CanvasSFML(const char* typeName, bool initRenderer) : - CanvasBase{typeName, initRenderer} + CanvasBase{typeName, initRenderer}, + m_view{{{}, {1, 1}}} { } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// CanvasSFML::CanvasSFML(const CanvasSFML& other) : - CanvasBase{other} + CanvasBase{other}, + m_view {other.m_view} { setSize(other.getSize()); } @@ -57,6 +59,7 @@ namespace tgui CanvasSFML::CanvasSFML(CanvasSFML&& other) noexcept : CanvasBase{std::move(other)}, + m_view {std::move(other.m_view)}, #if SFML_VERSION_MAJOR >= 3 m_renderTexture{std::move(other.m_renderTexture)}, #endif @@ -74,6 +77,7 @@ namespace tgui if (this != &right) { ClickableWidget::operator=(right); + m_view = right.m_view; m_usedTextureSize = right.m_usedTextureSize; setSize(right.getSize()); } @@ -87,11 +91,16 @@ namespace tgui { if (this != &right) { - m_usedTextureSize = std::move(right.m_usedTextureSize); ClickableWidget::operator=(std::move(right)); + m_view = std::move(right.m_view); + m_usedTextureSize = std::move(right.m_usedTextureSize); +#if SFML_VERSION_MAJOR >= 3 + m_renderTexture = std::move(right.m_renderTexture); +#else // sf::RenderTexture does not support move yet setSize(getSize()); +#endif } return *this; @@ -137,27 +146,52 @@ namespace tgui m_usedTextureSize = newTextureSize; } + + setView(getDefaultView()); } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void CanvasSFML::setView(const sf::View& view) { - m_renderTexture.setView(view); + m_view = view; + + // The render texture might be larger than the canvas + sf::FloatRect viewport = view.getViewport(); + if ((m_renderTexture.getSize().x > 0) && (m_renderTexture.getSize().y > 0)) + { + const float scaleX = static_cast(m_usedTextureSize.x) / static_cast(m_renderTexture.getSize().x); + const float scaleY = static_cast(m_usedTextureSize.y) / static_cast(m_renderTexture.getSize().y); +#if SFML_VERSION_MAJOR >= 3 + viewport.position.x *= scaleX; + viewport.position.y *= scaleY; + viewport.size.x *= scaleX; + viewport.size.y *= scaleY; +#else + viewport.left *= scaleX; + viewport.top *= scaleY; + viewport.width *= scaleX; + viewport.height *= scaleY; +#endif + } + + sf::View internalView = view; + internalView.setViewport(viewport); + m_renderTexture.setView(internalView); } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// const sf::View& CanvasSFML::getView() const { - return m_renderTexture.getView(); + return m_view; } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// - const sf::View& CanvasSFML::getDefaultView() const + sf::View CanvasSFML::getDefaultView() const { - return m_renderTexture.getDefaultView(); + return sf::View{{{}, {static_cast(m_usedTextureSize.x), static_cast(m_usedTextureSize.y)}}}; } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// diff --git a/tests/Widgets/Canvas.cpp b/tests/Widgets/Canvas.cpp index 56a99c23e..fada6c78d 100644 --- a/tests/Widgets/Canvas.cpp +++ b/tests/Widgets/Canvas.cpp @@ -114,7 +114,9 @@ TEST_CASE("[CanvasSFML]") SECTION("view") { - canvas = tgui::CanvasSFML::create({200, 100}); + canvas = tgui::CanvasSFML::create({300, 200}); + canvas->setSize({50, 30}); + canvas->setSize({200, 100}); REQUIRE(canvas->getView() == sf::View(sf::FloatRect{{0, 0}, {200, 100}})); REQUIRE(canvas->getDefaultView() == sf::View(sf::FloatRect{{0, 0}, {200, 100}}));