浏览代码

Merge pull request #5819 from Laserlicht/battle_anim

Using attack sprite
Ivan Savenko 3 月之前
父节点
当前提交
3817e1002b

+ 3 - 0
client/mapView/IMapRendererContext.h

@@ -56,6 +56,9 @@ public:
 	/// returns true if specified object is the currently active hero
 	virtual bool isActiveHero(const CGObjectInstance* obj) const = 0;
 
+	/// Returns moveDir of hero that attacked this wandering monster, or -1 on failure
+	virtual int attackedMonsterDirection(const CGObjectInstance * wanderingMonster) const = 0;
+
 	virtual size_t objectGroupIndex(ObjectInstanceID objectID) const = 0;
 	virtual Point objectImageOffset(ObjectInstanceID objectID, const int3 & coordinates) const = 0;
 

+ 28 - 4
client/mapView/MapRenderer.cpp

@@ -420,6 +420,19 @@ std::shared_ptr<CAnimation> MapRendererObjects::getAnimation(const AnimationPath
 	return ret;
 }
 
+std::shared_ptr<IImage> MapRendererObjects::getImage(const ImagePath & filename) const
+{
+	auto it = images.find(filename);
+
+	if(it != images.end())
+		return it->second;
+
+	auto ret = ENGINE->renderHandler().loadImage(filename, EImageBlitMode::SIMPLE);
+	images[filename] = ret;
+
+	return ret;
+}
+
 std::shared_ptr<CAnimation> MapRendererObjects::getFlagAnimation(const CGObjectInstance* obj)
 {
 	//TODO: relocate to config file?
@@ -456,7 +469,7 @@ std::shared_ptr<CAnimation> MapRendererObjects::getOverlayAnimation(const CGObje
 	return nullptr;
 }
 
-std::shared_ptr<IImage> MapRendererObjects::getImage(IMapRendererContext & context, const CGObjectInstance * obj, const std::shared_ptr<CAnimation>& animation) const
+std::shared_ptr<IImage> MapRendererObjects::getImageToRender(IMapRendererContext & context, const CGObjectInstance * obj, const std::shared_ptr<CAnimation>& animation) const
 {
 	if(!animation)
 		return nullptr;
@@ -465,6 +478,17 @@ std::shared_ptr<IImage> MapRendererObjects::getImage(IMapRendererContext & conte
 
 	if(animation->size(groupIndex) == 0)
 		return nullptr;
+	
+	auto attackerPos = context.attackedMonsterDirection(obj);
+	if(attackerPos != -1)
+	{
+		const auto * creature = dynamic_cast<const CArmedInstance *>(obj);
+		auto const & creatureType = LIBRARY->creh->objects[creature->appearance->subid];
+		auto dir = std::vector<int>({1, 2, 7, 8});
+		ImagePath imgPath = std::count(dir.begin(), dir.end(), attackerPos) ? creatureType->mapAttackFromRight : creatureType->mapAttackFromLeft;
+		if(!imgPath.empty())
+			return getImage(imgPath);
+	}
 
 	size_t frameIndex = context.objectImageIndex(obj->id, animation->size(groupIndex));
 
@@ -502,9 +526,9 @@ void MapRendererObjects::renderImage(IMapRendererContext & context, Canvas & tar
 
 void MapRendererObjects::renderObject(IMapRendererContext & context, Canvas & target, const int3 & coordinates, const CGObjectInstance * instance)
 {
-	renderImage(context, target, coordinates, instance, getImage(context, instance, getBaseAnimation(instance)));
-	renderImage(context, target, coordinates, instance, getImage(context, instance, getFlagAnimation(instance)));
-	renderImage(context, target, coordinates, instance, getImage(context, instance, getOverlayAnimation(instance)));
+	renderImage(context, target, coordinates, instance, getImageToRender(context, instance, getBaseAnimation(instance)));
+	renderImage(context, target, coordinates, instance, getImageToRender(context, instance, getFlagAnimation(instance)));
+	renderImage(context, target, coordinates, instance, getImageToRender(context, instance, getOverlayAnimation(instance)));
 }
 
 void MapRendererObjects::renderTile(IMapRendererContext & context, Canvas & target, const int3 & coordinates)

+ 3 - 1
client/mapView/MapRenderer.h

@@ -73,14 +73,16 @@ public:
 class MapRendererObjects
 {
 	std::map<AnimationPath, std::shared_ptr<CAnimation>> animations;
+	mutable std::map<ImagePath, std::shared_ptr<IImage>> images;
 
 	std::shared_ptr<CAnimation> getBaseAnimation(const CGObjectInstance * obj);
 	std::shared_ptr<CAnimation> getFlagAnimation(const CGObjectInstance * obj);
 	std::shared_ptr<CAnimation> getOverlayAnimation(const CGObjectInstance * obj);
 
 	std::shared_ptr<CAnimation> getAnimation(const AnimationPath & filename, bool generateMovementGroups, bool enableOverlay);
+	std::shared_ptr<IImage> getImage(const ImagePath & filename) const;
 
-	std::shared_ptr<IImage> getImage(IMapRendererContext & context, const CGObjectInstance * obj, const std::shared_ptr<CAnimation> & animation) const;
+	std::shared_ptr<IImage> getImageToRender(IMapRendererContext & context, const CGObjectInstance * obj, const std::shared_ptr<CAnimation> & animation) const;
 
 	void renderImage(IMapRendererContext & context, Canvas & target, const int3 & coordinates, const CGObjectInstance * object, const std::shared_ptr<IImage> & image);
 	void renderObject(IMapRendererContext & context, Canvas & target, const int3 & coordinates, const CGObjectInstance * obj);

+ 14 - 0
client/mapView/MapRendererContext.cpp

@@ -25,6 +25,8 @@
 #include "../../lib/spells/CSpellHandler.h"
 #include "../../lib/mapping/CMap.h"
 #include "../../lib/pathfinder/CGPathNode.h"
+#include "../../lib/battle/CPlayerBattleCallback.h"
+#include "../../lib/battle/IBattleState.h"
 
 MapRendererBaseContext::MapRendererBaseContext(const MapRendererContextState & viewState)
 	: viewState(viewState)
@@ -85,6 +87,18 @@ bool MapRendererBaseContext::isActiveHero(const CGObjectInstance * obj) const
 	return false;
 }
 
+int MapRendererBaseContext::attackedMonsterDirection(const CGObjectInstance * wanderingMonster) const
+{
+	if(wanderingMonster->ID != Obj::MONSTER)
+		return -1;
+		
+	for(auto & battle : GAME->interface()->cb->getActiveBattles())
+		if(wanderingMonster->pos == battle.second->getBattle()->getLocation())
+			return battle.second->getBattle()->getSideHero(BattleSide::ATTACKER)->moveDir;
+
+	return -1;
+}
+
 bool MapRendererBaseContext::tileAnimated(const int3 & coordinates) const
 {
 	return false;

+ 1 - 0
client/mapView/MapRendererContext.h

@@ -36,6 +36,7 @@ public:
 	bool tileAnimated(const int3 & coordinates) const override;
 
 	bool isActiveHero(const CGObjectInstance* obj) const override;
+	int attackedMonsterDirection(const CGObjectInstance * wanderingMonster) const override;
 
 	const TerrainTile & getMapTile(const int3 & coordinates) const override;
 	const MapObjectsList & getObjects(const int3 & coordinates) const override;

+ 10 - 0
client/renderSDL/RenderHandler.cpp

@@ -354,6 +354,16 @@ std::shared_ptr<IImage> RenderHandler::loadImage(const AnimationPath & path, int
 
 std::shared_ptr<IImage> RenderHandler::loadImage(const ImagePath & path, EImageBlitMode mode)
 {
+	auto name = path.getOriginalName();
+	
+	std::vector<std::string> splitted;
+	boost::split(splitted, name, boost::is_any_of(":"));
+	if(splitted.size() == 3)
+	{
+		ImageLocator locator = getLocatorForAnimationFrame(AnimationPath::builtin(splitted[0]), std::stoi(splitted[2]), std::stoi(splitted[1]), 1, mode);
+		return loadImage(locator);
+	}
+
 	ImageLocator locator(path, mode);
 	return loadImage(locator);
 }

+ 28 - 0
config/creatures/castle.json

@@ -14,6 +14,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:0",
+			"mapAttackFromLeft": "AvWattak.def:0:1",
 			"animation": "CPKMAN.DEF"
 		},
 		"sound" :
@@ -39,6 +41,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:2",
+			"mapAttackFromLeft": "AvWattak.def:0:3",
 			"animation": "CHALBD.DEF"
 		},
 		"sound" :
@@ -66,6 +70,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:4",
+			"mapAttackFromLeft": "AvWattak.def:0:5",
 			"animation": "CLCBOW.DEF",
 			"missile" :
 			{
@@ -103,6 +109,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:6",
+			"mapAttackFromLeft": "AvWattak.def:0:7",
 			"animation": "CHCBOW.DEF",
 			"missile" :
 			{
@@ -140,6 +148,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:8",
+			"mapAttackFromLeft": "AvWattak.def:0:9",
 			"animation": "CGRIFF.DEF"
 		},
 		"sound" :
@@ -169,6 +179,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:10",
+			"mapAttackFromLeft": "AvWattak.def:0:11",
 			"animation": "CRGRIF.DEF"
 		},
 		"sound" :
@@ -188,6 +200,8 @@
 		"upgrades": ["crusader"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:12",
+			"mapAttackFromLeft": "AvWattak.def:0:13",
 			"animation": "CSWORD.DEF"
 		},
 		"sound" :
@@ -214,6 +228,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:14",
+			"mapAttackFromLeft": "AvWattak.def:0:15",
 			"animation": "CCRUSD.DEF"
 		},
 		"sound" :
@@ -240,6 +256,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:16",
+			"mapAttackFromLeft": "AvWattak.def:0:17",
 			"animation": "CMONKK.DEF",
 			"missile" :
 			{
@@ -273,6 +291,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:18",
+			"mapAttackFromLeft": "AvWattak.def:0:19",
 			"animation": "CZEALT.DEF",
 			"missile" :
 			{
@@ -306,6 +326,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:20",
+			"mapAttackFromLeft": "AvWattak.def:0:21",
 			"animation": "CCAVLR.DEF"
 		},
 		"sound" :
@@ -333,6 +355,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:22",
+			"mapAttackFromLeft": "AvWattak.def:0:23",
 			"animation": "CCHAMP.DEF"
 		},
 		"sound" :
@@ -384,6 +408,8 @@
 		"upgrades": ["archangel"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:24",
+			"mapAttackFromLeft": "AvWattak.def:0:25",
 			"animation": "CANGEL.DEF"
 		},
 		"sound" :
@@ -451,6 +477,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:26",
+			"mapAttackFromLeft": "AvWattak.def:0:27",
 			"animation": "CRANGL.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/conflux.json

@@ -15,6 +15,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:236",
+			"mapAttackFromLeft": "AvWattak.def:0:237",
 			"animation": "CPIXIE.DEF"
 		},
 		"sound" :
@@ -44,6 +46,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:238",
+			"mapAttackFromLeft": "AvWattak.def:0:239",
 			"animation": "CSPRITE.DEF"
 		},
 		"sound" :
@@ -111,6 +115,8 @@
 		"upgrades": ["stormElemental"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:224",
+			"mapAttackFromLeft": "AvWattak.def:0:225",
 			"animation": "CAELEM.DEF"
 		},
 		"sound" :
@@ -196,6 +202,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:254",
+			"mapAttackFromLeft": "AvWattak.def:0:255",
 			"animation": "CSTORM.DEF",
 			"missile" :
 			{
@@ -285,6 +293,8 @@
 		"upgrades": ["iceElemental"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:230",
+			"mapAttackFromLeft": "AvWattak.def:0:231",
 			"animation": "CWELEM.DEF"
 		},
 		"sound" :
@@ -388,6 +398,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:246",
+			"mapAttackFromLeft": "AvWattak.def:0:247",
 			"animation": "CICEE.DEF",
 			"missile" :
 			{
@@ -452,6 +464,8 @@
 		"upgrades": ["energyElemental"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:228",
+			"mapAttackFromLeft": "AvWattak.def:0:229",
 			"animation": "CFELEM.DEF"
 		},
 		"sound" :
@@ -530,6 +544,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:258",
+			"mapAttackFromLeft": "AvWattak.def:0:259",
 			"animation": "CNRG.DEF"
 		},
 		"sound" :
@@ -593,6 +609,8 @@
 		"upgrades": ["magmaElemental"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:226",
+			"mapAttackFromLeft": "AvWattak.def:0:227",
 			"animation": "CEELEM.DEF"
 		},
 		"sound" :
@@ -671,6 +689,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:250",
+			"mapAttackFromLeft": "AvWattak.def:0:251",
 			"animation": "CSTONE.DEF"
 		},
 		"sound" :
@@ -710,6 +730,8 @@
 		"upgrades": ["magicElemental"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:240",
+			"mapAttackFromLeft": "AvWattak.def:0:241",
 			"animation": "CPSYEL.DEF"
 		},
 		"sound" :
@@ -749,6 +771,8 @@
 		"doubleWide" : false,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:242",
+			"mapAttackFromLeft": "AvWattak.def:0:243",
 			"animation": "CMAGEL.DEF"
 		},
 		"sound" :
