Преглед изворни кода

Merge pull request #4808 from Laserlicht/prism_breath

Bonus: prism breath
Ivan Savenko пре 11 месеци
родитељ
комит
db913d95e0

+ 3 - 1
Mods/vcmi/config/vcmi/english.json

@@ -687,5 +687,7 @@
 	"core.bonus.DISINTEGRATE.name": "Disintegrate",
 	"core.bonus.DISINTEGRATE.description": "No corpse remains after death",
 	"core.bonus.INVINCIBLE.name": "Invincible",
-	"core.bonus.INVINCIBLE.description": "Cannot be affected by anything"
+	"core.bonus.INVINCIBLE.description": "Cannot be affected by anything",
+	"core.bonus.PRISM_HEX_ATTACK_BREATH.name": "Prism Breath",
+	"core.bonus.PRISM_HEX_ATTACK_BREATH.description": "Prism Breath Attack (three directions)"
 }

+ 8 - 0
config/bonuses.json

@@ -548,6 +548,14 @@
 		}
 	},
 
+	"PRISM_HEX_ATTACK_BREATH":
+	{
+		"graphics":
+		{
+			"icon":  "zvs/Lib1.res/PrismBreath"
+		}
+	},
+
 	"THREE_HEADED_ATTACK":
 	{
 		"graphics":

+ 4 - 0
docs/modders/Bonus/Bonus_Types.md

@@ -502,6 +502,10 @@ Affected unit attacks all adjacent creatures (Hydra). Only directly targeted cre
 
 Affected unit attacks creature located directly behind targeted tile (Dragons). Only directly targeted creature will attempt to retaliate
 
+### PRISM_HEX_ATTACK_BREATH
+
+Like `TWO_HEX_ATTACK_BREATH` but affects also two additional cratures (in triangle form from target tile)
+
 ### RETURN_AFTER_STRIKE
 
 Affected unit can return to his starting location after attack (Harpies)

+ 29 - 17
lib/battle/CBattleInfoCallback.cpp

@@ -1392,7 +1392,7 @@ AttackableTiles CBattleInfoCallback::getPotentiallyAttackableHexes(
 				at.friendlyCreaturePositions.insert(tile);
 		}
 	}
-	else if(attacker->hasBonusOfType(BonusType::TWO_HEX_ATTACK_BREATH))
+	else if(attacker->hasBonusOfType(BonusType::TWO_HEX_ATTACK_BREATH) || attacker->hasBonusOfType(BonusType::PRISM_HEX_ATTACK_BREATH))
 	{
 		auto direction = BattleHex::mutualPosition(attackOriginHex, destinationTile);
 		
@@ -1404,27 +1404,39 @@ AttackableTiles CBattleInfoCallback::getPotentiallyAttackableHexes(
 			direction = BattleHex::mutualPosition(attackOriginHex, defender->occupiedHex(defenderPos));
 		}
 
-		if(direction != BattleHex::NONE) //only adjacent hexes are subject of dragon breath calculation
+		for(int i = 0; i < 3; i++)
 		{
-			BattleHex nextHex = destinationTile.cloneInDirection(direction, false);
-
-			if ( defender->doubleWide() )
+			if(direction != BattleHex::NONE) //only adjacent hexes are subject of dragon breath calculation
 			{
-				auto secondHex = destinationTile == defenderPos ? defender->occupiedHex(defenderPos) : defenderPos;
+				BattleHex nextHex = destinationTile.cloneInDirection(direction, false);
 
-				// if targeted double-wide creature is attacked from above or below ( -> second hex is also adjacent to attack origin)
-				// then dragon breath should target tile on the opposite side of targeted creature
-				if(BattleHex::mutualPosition(attackOriginHex, secondHex) != BattleHex::NONE)
-					nextHex = secondHex.cloneInDirection(direction, false);
-			}
+				if ( defender->doubleWide() )
+				{
+					auto secondHex = destinationTile == defenderPos ? defender->occupiedHex(defenderPos) : defenderPos;
 
-			if (nextHex.isValid())
-			{
-				//friendly stacks can also be damaged by Dragon Breath
-				const auto * st = battleGetUnitByPos(nextHex, true);
-				if(st != nullptr)
-					at.friendlyCreaturePositions.insert(nextHex);
+					// if targeted double-wide creature is attacked from above or below ( -> second hex is also adjacent to attack origin)
+					// then dragon breath should target tile on the opposite side of targeted creature
+					if(BattleHex::mutualPosition(attackOriginHex, secondHex) != BattleHex::NONE)
+						nextHex = secondHex.cloneInDirection(direction, false);
+				}
+
+				if (nextHex.isValid())
+				{
+					//friendly stacks can also be damaged by Dragon Breath
+					const auto * st = battleGetUnitByPos(nextHex, true);
+					if(st != nullptr)
+						at.friendlyCreaturePositions.insert(nextHex);
+				}
 			}
+
+			if(!attacker->hasBonusOfType(BonusType::PRISM_HEX_ATTACK_BREATH))
+				break;
+
+			// only needed for prism
+			int tmpDirection = static_cast<int>(direction) + 2;
+			if(tmpDirection > static_cast<int>(BattleHex::EDir::LEFT))
+				tmpDirection -= static_cast<int>(BattleHex::EDir::TOP);
+			direction = static_cast<BattleHex::EDir>(tmpDirection);
 		}
 	}
 	return at;

+ 1 - 0
lib/bonuses/BonusEnum.h

@@ -180,6 +180,7 @@ class JsonNode;
 	BONUS_NAME(RESOURCES_TOWN_MULTIPLYING_BOOST) /*Bonus that does not account for propagation and gives extra resources per day with amount multiplied by number of owned towns. val - base resource amount to be multiplied times number of owned towns, subtype - resource type*/ \
 	BONUS_NAME(DISINTEGRATE) /* after death no corpse remains */ \
 	BONUS_NAME(INVINCIBLE) /* cannot be target of attacks or spells */ \
+	BONUS_NAME(PRISM_HEX_ATTACK_BREATH) /*eg. dragons*/	\
 	/* end of list */