From f9d6d70985b34fd570538ef79e2fccba879d4924 Mon Sep 17 00:00:00 2001 From: Petr Ohlidal Date: Mon, 2 Oct 2023 23:52:11 +0200 Subject: [PATCH] SurveyMap now zooms to static texture Changes: * Texture "MapRttTex-#" is now short-lived, after creating the map image it's exported as static image and destroyed * Map texture size is now hardcoded to 4096x4096 (the maximum value guaranteed to be portable) NOTE: even at this resolution and with small terrain like Auriga, the fully zoomed map doesn't look spectacular. * Minor fix: The minimap now resets zoom and display mode when loading new terrain. --- source/main/gfx/SurveyMapTextureCreator.cpp | 9 +++++ source/main/gfx/SurveyMapTextureCreator.h | 3 +- source/main/gui/panels/GUI_SurveyMap.cpp | 44 +++++++++++---------- source/main/gui/panels/GUI_SurveyMap.h | 10 ++--- 4 files changed, 36 insertions(+), 30 deletions(-) diff --git a/source/main/gfx/SurveyMapTextureCreator.cpp b/source/main/gfx/SurveyMapTextureCreator.cpp index 390cfcec0b..50f3ab2f2d 100644 --- a/source/main/gfx/SurveyMapTextureCreator.cpp +++ b/source/main/gfx/SurveyMapTextureCreator.cpp @@ -43,6 +43,8 @@ SurveyMapTextureCreator::SurveyMapTextureCreator(Ogre::Real terrain_height) : SurveyMapTextureCreator::~SurveyMapTextureCreator() { + if (mRttTex) + mRttTex->removeAllViewports(); if (mCamera) App::GetGfxScene()->GetSceneManager()->destroyCamera(mCamera); if (mTexture) @@ -114,3 +116,10 @@ void SurveyMapTextureCreator::postRenderTargetUpdate(const RenderTargetEvent &ev water->UpdateWater(); } } + +Ogre::TexturePtr SurveyMapTextureCreator::convertTextureToStatic(const std::string& texName, const std::string& rgName) +{ + Ogre::Image img; + mTexture->convertToImage(img); + return Ogre::TextureManager::getSingleton().loadImage(texName, rgName, img); +} diff --git a/source/main/gfx/SurveyMapTextureCreator.h b/source/main/gfx/SurveyMapTextureCreator.h index 4733d49721..d5b6ce3fcb 100644 --- a/source/main/gfx/SurveyMapTextureCreator.h +++ b/source/main/gfx/SurveyMapTextureCreator.h @@ -34,8 +34,7 @@ class SurveyMapTextureCreator : public Ogre::RenderTargetListener bool init(int res, int fsaa); void update(Ogre::Vector2 center, Ogre::Vector2 size); - - Ogre::TexturePtr GetTexture() const { return mTexture; } + Ogre::TexturePtr convertTextureToStatic(const std::string& texName, const std::string& rgName); protected: diff --git a/source/main/gui/panels/GUI_SurveyMap.cpp b/source/main/gui/panels/GUI_SurveyMap.cpp index 9af3b23aa2..52b7033dd5 100644 --- a/source/main/gui/panels/GUI_SurveyMap.cpp +++ b/source/main/gui/panels/GUI_SurveyMap.cpp @@ -2,7 +2,7 @@ This source file is part of Rigs of Rods Copyright 2005-2012 Pierre-Michel Ricordel Copyright 2007-2020 Thomas Fischer - Copyright 2013-2020 Petr Ohlidal + Copyright 2013-2023 Petr Ohlidal For more information, see http://www.rigsofrods.org/ @@ -124,13 +124,13 @@ void SurveyMap::Draw() // Draw map texture ImVec2 tl_screen_pos = ImGui::GetCursorScreenPos(); - Ogre::TexturePtr tex; Ogre::Vector2 smallmap_center; Ogre::Vector2 smallmap_size; Ogre::Vector2 view_origin; + Ogre::Vector2 texcoords_top_left(0,0); + Ogre::Vector2 texcoords_bottom_right(1,1); if (mMapMode == SurveyMapMode::BIG) { - tex = mMapTextureCreatorStatic->GetTexture(); view_origin = mMapCenterOffset; } else if (mMapMode == SurveyMapMode::SMALL) @@ -155,12 +155,8 @@ void SurveyMap::Draw() view_origin = ((smallmap_center + mMapCenterOffset) - smallmap_size / 2); - // Update texture - if (mMapZoom != 0.0f) - { - mMapTextureCreatorDynamic->update(smallmap_center + mMapCenterOffset, smallmap_size); - } - tex = mMapTextureCreatorDynamic->GetTexture(); + texcoords_top_left = (smallmap_center - (smallmap_size/2)) / mTerrainSize; + texcoords_bottom_right = (smallmap_center + (smallmap_size/2)) / mTerrainSize; } bool w_adj = false; @@ -175,10 +171,12 @@ void SurveyMap::Draw() } } } - + //ImGui::Text("DBG uv0=%5.3f %5.3f, uv1=%5.3f %5.3f", texcoords_top_left.x, texcoords_top_left.y, texcoords_bottom_right.x, texcoords_bottom_right.y); ImGui::BeginChild("map", ImVec2(0.f, view_size.y), false); + ImGui::Image(reinterpret_cast(mMapTexture->getHandle()), view_size, + ImVec2(texcoords_top_left.x, texcoords_top_left.y), + ImVec2(texcoords_bottom_right.x, texcoords_bottom_right.y)); - ImGui::Image(reinterpret_cast(tex->getHandle()), view_size); if (ImGui::IsItemClicked(0) || ImGui::IsItemClicked(1)) // 0 = left click, 1 = right click { ImVec2 mouse_view_offset = (ImGui::GetMousePos() - tl_screen_pos) / view_size; @@ -377,6 +375,15 @@ void SurveyMap::Draw() void SurveyMap::CreateTerrainTextures() { mMapCenterOffset = Ogre::Vector2::ZERO; // Reset, maybe new terrain was loaded + if (mMapTexture) + { + Ogre::TextureManager::getSingleton().unload(mMapTexture->getName(), mMapTexture->getGroup()); + Ogre::TextureManager::getSingleton().remove(mMapTexture->getName(), mMapTexture->getGroup()); + mMapTexture.setNull(); + } + mMapZoom = 0.f; + mMapMode = SurveyMapMode::NONE; + AxisAlignedBox aab = App::GetGameContext()->GetTerrain()->getTerrainCollisionAAB(); Vector3 terrain_size = App::GetGameContext()->GetTerrain()->getMaxTerrainSize(); bool use_aab = App::GetGameContext()->GetTerrain()->isFlat() && std::min(aab.getSize().x, aab.getSize().z) > 50.0f; @@ -393,18 +400,13 @@ void SurveyMap::CreateTerrainTextures() Ogre::Vector2 mMapCenter = mTerrainSize / 2; ConfigOptionMap ropts = App::GetAppContext()->GetOgreRoot()->getRenderSystem()->getConfigOptions(); - int resolution = StringConverter::parseInt(StringUtil::split(ropts["Video Mode"].currentValue, " x ")[0], 1024); int fsaa = StringConverter::parseInt(ropts["FSAA"].currentValue, 0); - int res = std::pow(2, std::floor(std::log2(resolution))); - - mMapTextureCreatorStatic = std::unique_ptr(new SurveyMapTextureCreator(terrain_size.y)); - mMapTextureCreatorStatic->init(res / 1.5, fsaa); - mMapTextureCreatorStatic->update(mMapCenter + mMapCenterOffset, mTerrainSize); - // TODO: Find out how to zoom into the static texture instead - mMapTextureCreatorDynamic = std::unique_ptr(new SurveyMapTextureCreator(terrain_size.y)); - mMapTextureCreatorDynamic->init(res / 4, fsaa); - mMapTextureCreatorDynamic->update(mMapCenter + mMapCenterOffset, mTerrainSize); + SurveyMapTextureCreator texCreatorStatic(terrain_size.y); + texCreatorStatic.init(4096, fsaa); + texCreatorStatic.update(mMapCenter + mMapCenterOffset, mTerrainSize); + mMapTexture = texCreatorStatic.convertTextureToStatic( + "SurveyMapStatic", App::GetGameContext()->GetTerrain()->getTerrainFileResourceGroup()); } diff --git a/source/main/gui/panels/GUI_SurveyMap.h b/source/main/gui/panels/GUI_SurveyMap.h index d6b24a2e3f..1c7f6f9314 100644 --- a/source/main/gui/panels/GUI_SurveyMap.h +++ b/source/main/gui/panels/GUI_SurveyMap.h @@ -2,7 +2,7 @@ This source file is part of Rigs of Rods Copyright 2005-2012 Pierre-Michel Ricordel Copyright 2007-2012 Thomas Fischer - Copyright 2013-2020 Petr Ohlidal + Copyright 2013-2023 Petr Ohlidal For more information, see http://www.rigsofrods.org/ @@ -50,15 +50,13 @@ class SurveyMap const float WINDOW_PADDING = 4.f; const float WINDOW_ROUNDING = 2.f; - void CreateTerrainTextures(); //!< Init + void CreateTerrainTextures(); void Draw(); bool IsVisible() const { return mMapMode != SurveyMapMode::NONE; } bool IsHovered() const { return IsVisible() && mWindowMouseHovered; } void CycleMode(); void ToggleMode(); - const char* getTypeByDriveable(int driveable); - protected: enum class SurveyMapMode @@ -93,9 +91,7 @@ class SurveyMap Ogre::Vector2 mTerrainSize = Ogre::Vector2::ZERO; // Computed reference map size (in meters) Ogre::Vector2 mMapCenterOffset = Ogre::Vector2::ZERO; // Displacement, in meters float mMapZoom = 0.f; // Ratio: 0-1 - - std::unique_ptr mMapTextureCreatorStatic; - std::unique_ptr mMapTextureCreatorDynamic; + Ogre::TexturePtr mMapTexture; // Icon cache bool m_icons_cached = false;