@@ -790,6 +814,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:260",
+			"mapAttackFromLeft": "AvWattak.def:0:261",
 			"animation": "CFBIRD.DEF"
 		},
 		"sound" :
@@ -840,6 +866,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:262",
+			"mapAttackFromLeft": "AvWattak.def:0:263",
 			"animation": "CPHX.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/dungeon.json

@@ -21,6 +21,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:140",
+			"mapAttackFromLeft": "AvWattak.def:0:141",
 			"animation": "CTROGL.DEF"
 		},
 		"sound" :
@@ -52,6 +54,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:142",
+			"mapAttackFromLeft": "AvWattak.def:0:143",
 			"animation": "CITROG.DEF"
 		},
 		"sound" :
@@ -83,6 +87,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:144",
+			"mapAttackFromLeft": "AvWattak.def:0:145",
 			"animation": "CHARPY.DEF"
 		},
 		"sound" :
@@ -116,6 +122,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:146",
+			"mapAttackFromLeft": "AvWattak.def:0:147",
 			"animation": "CHARPH.DEF"
 		},
 		"sound" :
@@ -148,6 +156,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:148",
+			"mapAttackFromLeft": "AvWattak.def:0:149",
 			"animation": "CBEHOL.DEF",
 			"missile" :
 			{
@@ -190,6 +200,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:150",
+			"mapAttackFromLeft": "AvWattak.def:0:151",
 			"animation": "CEVEYE.DEF",
 			"missile" :
 			{
@@ -241,6 +253,8 @@
 		"upgrades": ["medusaQueen"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:152",
+			"mapAttackFromLeft": "AvWattak.def:0:153",
 			"animation": "CMEDUS.DEF",
 			"missile" :
 			{
@@ -284,6 +298,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:154",
+			"mapAttackFromLeft": "AvWattak.def:0:155",
 			"animation": "CMEDUQ.DEF",
 			"missile" :
 			{
@@ -317,6 +333,8 @@
 		"upgrades": ["minotaurKing"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:156",
+			"mapAttackFromLeft": "AvWattak.def:0:157",
 			"animation": "CMINOT.DEF"
 		},
 		"sound" :
@@ -344,6 +362,8 @@
 		 },
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:158",
+			"mapAttackFromLeft": "AvWattak.def:0:159",
 			"animation": "CMINOK.DEF"
 		},
 		"sound" :
@@ -372,6 +392,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:160",
+			"mapAttackFromLeft": "AvWattak.def:0:161",
 			"animation": "CMCORE.DEF"
 		},
 		"sound" :
@@ -405,6 +427,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:162",
+			"mapAttackFromLeft": "AvWattak.def:0:163",
 			"animation": "CCMCOR.DEF"
 		},
 		"sound" :
@@ -456,6 +480,8 @@
 		"upgrades": ["blackDragon"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:164",
+			"mapAttackFromLeft": "AvWattak.def:0:165",
 			"animation": "CRDRGN.DEF"
 		},
 		"sound" :
@@ -511,6 +537,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:166",
+			"mapAttackFromLeft": "AvWattak.def:0:167",
 			"animation": "CBDRGN.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/fortress.json

@@ -7,6 +7,8 @@
 		"upgrades": ["gnollMarauder"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:196",
+			"mapAttackFromLeft": "AvWattak.def:0:197",
 			"animation": "CGNOLL.DEF"
 		},
 		"sound" :
@@ -25,6 +27,8 @@
 		"faction": "fortress",
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:198",
+			"mapAttackFromLeft": "AvWattak.def:0:199",
 			"animation": "CGNOLM.DEF"
 		},
 		"sound" :
