فهرست منبع

Implemented mapping of hero portraits

Ivan Savenko 2 سال پیش
والد
کامیت
6564502a0e

+ 1 - 1
lib/GameConstants.h

@@ -75,7 +75,7 @@ namespace GameConstants
 
 	constexpr ui32 BASE_MOVEMENT_COST = 100; //default cost for non-diagonal movement
 
-	constexpr int HERO_PORTRAIT_SHIFT = 30;// 2 special frames + some extra portraits
+	constexpr int HERO_PORTRAIT_SHIFT = 9;// 2 special frames + 7 extra portraits
 
 	constexpr std::array<int, 11> POSSIBLE_TURNTIME = {1, 2, 4, 6, 8, 10, 15, 20, 25, 30, 0};
 }

+ 3 - 5
lib/mapping/MapFeaturesH3M.cpp

@@ -135,21 +135,19 @@ MapFormatFeaturesH3M MapFormatFeaturesH3M::getFeaturesHOTA(uint32_t hotaVersion)
 	if(hotaVersion < 3)
 	{
 		result.artifactsCount = 163; // + HotA artifacts
-		result.heroesCount = 177; // + Cove
-		result.heroesPortraitsCount = 187; // + Cove
+		result.heroesCount = 178; // + Cove
+		result.heroesPortraitsCount = 185; // + Cove
 	}
 	if(hotaVersion == 3)
 	{
 		result.artifactsCount = 165; // + HotA artifacts
-		result.heroesCount = 177; // + Cove + Giselle
+		result.heroesCount = 179; // + Cove + Giselle
 		result.heroesPortraitsCount = 188; // + Cove + Giselle
 	}
 
 	assert((result.heroesCount + 7) / 8 == result.heroesBytes);
 	assert((result.artifactsCount + 7) / 8 == result.artifactsBytes);
 
-	result.heroesCount = 179; // + Cove
-
 	return result;
 }
 

+ 5 - 5
lib/mapping/MapFormatH3M.cpp

@@ -251,7 +251,7 @@ void CMapLoaderH3M::readPlayerInfo()
 
 		if(playerInfo.mainCustomHeroId != -1)
 		{
-			playerInfo.mainCustomHeroPortrait = reader->readHero().getNum();
+			playerInfo.mainCustomHeroPortrait = reader->readHeroPortrait();
 			playerInfo.mainCustomHeroName = readLocalizedString(TextIdentifier("header", "player", i, "mainHeroName"));
 		}
 
@@ -686,7 +686,7 @@ void CMapLoaderH3M::readDisposedHeroes()
 		for(int g = 0; g < disp; ++g)
 		{
 			map->disposedHeroes[g].heroId = reader->readHero().getNum();
-			map->disposedHeroes[g].portrait = reader->readHero().getNum();
+			map->disposedHeroes[g].portrait = reader->readHeroPortrait();
 			map->disposedHeroes[g].name = readLocalizedString(TextIdentifier("header", "heroes", map->disposedHeroes[g].heroId));
 			map->disposedHeroes[g].players = reader->readUInt8();
 		}
@@ -1623,7 +1623,7 @@ CGObjectInstance * CMapLoaderH3M::readHero(const int3 & mapPosition, const Objec
 	}
 
 	PlayerColor owner = reader->readPlayer();
-	object->subID = reader->readUInt8();
+	object->subID = reader->readHero().getNum();
 
 	//If hero of this type has been predefined, use that as a base.
 	//Instance data will overwrite the predefined values where appropriate.
@@ -1639,7 +1639,7 @@ CGObjectInstance * CMapLoaderH3M::readHero(const int3 & mapPosition, const Objec
 	}
 
 	setOwnerAndValidate(mapPosition, object, owner);
