diff --git a/Mods/vcmi/config/vcmi/czech.json b/Mods/vcmi/config/vcmi/czech.json
index 1e9f8b2e8..f1c561b97 100644
--- a/Mods/vcmi/config/vcmi/czech.json
+++ b/Mods/vcmi/config/vcmi/czech.json
@@ -44,7 +44,7 @@
"vcmi.mainMenu.joinTCP" : "Připojit se do hry TCP/IP",
"vcmi.mainMenu.playerName" : "Hráč",
- "vcmi.lobby.filename" : "Název souboru",
+ "vcmi.lobby.filepath" : "Název souboru",
"vcmi.lobby.creationDate" : "Datum vytvoření",
"vcmi.server.errors.existingProcess" : "Již běží jiný server VCMI. Prosím, ukončete ho před startem nové hry.",
diff --git a/Mods/vcmi/config/vcmi/english.json b/Mods/vcmi/config/vcmi/english.json
index a14081798..c5cba2fa1 100644
--- a/Mods/vcmi/config/vcmi/english.json
+++ b/Mods/vcmi/config/vcmi/english.json
@@ -49,8 +49,12 @@
"vcmi.mainMenu.joinTCP" : "Join TCP/IP game",
"vcmi.mainMenu.playerName" : "Player",
- "vcmi.lobby.filename" : "Filename",
+ "vcmi.lobby.filepath" : "File path",
"vcmi.lobby.creationDate" : "Creation date",
+ "vcmi.lobby.scenarioName" : "Scenario name",
+ "vcmi.lobby.mapPreview" : "Map preview",
+ "vcmi.lobby.noPreview" : "no preview",
+ "vcmi.lobby.noUnderground" : "no underground",
"vcmi.server.errors.existingProcess" : "Another VCMI server process is running. Please terminate it before starting a new game.",
"vcmi.server.errors.modsToEnable" : "{Following mods are required}",
diff --git a/Mods/vcmi/config/vcmi/german.json b/Mods/vcmi/config/vcmi/german.json
index abe112ebd..121deacb2 100644
--- a/Mods/vcmi/config/vcmi/german.json
+++ b/Mods/vcmi/config/vcmi/german.json
@@ -48,8 +48,12 @@
"vcmi.mainMenu.joinTCP" : "Trete TCP/IP Spiel bei",
"vcmi.mainMenu.playerName" : "Spieler",
- "vcmi.lobby.filename" : "Dateiname",
+ "vcmi.lobby.filepath" : "Dateipfad",
"vcmi.lobby.creationDate" : "Erstellungsdatum",
+ "vcmi.lobby.scenarioName" : "Szenario-Name",
+ "vcmi.lobby.mapPreview" : "Kartenvorschau",
+ "vcmi.lobby.noPreview" : "Keine Vorschau",
+ "vcmi.lobby.noUnderground" : "Kein Untergrund",
"vcmi.server.errors.existingProcess" : "Es läuft ein weiterer vcmiserver-Prozess, bitte beendet diesen zuerst",
"vcmi.server.errors.modsToEnable" : "{Erforderliche Mods um das Spiel zu laden}",
diff --git a/Mods/vcmi/config/vcmi/polish.json b/Mods/vcmi/config/vcmi/polish.json
index 51c96dac4..1526e83e3 100644
--- a/Mods/vcmi/config/vcmi/polish.json
+++ b/Mods/vcmi/config/vcmi/polish.json
@@ -43,7 +43,7 @@
"vcmi.mainMenu.joinTCP" : "Dołącz do gry TCP/IP",
"vcmi.mainMenu.playerName" : "Gracz",
- "vcmi.lobby.filename" : "Nazwa pliku",
+ "vcmi.lobby.filepath" : "Nazwa pliku",
"vcmi.lobby.creationDate" : "Data utworzenia",
"vcmi.server.errors.existingProcess" : "Inny proces 'vcmiserver' został już uruchomiony, zakończ go nim przejdziesz dalej",
diff --git a/Mods/vcmi/config/vcmi/ukrainian.json b/Mods/vcmi/config/vcmi/ukrainian.json
index 4f5228821..9773fc7af 100644
--- a/Mods/vcmi/config/vcmi/ukrainian.json
+++ b/Mods/vcmi/config/vcmi/ukrainian.json
@@ -44,7 +44,7 @@
"vcmi.mainMenu.joinTCP" : "Приєднатися до TCP/IP гри",
"vcmi.mainMenu.playerName" : "Гравець",
- "vcmi.lobby.filename" : "Назва файлу",
+ "vcmi.lobby.filepath" : "Назва файлу",
"vcmi.lobby.creationDate" : "Дата створення",
"vcmi.server.errors.existingProcess" : "Працює інший процес vcmiserver, будь ласка, спочатку завершіть його",
diff --git a/Mods/vcmi/config/vcmi/vietnamese.json b/Mods/vcmi/config/vcmi/vietnamese.json
index 9926fce10..890e699d1 100644
--- a/Mods/vcmi/config/vcmi/vietnamese.json
+++ b/Mods/vcmi/config/vcmi/vietnamese.json
@@ -50,7 +50,7 @@
"vcmi.mainMenu.joinTCP": "Tham gia TCP/IP",
"vcmi.mainMenu.playerName": "Người chơi",
- "vcmi.lobby.filename": "Tên tập tin",
+ "vcmi.lobby.filepath": "Tên tập tin",
"vcmi.lobby.creationDate": "Ngày tạo",
"vcmi.server.errors.existingProcess": "1 chương trình VCMI khác đang chạy. Tắt nó trước khi mở cái mới",
diff --git a/client/CMakeLists.txt b/client/CMakeLists.txt
index ed53ca99a..2912d02cf 100644
--- a/client/CMakeLists.txt
+++ b/client/CMakeLists.txt
@@ -119,6 +119,7 @@ set(client_SRCS
windows/CHeroOverview.cpp
windows/CHeroWindow.cpp
windows/CKingdomInterface.cpp
+ windows/CMapOverview.cpp
windows/CMessage.cpp
windows/CPuzzleWindow.cpp
windows/CQuestLog.cpp
@@ -285,6 +286,7 @@ set(client_HEADERS
windows/CHeroWindow.h
windows/CKingdomInterface.h
windows/CMessage.h
+ windows/CMapOverview.h
windows/CPuzzleWindow.h
windows/CQuestLog.h
windows/CSpellWindow.h
diff --git a/client/VCMI_client.cbp b/client/VCMI_client.cbp
index 57fc618b5..081be52ae 100644
--- a/client/VCMI_client.cbp
+++ b/client/VCMI_client.cbp
@@ -229,6 +229,8 @@
+
+
diff --git a/client/VCMI_client.vcxproj b/client/VCMI_client.vcxproj
index 3fe7331f9..997bdba6a 100644
--- a/client/VCMI_client.vcxproj
+++ b/client/VCMI_client.vcxproj
@@ -238,6 +238,7 @@
+
@@ -305,6 +306,7 @@
+
diff --git a/client/VCMI_client.vcxproj.filters b/client/VCMI_client.vcxproj.filters
index 8831d0480..9b717e834 100644
--- a/client/VCMI_client.vcxproj.filters
+++ b/client/VCMI_client.vcxproj.filters
@@ -25,6 +25,9 @@
windows
+
+ windows
+
windows
@@ -179,6 +182,9 @@
windows
+
+ windows
+
windows
diff --git a/client/gui/InterfaceObjectConfigurable.cpp b/client/gui/InterfaceObjectConfigurable.cpp
index 3a1fd45cb..24d20d3fc 100644
--- a/client/gui/InterfaceObjectConfigurable.cpp
+++ b/client/gui/InterfaceObjectConfigurable.cpp
@@ -56,6 +56,8 @@ InterfaceObjectConfigurable::InterfaceObjectConfigurable(int used, Point offset)
REGISTER_BUILDER("layout", &InterfaceObjectConfigurable::buildLayout);
REGISTER_BUILDER("comboBox", &InterfaceObjectConfigurable::buildComboBox);
REGISTER_BUILDER("textInput", &InterfaceObjectConfigurable::buildTextInput);
+ REGISTER_BUILDER("transparentFilledRectangle", &InterfaceObjectConfigurable::buildTransparentFilledRectangle);
+ REGISTER_BUILDER("textBox", &InterfaceObjectConfigurable::buildTextBox);
}
void InterfaceObjectConfigurable::registerBuilder(const std::string & type, BuilderFunction f)
@@ -684,6 +686,33 @@ std::shared_ptr InterfaceObjectConfigurable::buildAnimation(const
return anim;
}
+std::shared_ptr InterfaceObjectConfigurable::buildTransparentFilledRectangle(const JsonNode & config) const
+{
+ logGlobal->debug("Building widget TransparentFilledRectangle");
+
+ auto rect = readRect(config["rect"]);
+ auto color = readColor(config["color"]);
+ if(!config["colorLine"].isNull())
+ {
+ auto colorLine = readColor(config["colorLine"]);
+ return std::make_shared(rect, color, colorLine);
+ }
+ return std::make_shared(rect, color);
+}
+
+std::shared_ptr InterfaceObjectConfigurable::buildTextBox(const JsonNode & config) const
+{
+ logGlobal->debug("Building widget CTextBox");
+
+ auto rect = readRect(config["rect"]);
+ auto font = readFont(config["font"]);
+ auto alignment = readTextAlignment(config["alignment"]);
+ auto color = readColor(config["color"]);
+ auto text = readText(config["text"]);
+
+ return std::make_shared(text, rect, 0, font, alignment, color);
+}
+
std::shared_ptr InterfaceObjectConfigurable::buildWidget(JsonNode config) const
{
assert(!config.isNull());
diff --git a/client/gui/InterfaceObjectConfigurable.h b/client/gui/InterfaceObjectConfigurable.h
index 30b96bfb4..cc812299e 100644
--- a/client/gui/InterfaceObjectConfigurable.h
+++ b/client/gui/InterfaceObjectConfigurable.h
@@ -29,6 +29,8 @@ class CShowableAnim;
class CFilledTexture;
class ComboBox;
class CTextInput;
+class TransparentFilledRectangle;
+class CTextBox;
#define REGISTER_BUILDER(type, method) registerBuilder(type, std::bind(method, this, std::placeholders::_1))
@@ -105,6 +107,8 @@ protected:
std::shared_ptr buildLayout(const JsonNode &);
std::shared_ptr buildComboBox(const JsonNode &);
std::shared_ptr buildTextInput(const JsonNode &) const;
+ std::shared_ptr buildTransparentFilledRectangle(const JsonNode & config) const;
+ std::shared_ptr buildTextBox(const JsonNode & config) const;
//composite widgets
std::shared_ptr buildWidget(JsonNode config) const;
diff --git a/client/lobby/SelectionTab.cpp b/client/lobby/SelectionTab.cpp
index 9e0f87052..6faa7fc2c 100644
--- a/client/lobby/SelectionTab.cpp
+++ b/client/lobby/SelectionTab.cpp
@@ -27,11 +27,10 @@
#include "../widgets/TextControls.h"
#include "../windows/GUIClasses.h"
#include "../windows/InfoWindows.h"
+#include "../windows/CMapOverview.h"
#include "../render/CAnimation.h"
-#include "../render/Canvas.h"
#include "../render/IImage.h"
#include "../render/IRenderHandler.h"
-#include "../render/Graphics.h"
#include "../../CCallback.h"
@@ -41,8 +40,6 @@
#include "../../lib/GameSettings.h"
#include "../../lib/filesystem/Filesystem.h"
#include "../../lib/campaign/CampaignState.h"
-#include "../../lib/mapping/CMap.h"
-#include "../../lib/mapping/CMapService.h"
#include "../../lib/mapping/CMapInfo.h"
#include "../../lib/mapping/CMapHeader.h"
#include "../../lib/mapping/MapFormat.h"
@@ -366,13 +363,7 @@ void SelectionTab::showPopupWindow(const Point & cursorPosition)
return;
if(!curItems[py]->isFolder)
- {
- std::string text = boost::str(boost::format("{%1%}\r\n\r\n%2%:\r\n%3%") % curItems[py]->getNameTranslated() % CGI->generaltexth->translate("vcmi.lobby.filename") % curItems[py]->fullFileURI);
- if(curItems[py]->date != "")
- text += boost::str(boost::format("\r\n\r\n%1%:\r\n%2%") % CGI->generaltexth->translate("vcmi.lobby.creationDate") % curItems[py]->date);
-
- GH.windows().createAndPushWindow(text, ResourcePath(curItems[py]->fileURI), tabType);
- }
+ GH.windows().createAndPushWindow(curItems[py]->getNameTranslated(), curItems[py]->fullFileURI, curItems[py]->date, ResourcePath(curItems[py]->fileURI), tabType);
else
CRClickPopup::createAndPush(curItems[py]->folderName);
}
@@ -822,121 +813,6 @@ std::unordered_set SelectionTab::getFiles(std::string dirURI, ERes
return ret;
}
-SelectionTab::CMapInfoTooltipBox::CMapInfoTooltipBox(std::string text, ResourcePath resource, ESelectionScreen tabType)
- : CWindowObject(BORDERED | RCLICK_POPUP)
-{
- drawPlayerElements = tabType == ESelectionScreen::newGame;
- renderImage = tabType == ESelectionScreen::newGame && settings["lobby"]["mapPreview"].Bool();
-
- OBJ_CONSTRUCTION_CAPTURING_ALL_NO_DISPOSE;
-
- std::vector> mapLayerImages;
- if(renderImage)
- mapLayerImages = createMinimaps(ResourcePath(resource.getName(), EResType::MAP), IMAGE_SIZE);
-
- if(mapLayerImages.size() == 0)
- renderImage = false;
-
- pos = Rect(0, 0, 3 * BORDER + 2 * IMAGE_SIZE, 2000);
-
- auto drawLabel = [&]() {
- label = std::make_shared(text, Rect(BORDER, BORDER, BORDER + 2 * IMAGE_SIZE, 350), 0, FONT_MEDIUM, ETextAlignment::CENTER, Colors::WHITE);
- if(!label->slider)
- label->resize(Point(BORDER + 2 * IMAGE_SIZE, label->label->textSize.y));
- };
- drawLabel();
-
- int textHeight = std::min(350, label->label->textSize.y);
- pos.h = BORDER + textHeight + BORDER;
- if(renderImage)
- pos.h += IMAGE_SIZE + BORDER;
- backgroundTexture = std::make_shared(ImagePath::builtin("DIBOXBCK"), pos);
- updateShadow();
-
- drawLabel();
-
- if(renderImage)
- {
- if(mapLayerImages.size() == 1)
- image1 = std::make_shared(mapLayerImages[0], Point(BORDER + (BORDER + IMAGE_SIZE) / 2, textHeight + 2 * BORDER));
- else
- {
- image1 = std::make_shared(mapLayerImages[0], Point(BORDER, textHeight + 2 * BORDER));
- image2 = std::make_shared(mapLayerImages[1], Point(BORDER + IMAGE_SIZE + BORDER, textHeight + 2 * BORDER));
- }
- }
-
- center(GH.getCursorPosition()); //center on mouse
-#ifdef VCMI_MOBILE
- moveBy({0, -pos.h / 2});
-#endif
- fitToScreen(10);
-}
-
-Canvas SelectionTab::CMapInfoTooltipBox::createMinimapForLayer(std::unique_ptr & map, int layer)
-{
- Canvas canvas = Canvas(Point(map->width, map->height));
-
- for (int y = 0; y < map->height; ++y)
- for (int x = 0; x < map->width; ++x)
- {
- TerrainTile & tile = map->getTile(int3(x, y, layer));
-
- ColorRGBA color = tile.terType->minimapUnblocked;
- if (tile.blocked && (!tile.visitable))
- color = tile.terType->minimapBlocked;
-
- if(drawPlayerElements)
- // if object at tile is owned - it will be colored as its owner
- for (const CGObjectInstance *obj : tile.blockingObjects)
- {
- PlayerColor player = obj->getOwner();
- if(player == PlayerColor::NEUTRAL)
- {
- color = graphics->neutralColor;
- break;
- }
- if (player.isValidPlayer())
- {
- color = graphics->playerColors[player.getNum()];
- break;
- }
- }
-
- canvas.drawPoint(Point(x, y), color);
- }
-
- return canvas;
-}
-
-std::vector> SelectionTab::CMapInfoTooltipBox::createMinimaps(ResourcePath resource, int size)
-{
- std::vector> ret = std::vector>();
-
- CMapService mapService;
- std::unique_ptr map;
- try
- {
- map = mapService.loadMap(resource);
- }
- catch (...)
- {
- return ret;
- }
-
- for(int i = 0; i < (map->twoLevel ? 2 : 1); i++)
- {
- Canvas canvas = createMinimapForLayer(map, i);
- Canvas canvasScaled = Canvas(Point(size, size));
- canvasScaled.drawScaled(canvas, Point(0, 0), Point(size, size));
- std::shared_ptr img = GH.renderHandler().createImage(canvasScaled.getInternalSurface());
-
- ret.push_back(img);
- }
-
- return ret;
-}
-
SelectionTab::ListItem::ListItem(Point position, std::shared_ptr iconsFormats, std::shared_ptr iconsVictory, std::shared_ptr iconsLoss)
: CIntObject(LCLICK, position)
{
diff --git a/client/lobby/SelectionTab.h b/client/lobby/SelectionTab.h
index e4d67ef83..50f501769 100644
--- a/client/lobby/SelectionTab.h
+++ b/client/lobby/SelectionTab.h
@@ -67,25 +67,6 @@ class SelectionTab : public CIntObject
// FIXME: CSelectionBase use them too!
std::shared_ptr iconsVictoryCondition;
std::shared_ptr iconsLossCondition;
-
- class CMapInfoTooltipBox : public CWindowObject
- {
- const int IMAGE_SIZE = 169;
- const int BORDER = 30;
-
- bool drawPlayerElements;
- bool renderImage;
-
- std::shared_ptr backgroundTexture;
- std::shared_ptr label;
- std::shared_ptr image1;
- std::shared_ptr image2;
-
- Canvas createMinimapForLayer(std::unique_ptr & map, int layer);
- std::vector> createMinimaps(ResourcePath resource, int size);
- public:
- CMapInfoTooltipBox(std::string text, ResourcePath resource, ESelectionScreen tabType);
- };
public:
std::vector> allItems;
std::vector> curItems;
diff --git a/client/windows/CMapOverview.cpp b/client/windows/CMapOverview.cpp
new file mode 100644
index 000000000..ffa7aeb03
--- /dev/null
+++ b/client/windows/CMapOverview.cpp
@@ -0,0 +1,206 @@
+/*
+ * CMapOverview.cpp, part of VCMI engine
+ *
+ * Authors: listed in file AUTHORS in main folder
+ *
+ * License: GNU General Public License v2.0 or later
+ * Full text of license available in license.txt file, in main folder
+ *
+ */
+#include "StdInc.h"
+
+#include "CMapOverview.h"
+
+#include "../lobby/SelectionTab.h"
+
+#include
+
+#include "../gui/CGuiHandler.h"
+#include "../gui/WindowHandler.h"
+#include "../widgets/CComponent.h"
+#include "../widgets/MiscWidgets.h"
+#include "../widgets/TextControls.h"
+#include "../windows/GUIClasses.h"
+#include "../windows/InfoWindows.h"
+#include "../render/CAnimation.h"
+#include "../render/Canvas.h"
+#include "../render/IImage.h"
+#include "../render/IRenderHandler.h"
+#include "../render/Graphics.h"
+
+#include "../../lib/CGeneralTextHandler.h"
+#include "../../lib/CConfigHandler.h"
+#include "../../lib/campaign/CampaignState.h"
+#include "../../lib/mapping/CMap.h"
+#include "../../lib/mapping/CMapService.h"
+#include "../../lib/mapping/CMapInfo.h"
+#include "../../lib/mapping/CMapHeader.h"
+#include "../../lib/mapping/MapFormat.h"
+#include "../../lib/TerrainHandler.h"
+#include "../../lib/filesystem/Filesystem.h"
+
+#include "../../lib/serializer/BinaryDeserializer.h"
+#include "../../lib/StartInfo.h"
+#include "../../lib/rmg/CMapGenOptions.h"
+
+CMapOverview::CMapOverview(std::string mapName, std::string fileName, std::string date, ResourcePath resource, ESelectionScreen tabType)
+ : CWindowObject(BORDERED | RCLICK_POPUP), resource(resource), mapName(mapName), fileName(fileName), date(date), tabType(tabType)
+{
+
+ OBJ_CONSTRUCTION_CAPTURING_ALL_NO_DISPOSE;
+
+ widget = std::make_shared(*this);
+
+ updateShadow();
+
+ center(GH.getCursorPosition()); //center on mouse
+#ifdef VCMI_MOBILE
+ moveBy({0, -pos.h / 2});
+#endif
+ fitToScreen(10);
+}
+
+Canvas CMapOverviewWidget::createMinimapForLayer(std::unique_ptr & map, int layer) const
+{
+ Canvas canvas = Canvas(Point(map->width, map->height));
+
+ for (int y = 0; y < map->height; ++y)
+ for (int x = 0; x < map->width; ++x)
+ {
+ TerrainTile & tile = map->getTile(int3(x, y, layer));
+
+ ColorRGBA color = tile.terType->minimapUnblocked;
+ if (tile.blocked && (!tile.visitable))
+ color = tile.terType->minimapBlocked;
+
+ if(drawPlayerElements)
+ // if object at tile is owned - it will be colored as its owner
+ for (const CGObjectInstance *obj : tile.blockingObjects)
+ {
+ PlayerColor player = obj->getOwner();
+ if(player == PlayerColor::NEUTRAL)
+ {
+ color = graphics->neutralColor;
+ break;
+ }
+ if (player.isValidPlayer())
+ {
+ color = graphics->playerColors[player.getNum()];
+ break;
+ }
+ }
+
+ canvas.drawPoint(Point(x, y), color);
+ }
+
+ return canvas;
+}
+
+std::vector