@@ -54,6 +58,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:200",
+			"mapAttackFromLeft": "AvWattak.def:0:201",
 			"animation": "CPLIZA.DEF",
 			"missile" :
 			{
@@ -85,6 +91,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:202",
+			"mapAttackFromLeft": "AvWattak.def:0:203",
 			"animation": "CALIZA.DEF",
 			"missile" :
 			{
@@ -124,6 +132,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:208",
+			"mapAttackFromLeft": "AvWattak.def:0:209",
 			"animation": "CDRFLY.DEF"
 		},
 		"sound" :
@@ -161,6 +171,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:210",
+			"mapAttackFromLeft": "AvWattak.def:0:211",
 			"animation": "CDRFIR.DEF"
 		},
 		"sound" :
@@ -191,6 +203,8 @@
 		"upgrades": ["greaterBasilisk"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:212",
+			"mapAttackFromLeft": "AvWattak.def:0:213",
 			"animation": "CBASIL.DEF"
 		},
 		"sound" :
@@ -219,6 +233,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:214",
+			"mapAttackFromLeft": "AvWattak.def:0:215",
 			"animation": "CGBASI.DEF"
 		},
 		"sound" :
@@ -239,6 +255,8 @@
 		"doubleWide" : true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:204",
+			"mapAttackFromLeft": "AvWattak.def:0:205",
 			"animation": "CCGORG.DEF"
 		},
 		"sound" :