-	object->portrait = object->subID;
+	object->portrait = CGHeroInstance::UNINITIALIZED_PORTRAIT;
 
 	for(auto & elem : map->disposedHeroes)
 	{
@@ -1674,7 +1674,7 @@ CGObjectInstance * CMapLoaderH3M::readHero(const int3 & mapPosition, const Objec
 
 	bool hasPortrait = reader->readBool();
 	if(hasPortrait)
-		object->portrait = reader->readHero().getNum();
+		object->portrait = reader->readHeroPortrait();
 
 	bool hasSecSkills = reader->readBool();
 	if(hasSecSkills)

+ 17 - 0
lib/mapping/MapIdentifiersH3M.cpp

@@ -15,6 +15,7 @@
 #include "../VCMI_Lib.h"
 #include "../CModHandler.h"
 #include "../CTownHandler.h"
+#include "../CHeroHandler.h"
 #include "../filesystem/Filesystem.h"
 #include "../mapObjectConstructors/AObjectTypeHandler.h"
 #include "../mapObjectConstructors/CObjectClassesHandler.h"
@@ -86,6 +87,15 @@ void MapIdentifiersH3M::loadMapping(const JsonNode & mapping)
 		}
 	}
 
+	for (auto entry : mapping["portraits"].Struct())
+	{
+		int32_t sourceID = entry.second.Integer();
+		int32_t targetID = *VLC->modh->identifiers.getIdentifier(VLC->modh->scopeGame(), "hero", entry.first);
+		int32_t iconID = VLC->heroTypes()->getByIndex(targetID)->getIconIndex();
+
+		mappingHeroPortrait[sourceID] = iconID;
+	}
+
 	loadMapping(mappingBuilding, mapping["buildingsCommon"], "building.core:random");
 	loadMapping(mappingFaction, mapping["factions"], "faction");
 	loadMapping(mappingCreature, mapping["creatures"], "creature");
@@ -158,6 +168,13 @@ HeroTypeID MapIdentifiersH3M::remap(HeroTypeID input) const
 	return input;
 }
 
+int32_t MapIdentifiersH3M::remapPortrrait(int32_t input) const
+{
+	if (mappingHeroPortrait.count(input))
+		return mappingHeroPortrait.at(input);
+	return input;
+}
+
 HeroClassID MapIdentifiersH3M::remap(HeroClassID input) const
 {
 	if (mappingHeroClass.count(input))

+ 3 - 0
lib/mapping/MapIdentifiersH3M.h

@@ -37,6 +37,7 @@ class MapIdentifiersH3M
 	std::map<FactionID, FactionID> mappingFaction;
 	std::map<CreatureID, CreatureID> mappingCreature;
 	std::map<HeroTypeID, HeroTypeID> mappingHeroType;
+	std::map<int32_t, int32_t> mappingHeroPortrait;
 	std::map<HeroClassID, HeroClassID> mappingHeroClass;
 	std::map<TerrainId, TerrainId> mappingTerrain;
 	std::map<ArtifactID, ArtifactID> mappingArtifact;
@@ -53,6 +54,7 @@ public:
 	void remapTemplate(ObjectTemplate & objectTemplate);
 
 	BuildingID remapBuilding(std::optional<FactionID> owner, BuildingID input) const;
+	int32_t remapPortrrait(int32_t input) const;
 	FactionID remap(FactionID input) const;
 	CreatureID remap(CreatureID input) const;
 	HeroTypeID remap(HeroTypeID input) const;
@@ -60,6 +62,7 @@ public:
 	TerrainId remap(TerrainId input) const;
 	ArtifactID remap(ArtifactID input) const;
 	SecondarySkill remap(SecondarySkill input) const;
+
 };
 
 VCMI_LIB_NAMESPACE_END

+ 12 - 1
lib/mapping/MapReaderH3M.cpp

@@ -96,8 +96,19 @@ HeroTypeID MapReaderH3M::readHero()
 	if(result.getNum() == features.heroIdentifierInvalid)
 		return HeroTypeID(-1);
 
+	assert(result.getNum() < features.heroesCount);
+	return remapIdentifier(result);
+}
+
+int32_t MapReaderH3M::readHeroPortrait()
+{
+	HeroTypeID result(reader->readUInt8());
+
+	if(result.getNum() == features.heroIdentifierInvalid)
+		return int32_t(-1);
+
 	assert(result.getNum() < features.heroesPortraitsCount);
-	return remapIdentifier(result);;
+	return remapper.remapPortrrait(result);
 }
 
 CreatureID MapReaderH3M::readCreature()

+ 1 - 0
lib/mapping/MapReaderH3M.h

@@ -35,6 +35,7 @@ public:
 	ArtifactID readArtifact32();
 	CreatureID readCreature();
 	HeroTypeID readHero();
+	int32_t readHeroPortrait();
 	TerrainId readTerrain();
 	RoadId readRoad();
 	RiverId readRiver();