Jelajahi Sumber

Implemeted runtime generation of player-colored background texture

Ivan Savenko 2 tahun lalu
induk
melakukan
7228b08d1d

+ 13 - 0
client/adventureMap/CAdventureMapWidget.cpp

@@ -51,6 +51,7 @@ CAdventureMapWidget::CAdventureMapWidget( std::shared_ptr<AdventureMapShortcuts>
 	REGISTER_BUILDER("adventureMinimap",         &CAdventureMapWidget::buildMinimap         );
 	REGISTER_BUILDER("adventureResourceDateBar", &CAdventureMapWidget::buildResourceDateBar );
 	REGISTER_BUILDER("adventureStatusBar",       &CAdventureMapWidget::buildStatusBar       );
+	REGISTER_BUILDER("adventurePlayerTexture",   &CAdventureMapWidget::buildTexturePlayerColored);
 
 	for (const auto & entry : shortcuts->getShortcuts())
 		addShortcut(entry.shortcut, entry.callback);
@@ -326,6 +327,14 @@ std::shared_ptr<CIntObject> CAdventureMapWidget::buildStatusBar(const JsonNode &
 	return CGStatusBar::create(background);
 }
 
+std::shared_ptr<CIntObject> CAdventureMapWidget::buildTexturePlayerColored(const JsonNode & input)
+{
+	logGlobal->debug("Building widget CFilledTexture");
+	auto image = input["image"].String();
+	Rect area = readTargetArea(input["area"]);
+	return std::make_shared<FilledTexturePlayerColored>(image, area);
+}
+
 std::shared_ptr<CHeroList> CAdventureMapWidget::getHeroList()
 {
 	return heroList;
@@ -363,6 +372,7 @@ void CAdventureMapWidget::setPlayerChildren(CIntObject * widget, const PlayerCol
 		auto container = dynamic_cast<CAdventureMapContainerWidget *>(entry);
 		auto icon = dynamic_cast<CAdventureMapIcon *>(entry);
 		auto button = dynamic_cast<CButton *>(entry);
+		auto texture = dynamic_cast<FilledTexturePlayerColored *>(entry);
 
 		if(button)
 			button->setPlayerColor(player);
@@ -372,6 +382,9 @@ void CAdventureMapWidget::setPlayerChildren(CIntObject * widget, const PlayerCol
 
 		if(container)
 			setPlayerChildren(container, player);
+
+		if (texture)
+			texture->playerColored(player);
 	}
 
 	for(const auto & entry : playerColorerImages)

+ 2 - 0
client/adventureMap/CAdventureMapWidget.h

@@ -61,6 +61,8 @@ class CAdventureMapWidget : public InterfaceObjectConfigurable
 	std::shared_ptr<CIntObject> buildMinimap(const JsonNode & input);
 	std::shared_ptr<CIntObject> buildResourceDateBar(const JsonNode & input);
 	std::shared_ptr<CIntObject> buildStatusBar(const JsonNode & input);
+	std::shared_ptr<CIntObject> buildTexturePlayerColored(const JsonNode &);
+
 
 	void setPlayerChildren(CIntObject * widget, const PlayerColor & player);
 	void updateActiveStateChildden(CIntObject * widget);

+ 30 - 0
client/widgets/Images.cpp

@@ -16,6 +16,7 @@
 #include "../renderSDL/SDL_Extensions.h"
 #include "../render/IImage.h"
 #include "../render/CAnimation.h"
+#include "../render/ColorFilter.h"
 
 #include "../battle/BattleInterface.h"
 #include "../battle/BattleInterfaceClasses.h"
@@ -135,6 +136,35 @@ void CFilledTexture::showAll(SDL_Surface *to)
 	}
 }
 
+FilledTexturePlayerColored::FilledTexturePlayerColored(std::string imageName, Rect position)
+	: CFilledTexture(imageName, position)
+{
+}
+
+void FilledTexturePlayerColored::playerColored(PlayerColor player)
+{
+	// Color transform to make color of brown DIBOX.PCX texture match color of specified player
+	std::array<ColorFilter, PlayerColor::PLAYER_LIMIT_I> filters = {
+		ColorFilter::genRangeShifter( 0.250,0,0, 1.250, 0.000, 0.000 ), // red
+		ColorFilter::genRangeShifter( 0,0,0, 0.435, 1.160, 4.500 ), // blue
+		ColorFilter::genRangeShifter( 0,0,0, 2.000, 2.400, 3.200 ), // tan
+		ColorFilter::genRangeShifter( 0,0,0, 0.160, 2.150, 0.125 ), // green
+		ColorFilter::genRangeShifter( 0,0,0, 2.700, 1.900, 0.000 ), // orange
+		ColorFilter::genRangeShifter( 0,0,0, 1.400, 0.540, 5.000 ), // purple
+		ColorFilter::genRangeShifter( 0,0,0, 0.450, 2.250, 4.400 ), // teal
+		ColorFilter::genRangeShifter( 0,0,0, 2.000, 1.750, 3.750 ) // pink
+	};
+
+	assert(player.isValidPlayer());
+	if (!player.isValidPlayer())
+	{
+		logGlobal->error("Unable to colorize to invalid player color %d!", static_cast<int>(player.getNum()));
+		return;
+	}
+
+	texture->adjustPalette(filters[player.getNum()], 0);
+}
+
 CAnimImage::CAnimImage(const std::string & name, size_t Frame, size_t Group, int x, int y, ui8 Flags):
 	frame(Frame),
 	group(Group),

+ 9 - 0
client/widgets/Images.h

@@ -68,6 +68,7 @@ public:
 /// area filled with specific texture
 class CFilledTexture : public CIntObject
 {
+protected:
 	std::shared_ptr<IImage> texture;
 	Rect imageArea;
 
@@ -78,6 +79,14 @@ public:
 	void showAll(SDL_Surface *to) override;
 };
 
+class FilledTexturePlayerColored : public CFilledTexture
+{
+public:
+	FilledTexturePlayerColored(std::string imageName, Rect position);
+
+	void playerColored(PlayerColor player);
+};
+
 /// Class for displaying one image from animation
 class CAnimImage: public CIntObject
 {

+ 12 - 6
config/widgets/adventureMap.json

@@ -115,7 +115,7 @@
 				{
 					"type": "adventureMapContainer",
 					"hideWhen" : "mapLayerSurface",
-					"area": { "top" : 0, "left": 32, "width" : 32, "height" : 32 }
+					"area": { "top" : 0, "left": 32, "width" : 32, "height" : 32 },
 					"items" : [
 						{
 							"type": "adventureMapButton",
@@ -131,7 +131,7 @@
 				{
 					"type": "adventureMapContainer",
 					"hideWhen" : "mapLayerUnderground",
-					"area": { "top" : 0, "left": 32, "width" : 32, "height" : 32 }
+					"area": { "top" : 0, "left": 32, "width" : 32, "height" : 32 },
 					"items" : [
 						{
 							"type": "adventureMapButton",
@@ -156,7 +156,7 @@
 				{
 					"type": "adventureMapContainer",
 					"hideWhen" : "heroAwake",
-					"area": { "top" : 32, "left": 32, "width" : 32, "height" : 32 }
+					"area": { "top" : 32, "left": 32, "width" : 32, "height" : 32 },
 					"items" : [
 						{
 							"type": "adventureMapButton",
@@ -172,7 +172,7 @@
 				{
 					"type": "adventureMapContainer",
 					"hideWhen" : "heroSleeping",
-					"area": { "top" : 32, "left": 32, "width" : 32, "height" : 32 }
+					"area": { "top" : 32, "left": 32, "width" : 32, "height" : 32 },
 					"items" : [
 						{
 							"type": "adventureMapButton",
@@ -425,7 +425,7 @@
 			"type": "adventureMapContainer",
 			"name" : "adventureInfobarContainer",
 			"hideWhen" : "worldViewMode",
-			"area" : { "bottom": 0, "right" : 0, "width" : 199, "height" : 211 }
+			"area" : { "bottom": 0, "right" : 0, "width" : 199, "height" : 211 },
 			"items" : [
 				// Infobar
 				{
@@ -450,6 +450,12 @@
 			"area": { "left": 8, "bottom" : 26, "right" : 199, "height" : 18 }
 		},
 		// Resource & Data bar
+		{
+			"type": "adventurePlayerTexture",
+			"name" : "backgroundBottomCenter",
+			"image" : "DiBoxBck.pcx",
+			"area" : { "left": 3, "bottom" : 4, "right" : 797, "height" : 21 }
+		},
 		{
 			"type": "adventureResourceDateBar",
 			"name": "resourceDataBar",
@@ -784,7 +790,7 @@
 							"text": "core.genrltxt.625"
 						}
 					]
-				}
+				},
 				{
 					"type": "adventureMapImage",
 					"name" : "backgroundBelowWorldView",