@@ -267,6 +285,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:206",
+			"mapAttackFromLeft": "AvWattak.def:0:207",
 			"animation": "CBGOG.DEF"
 		},
 		"sound" :
@@ -294,6 +314,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:216",
+			"mapAttackFromLeft": "AvWattak.def:0:217",
 			"animation": "CWYVER.DEF"
 		},
 		"sound" :
@@ -326,6 +348,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:218",
+			"mapAttackFromLeft": "AvWattak.def:0:219",
 			"animation": "CWYVMN.DEF"
 		},
 		"sound" :
@@ -367,6 +391,8 @@
 		"upgrades": ["chaosHydra"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:220",
+			"mapAttackFromLeft": "AvWattak.def:0:221",
 			"animation": "CHYDRA.DEF"
 		},
 		"sound" :
@@ -407,6 +433,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:222",
+			"mapAttackFromLeft": "AvWattak.def:0:223",
 			"animation": "CCHYDR.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/inferno.json

@@ -7,6 +7,8 @@
 		"upgrades": ["familiar"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:84",
+			"mapAttackFromLeft": "AvWattak.def:0:85",
 			"animation": "CIMP.DEF"
 		},
 		"sound" :
@@ -33,6 +35,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:86",
+			"mapAttackFromLeft": "AvWattak.def:0:87",
 			"animation": "CFAMIL.DEF"
 		},
 		"sound" :
@@ -61,6 +65,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:88",
+			"mapAttackFromLeft": "AvWattak.def:0:89",
 			"animation": "CGOG.DEF",
 			"missile" :
 			{
@@ -97,6 +103,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:90",
+			"mapAttackFromLeft": "AvWattak.def:0:91",
 			"animation": "CMAGOG.DEF",
 			"missile" :
 			{
@@ -122,6 +130,8 @@
 		"doubleWide" : true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:92",
+			"mapAttackFromLeft": "AvWattak.def:0:93",
 			"animation": "CHHOUN.DEF"
 		},
 		"sound" :
@@ -152,6 +162,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:94",
+			"mapAttackFromLeft": "AvWattak.def:0:95",
 			"animation": "CCERBU.DEF"
 		},
 		"sound" :
@@ -171,6 +183,8 @@
 		"upgrades": ["hornedDemon"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:96",
+			"mapAttackFromLeft": "AvWattak.def:0:97",
 			"animation": "COHDEM.DEF"
 		},
 		"sound" :
@@ -189,6 +203,8 @@
 		"faction": "inferno",
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:98",
+			"mapAttackFromLeft": "AvWattak.def:0:99",
 			"animation": "CTHDEM.DEF"
 		},
 		"sound" :
@@ -208,6 +224,8 @@
 		"upgrades": ["pitLord"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:100",
+			"mapAttackFromLeft": "AvWattak.def:0:101",
 			"animation": "CPFIEN.DEF"
 		},
 		"sound" :
@@ -246,6 +264,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:102",
+			"mapAttackFromLeft": "AvWattak.def:0:103",
 			"animation": "CPFOE.DEF"
 		},
 		"sound" :
@@ -289,6 +309,8 @@
 		"upgrades": ["efreetSultan"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:104",
+			"mapAttackFromLeft": "AvWattak.def:0:105",
 			"animation": "CEFREE.DEF"
 		},
 		"sound" :
@@ -336,6 +358,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:106",
+			"mapAttackFromLeft": "AvWattak.def:0:107",
 			"animation": "CEFRES.DEF"
 		},
 		"sound" :
@@ -396,6 +420,8 @@
 		"upgrades": ["archDevil"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:108",
+			"mapAttackFromLeft": "AvWattak.def:0:109",
 			"animation": "CDEVIL.DEF"
 		},
 		"sound" :
@@ -456,6 +482,8 @@
 		"graphics" :
 		{
 			"missile" : null,
+			"mapAttackFromRight": "AvWattak.def:0:110",
+			"mapAttackFromLeft": "AvWattak.def:0:111",
 			"animation": "CADEVL.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/necropolis.json

@@ -14,6 +14,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:112",
+			"mapAttackFromLeft": "AvWattak.def:0:113",
 			"animation": "CSKELE.DEF"
 		},
 		"sound" :
@@ -39,6 +41,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:114",
+			"mapAttackFromLeft": "AvWattak.def:0:115",
 			"animation": "CWSKEL.DEF"
 		},
 		"sound" :
@@ -66,6 +70,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:116",
+			"mapAttackFromLeft": "AvWattak.def:0:117",
 			"animation": "CZOMBI.DEF"
 		},
 		"sound" :
@@ -84,6 +90,8 @@
 		"faction": "necropolis",
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:118",
+			"mapAttackFromLeft": "AvWattak.def:0:119",
 			"animation": "CZOMLO.DEF"
 		},
 		"sound" :
@@ -133,6 +141,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:120",
+			"mapAttackFromLeft": "AvWattak.def:0:121",
 			"animation": "CWIGHT.DEF"
 		},
 		"sound" :
@@ -172,6 +182,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:122",
+			"mapAttackFromLeft": "AvWattak.def:0:123",
 			"animation": "CWRAIT.DEF"
 		},
 		"sound" :
@@ -206,6 +218,8 @@
 		"upgrades": ["vampireLord"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:124",
+			"mapAttackFromLeft": "AvWattak.def:0:125",
 			"animation": "CVAMP.DEF"
 		},
 		"sound" :
@@ -246,6 +260,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:126",
+			"mapAttackFromLeft": "AvWattak.def:0:127",
 			"animation": "CNOSFE.DEF"
 		},
 		"sound" :
@@ -285,6 +301,8 @@
 		"upgrades": ["powerLich"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:128",
+			"mapAttackFromLeft": "AvWattak.def:0:129",
 			"animation": "CLICH.DEF",
 			"missile" :
 			{
@@ -325,6 +343,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:130",
+			"mapAttackFromLeft": "AvWattak.def:0:131",
 			"animation": "CPLICH.DEF",
 			"missile" :
 			{
@@ -363,6 +383,8 @@
 		"upgrades": ["dreadKnight"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:132",
+			"mapAttackFromLeft": "AvWattak.def:0:133",
 			"animation": "CBKNIG.DEF"
 		},
 		"sound" :
@@ -400,6 +422,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:134",
+			"mapAttackFromLeft": "AvWattak.def:0:135",
 			"animation": "CBLORD.DEF"
 		},
 		"sound" :
@@ -450,6 +474,8 @@
 		"upgrades": ["ghostDragon"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:136",
+			"mapAttackFromLeft": "AvWattak.def:0:137",
 			"animation": "CNDRGN.DEF"
 		},
 		"sound" :
@@ -505,6 +531,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:138",
+			"mapAttackFromLeft": "AvWattak.def:0:139",
 			"animation": "CHDRGN.DEF"
 		},
 		"sound" :

+ 30 - 0
config/creatures/neutral.json

@@ -20,6 +20,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:232",
+			"mapAttackFromLeft": "AvWattak.def:0:233",
 			"animation": "CGGOLE.DEF"
 		},
 		"sound" :
@@ -51,6 +53,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:234",
+			"mapAttackFromLeft": "AvWattak.def:0:235",
 			"animation": "CDGOLE.DEF"
 		},
 		"sound" :
@@ -124,6 +128,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:264",
+			"mapAttackFromLeft": "AvWattak.def:0:265",
 			"animation": "CADRGN.DEF"
 		},
 		"sound" :
@@ -170,6 +176,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:266",
+			"mapAttackFromLeft": "AvWattak.def:0:267",
 			"animation": "CCDRGN.DEF"
 		},
 		"sound" :
@@ -282,6 +290,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:268",
+			"mapAttackFromLeft": "AvWattak.def:0:269",
 			"animation": "CFDRGN.DEF"
 		},
 		"sound" :
@@ -340,6 +350,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:270",
+			"mapAttackFromLeft": "AvWattak.def:0:271",
 			"animation": "CRSDGN.DEF"
 		},
 		"sound" :
@@ -423,6 +435,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:272",
+			"mapAttackFromLeft": "AvWattak.def:0:273",
 			"animation": "Cench.DEF",
 			"missile" :
 			{
@@ -464,6 +478,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:274",
+			"mapAttackFromLeft": "AvWattak.def:0:275",
 			"animation": "CSHARP.DEF",
 			"missile" :
 			{
@@ -501,6 +517,8 @@
 		 },
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:276",
+			"mapAttackFromLeft": "AvWattak.def:0:277",
 			"animation": "CHALF.DEF",
 			"missile" :
 			{
@@ -524,6 +542,8 @@
 		"faction": "neutral",
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:278",
+			"mapAttackFromLeft": "AvWattak.def:0:279",
 			"animation": "CPEAS.DEF"
 		},
 		"sound" :
@@ -543,6 +563,8 @@
 		"doubleWide" : true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:280",
+			"mapAttackFromLeft": "AvWattak.def:0:281",
 			"animation": "CBOAR.DEF"
 		},
 		"sound" :
@@ -574,6 +596,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:282",
+			"mapAttackFromLeft": "AvWattak.def:0:283",
 			"animation": "CMUMMY.DEF"
 		},
 		"sound" :
@@ -602,6 +626,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:284",
+			"mapAttackFromLeft": "AvWattak.def:0:285",
 			"animation": "CNOMAD.DEF"
 		},
 		"sound" :
@@ -647,6 +673,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:286",
+			"mapAttackFromLeft": "AvWattak.def:0:287",
 			"animation": "CROGUE.DEF"
 		},
 		"sound" :
@@ -673,6 +701,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:288",
+			"mapAttackFromLeft": "AvWattak.def:0:289",
 			"animation": "CTROLL.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/rampart.json

@@ -10,6 +10,8 @@
 		"graphics" :
 		{
 			"missile" : null,
+			"mapAttackFromRight": "AvWattak.def:0:28",
+			"mapAttackFromLeft": "AvWattak.def:0:29",
 			"animation": "CCENTR.DEF"
 		},
 		"sound" :
@@ -31,6 +33,8 @@
 		"graphics" :
 		{
 			"missile" : null,
+			"mapAttackFromRight": "AvWattak.def:0:30",
+			"mapAttackFromLeft": "AvWattak.def:0:31",
 			"animation": "CECENT.DEF"
 		},
 		"sound" :
@@ -58,6 +62,8 @@
 		"upgrades": ["battleDwarf"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:32",
+			"mapAttackFromLeft": "AvWattak.def:0:33",
 			"animation": "CDWARF.DEF"
 		},
 		"sound" :
@@ -84,6 +90,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:34",
+			"mapAttackFromLeft": "AvWattak.def:0:35",
 			"animation": "CBDWAR.DEF"
 		},
 		"sound" :
@@ -111,6 +119,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:36",
+			"mapAttackFromLeft": "AvWattak.def:0:37",
 			"animation": "CELF.DEF",
 			"missile" :
 			{
@@ -149,6 +159,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:38",
+			"mapAttackFromLeft": "AvWattak.def:0:39",
 			"animation": "CGRELF.DEF",
 			"missile" :
 			{
@@ -187,6 +199,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:40",
+			"mapAttackFromLeft": "AvWattak.def:0:41",
 			"animation": "CPEGAS.DEF"
 		},
 		"sound" :
@@ -218,6 +232,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:42",
+			"mapAttackFromLeft": "AvWattak.def:0:43",
 			"animation": "CAPEGS.DEF"
 		},
 		"sound" :
@@ -246,6 +262,8 @@
 		"upgrades": ["dendroidSoldier"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:44",
+			"mapAttackFromLeft": "AvWattak.def:0:45",
 			"animation": "CTREE.DEF"
 		},
 		"sound" :
@@ -273,6 +291,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:46",
+			"mapAttackFromLeft": "AvWattak.def:0:47",
 			"animation": "CBTREE.DEF"
 		},
 		"sound" :
@@ -308,6 +328,8 @@
 		"upgrades": ["warUnicorn"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:48",
+			"mapAttackFromLeft": "AvWattak.def:0:49",
 			"animation": "CUNICO.DEF"
 		},
 		"sound" :
@@ -342,6 +364,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:50",
+			"mapAttackFromLeft": "AvWattak.def:0:51",
 			"animation": "CWUNIC.DEF"
 		},
 		"sound" :
@@ -393,6 +417,8 @@
 		"upgrades": ["goldDragon"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:52",
+			"mapAttackFromLeft": "AvWattak.def:0:53",
 			"animation": "CGDRAG.DEF"
 		},
 		"sound" :
@@ -442,6 +468,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:54",
+			"mapAttackFromLeft": "AvWattak.def:0:55",
 			"animation": "CDDRAG.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/stronghold.json

@@ -8,6 +8,8 @@
 		"upgrades": ["hobgoblin"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:168",
+			"mapAttackFromLeft": "AvWattak.def:0:169",
 			"animation": "CGOBLI.DEF"
 		},
 		"sound" :
@@ -27,6 +29,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:170",
+			"mapAttackFromLeft": "AvWattak.def:0:171",
 			"animation": "CHGOBL.DEF"
 		},
 		"sound" :
@@ -48,6 +52,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:172",
+			"mapAttackFromLeft": "AvWattak.def:0:173",
 			"animation": "CBWLFR.DEF"
 		},
 		"sound" :
@@ -75,6 +81,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:174",
+			"mapAttackFromLeft": "AvWattak.def:0:175",
 			"animation": "CUWLFR.DEF"
 		},
 		"sound" :
@@ -102,6 +110,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:176",
+			"mapAttackFromLeft": "AvWattak.def:0:177",
 			"animation": "CORC.DEF",
 			"missile" :
 			{
@@ -133,6 +143,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:178",
+			"mapAttackFromLeft": "AvWattak.def:0:179",
 			"animation": "CORCCH.DEF",
 			"missile" :
 			{
@@ -157,6 +169,8 @@
 		"upgrades": ["ogreMage"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:180",
+			"mapAttackFromLeft": "AvWattak.def:0:181",
 			"animation": "COGRE.DEF"
 		},
 		"sound" :
@@ -194,6 +208,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:182",
+			"mapAttackFromLeft": "AvWattak.def:0:183",
 			"animation": "COGMAG.DEF"
 		},
 		"sound" :
@@ -222,6 +238,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:184",
+			"mapAttackFromLeft": "AvWattak.def:0:185",
 			"animation": "CROC.DEF"
 		},
 		"sound" :
@@ -260,6 +278,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:186",
+			"mapAttackFromLeft": "AvWattak.def:0:187",
 			"animation": "CTBIRD.DEF"
 		},
 		"sound" :
@@ -292,6 +312,8 @@
 		"upgrades": ["cyclopKing"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:188",
+			"mapAttackFromLeft": "AvWattak.def:0:189",
 			"animation": "CCYCLR.DEF",
 			"missile" :
 			{
@@ -335,6 +357,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:190",
+			"mapAttackFromLeft": "AvWattak.def:0:191",
 			"animation": "CCYCLLOR.DEF",
 			"missile" :
 			{
@@ -373,6 +397,8 @@
 		"upgrades": ["ancientBehemoth"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:192",
+			"mapAttackFromLeft": "AvWattak.def:0:193",
 			"animation": "CYBEHE.DEF"
 		},
 		"sound" :
@@ -405,6 +431,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:194",
+			"mapAttackFromLeft": "AvWattak.def:0:195",
 			"animation": "CABEHE.DEF"
 		},
 		"sound" :

+ 28 - 0
config/creatures/tower.json

@@ -9,6 +9,8 @@
 		"hasDoubleWeek": true,
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:56",
+			"mapAttackFromLeft": "AvWattak.def:0:57",
 			"animation": "CGREMA.DEF"
 		},
 		"sound" :
@@ -36,6 +38,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:58",
+			"mapAttackFromLeft": "AvWattak.def:0:59",
 			"animation": "CGREMM.DEF",
 			"missile" :
 			{
@@ -71,6 +75,8 @@
 		"upgrades": ["obsidianGargoyle"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:60",
+			"mapAttackFromLeft": "AvWattak.def:0:61",
 			"animation": "CGARGO.DEF"
 		},
 		"sound" :
@@ -100,6 +106,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:62",
+			"mapAttackFromLeft": "AvWattak.def:0:63",
 			"animation": "COGARG.DEF"
 		},
 		"sound" :
@@ -132,6 +140,8 @@
 		"upgrades": ["stoneGolem"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:64",
+			"mapAttackFromLeft": "AvWattak.def:0:65",
 			"animation": "CSGOLE.DEF"
 		},
 		"sound" :
@@ -163,6 +173,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:66",
+			"mapAttackFromLeft": "AvWattak.def:0:67",
 			"animation": "CIGOLE.DEF"
 		},
 		"sound" :
@@ -199,6 +211,8 @@
 		"upgrades": ["archMage"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:68",
+			"mapAttackFromLeft": "AvWattak.def:0:69",
 			"animation": "CMAGE.DEF",
 			"missile" :
 			{
@@ -243,6 +257,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:70",
+			"mapAttackFromLeft": "AvWattak.def:0:71",
 			"animation": "CAMAGE.DEF",
 			"missile" :
 			{
@@ -294,6 +310,8 @@
 		"upgrades": ["masterGenie"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:72",
+			"mapAttackFromLeft": "AvWattak.def:0:73",
 			"animation": "CGENIE.DEF"
 		},
 		"sound" :
@@ -346,6 +364,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:74",
+			"mapAttackFromLeft": "AvWattak.def:0:75",
 			"animation": "CSULTA.DEF"
 		},
 		"sound" :
@@ -374,6 +394,8 @@
 		"upgrades": ["nagaQueen"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:76",
+			"mapAttackFromLeft": "AvWattak.def:0:77",
 			"animation": "CNAGA.DEF"
 		},
 		"sound" :
@@ -400,6 +422,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:78",
+			"mapAttackFromLeft": "AvWattak.def:0:79",
 			"animation": "CNAGAG.DEF"
 		},
 		"sound" :
@@ -431,6 +455,8 @@
 		"upgrades": ["titan"],
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:80",
+			"mapAttackFromLeft": "AvWattak.def:0:81",
 			"animation": "CLTITA.DEF"
 		},
 		"sound" :
@@ -476,6 +502,8 @@
 		},
 		"graphics" :
 		{
+			"mapAttackFromRight": "AvWattak.def:0:82",
+			"mapAttackFromLeft": "AvWattak.def:0:83",
 			"animation": "CGTITA.DEF",
 			"missile" :
 			{

+ 10 - 0
config/schemas/creature.json

@@ -153,6 +153,16 @@
 					"items" : { "type" : "string" },
 					"description" : "Object mask that describes on which tiles object is visible/blocked/activatable"
 				},
+				"mapAttackFromLeft" : {
+					"type" : "string",
+					"description" : "Adventure map creature image when attacked from left",
+					"format" : "imageFile"
+				},
+				"mapAttackFromRight" : {
+					"type" : "string",
+					"description" : "Adventure map creature image when attacked from right",
+					"format" : "imageFile"
+				},
 				"iconLarge" : {
 					"type" : "string",
 					"description" : "Large icon for this creature, used for example in town screen",

+ 4 - 0
docs/modders/Entities_Format/Creature_Format.md

@@ -128,6 +128,10 @@ In order to make functional creature you also need:
 		"iconSmall" : "",
 		// Large icon for this creature, used for example in town screen
 		"iconLarge" : "",
+
+		// Optional. Images of creatures when attacked on adventure map
+		"mapAttackFromRight": "",
+		"mapAttackFromLeft": "",
 		
 		// animation parameters
 

+ 2 - 0
lib/CCreatureHandler.cpp

@@ -902,6 +902,8 @@ void CCreatureHandler::loadJsonAnimation(CCreature * cre, const JsonNode & graph
 void CCreatureHandler::loadCreatureJson(CCreature * creature, const JsonNode & config) const
 {
 	creature->animDefName = AnimationPath::fromJson(config["graphics"]["animation"]);
+	creature->mapAttackFromLeft = ImagePath::fromJson(config["graphics"]["mapAttackFromLeft"]);
+	creature->mapAttackFromRight = ImagePath::fromJson(config["graphics"]["mapAttackFromRight"]);
 
 	for(const auto & ability : config["abilities"].Struct())
 	{

+ 2 - 0
lib/CCreatureHandler.h

@@ -67,6 +67,8 @@ public:
 	std::set<CreatureID> upgrades; // IDs of creatures to which this creature can be upgraded
 
 	AnimationPath animDefName; // creature animation used during battles
+	ImagePath mapAttackFromLeft; // adventure map creature image when attacked from left
+	ImagePath mapAttackFromRight; // adventure map creature image when attacked from right
 
 	si32 iconIndex = -1; // index of icon in files like twcrport, used in tests now.
 	/// names of files with appropriate icons. Used only during loading

+ 5 - 0
lib/callback/CBattleCallback.cpp

@@ -79,6 +79,11 @@ void CBattleCallback::onBattleEnded(const BattleID & battleID)
 	activeBattles.erase(battleID);
 }
 
+std::map<BattleID, std::shared_ptr<CPlayerBattleCallback>> CBattleCallback::getActiveBattles()
+{
+	return activeBattles;
+}
+
 void CBattleCallback::battleMakeSpellAction(const BattleID & battleID, const BattleAction & action)
 {
 	assert(action.actionType == EActionType::HERO_SPELL);

+ 1 - 0
lib/callback/CBattleCallback.h

@@ -39,6 +39,7 @@ public:
 
 	void onBattleStarted(const IBattleInfo * info);
 	void onBattleEnded(const BattleID & battleID);
+	std::map<BattleID, std::shared_ptr<CPlayerBattleCallback>> getActiveBattles();
 };
 
 VCMI_LIB_NAMESPACE_END