mirror of
https://github.com/correl/mage.git
synced 2024-12-25 11:11:16 +00:00
* Phyrexian Unlife - Fixed that damage from a combat damage step was not handled as if all damage was dealt at once. This could cause a wrong mix of damage and poison conters.
This commit is contained in:
parent
3ee609d98b
commit
53964ee80c
4 changed files with 54 additions and 19 deletions
|
@ -80,6 +80,9 @@ public class PhyrexianUnlife extends CardImpl {
|
|||
|
||||
class PhyrexianUnlifeEffect2 extends ReplacementEffectImpl {
|
||||
|
||||
int lastCheckedDamageStepNum = 0;
|
||||
boolean startedWithLifeAboveZero = false;
|
||||
|
||||
public PhyrexianUnlifeEffect2() {
|
||||
super(Duration.WhileOnBattlefield, Outcome.Benefit);
|
||||
staticText = "As long as you have 0 or less life, all damage is dealt to you as though its source had infect";
|
||||
|
@ -87,6 +90,8 @@ class PhyrexianUnlifeEffect2 extends ReplacementEffectImpl {
|
|||
|
||||
public PhyrexianUnlifeEffect2(final PhyrexianUnlifeEffect2 effect) {
|
||||
super(effect);
|
||||
this.lastCheckedDamageStepNum = effect.lastCheckedDamageStepNum;
|
||||
this.startedWithLifeAboveZero = effect.startedWithLifeAboveZero;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -119,11 +124,25 @@ class PhyrexianUnlifeEffect2 extends ReplacementEffectImpl {
|
|||
@Override
|
||||
public boolean applies(GameEvent event, Ability source, Game game) {
|
||||
if (event.getType() == EventType.DAMAGE_PLAYER && event.getPlayerId().equals(source.getControllerId())) {
|
||||
Player player = game.getPlayer(event.getPlayerId());
|
||||
if (player.getLife() <= 0) {
|
||||
return true;
|
||||
Player player = game.getPlayer(source.getControllerId());
|
||||
if (player != null) {
|
||||
// The decision if the player has more than 0 life has to be checked only at start of a combat damage step
|
||||
// and all damage in the same step has to be handled the same beause by the rules it's all done at once
|
||||
if (((DamagePlayerEvent) event).isCombatDamage()) {
|
||||
if (lastCheckedDamageStepNum != game.getState().getStepNum()) {
|
||||
lastCheckedDamageStepNum = game.getState().getStepNum();
|
||||
startedWithLifeAboveZero = player.getLife() > 0;
|
||||
}
|
||||
if (startedWithLifeAboveZero) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
if (player.getLife() <= 0) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -105,6 +105,7 @@ public class GameState implements Serializable, Copyable<GameState> {
|
|||
private Exile exile;
|
||||
private Battlefield battlefield;
|
||||
private int turnNum = 1;
|
||||
private int stepNum = 0;
|
||||
private UUID turnId = null;
|
||||
private boolean extraTurn = false;
|
||||
private boolean legendaryRuleActive = true;
|
||||
|
@ -149,6 +150,7 @@ public class GameState implements Serializable, Copyable<GameState> {
|
|||
this.lookedAt.putAll(state.lookedAt);
|
||||
this.battlefield = state.battlefield.copy();
|
||||
this.turnNum = state.turnNum;
|
||||
this.stepNum = state.stepNum;
|
||||
this.extraTurn = state.extraTurn;
|
||||
this.legendaryRuleActive = state.legendaryRuleActive;
|
||||
this.gameOver = state.gameOver;
|
||||
|
@ -351,6 +353,19 @@ public class GameState implements Serializable, Copyable<GameState> {
|
|||
return combat;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the game step counter. This counter isgoing one up for
|
||||
* every played step during the game.
|
||||
* @return
|
||||
*/
|
||||
public int getStepNum() {
|
||||
return stepNum;
|
||||
}
|
||||
|
||||
public void increaseStepNum() {
|
||||
this.stepNum++;
|
||||
}
|
||||
|
||||
public int getTurnNum() {
|
||||
return turnNum;
|
||||
}
|
||||
|
@ -695,6 +710,7 @@ public class GameState implements Serializable, Copyable<GameState> {
|
|||
revealed.clear();
|
||||
lookedAt.clear();
|
||||
turnNum = 0;
|
||||
stepNum = 0;
|
||||
extraTurn = false;
|
||||
legendaryRuleActive = true;
|
||||
gameOver = false;
|
||||
|
|
|
@ -53,11 +53,11 @@ import mage.util.Copyable;
|
|||
*/
|
||||
public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
||||
|
||||
protected List<UUID> attackers = new ArrayList<UUID>();
|
||||
protected List<UUID> blockers = new ArrayList<UUID>();
|
||||
protected List<UUID> blockerOrder = new ArrayList<UUID>();
|
||||
protected List<UUID> attackerOrder = new ArrayList<UUID>();
|
||||
protected Map<UUID, UUID> players = new HashMap<UUID, UUID>();
|
||||
protected List<UUID> attackers = new ArrayList<>();
|
||||
protected List<UUID> blockers = new ArrayList<>();
|
||||
protected List<UUID> blockerOrder = new ArrayList<>();
|
||||
protected List<UUID> attackerOrder = new ArrayList<>();
|
||||
protected Map<UUID, UUID> players = new HashMap<>();
|
||||
protected boolean blocked;
|
||||
protected UUID defenderId; // planeswalker or player
|
||||
protected UUID defendingPlayerId;
|
||||
|
@ -274,7 +274,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
int damage = getDamageValueFromPermanent(attacker, game);
|
||||
if (canDamage(attacker, first)) {
|
||||
// must be set before attacker damage marking because of effects like Test of Faith
|
||||
Map<UUID, Integer> blockerPower = new HashMap<UUID, Integer>();
|
||||
Map<UUID, Integer> blockerPower = new HashMap<>();
|
||||
for (UUID blockerId: blockerOrder) {
|
||||
Permanent blocker = game.getPermanent(blockerId);
|
||||
if (canDamage(blocker, first)) {
|
||||
|
@ -283,7 +283,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
}
|
||||
}
|
||||
}
|
||||
Map<UUID, Integer> assigned = new HashMap<UUID, Integer>();
|
||||
Map<UUID, Integer> assigned = new HashMap<>();
|
||||
if (blocked) {
|
||||
for (UUID blockerId: blockerOrder) {
|
||||
Permanent blocker = game.getPermanent(blockerId);
|
||||
|
@ -316,8 +316,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
Permanent blocker = game.getPermanent(entry.getKey());
|
||||
blocker.markDamage(entry.getValue(), attacker.getId(), game, true, true);
|
||||
}
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
for (UUID blockerId: blockerOrder) {
|
||||
Permanent blocker = game.getPermanent(blockerId);
|
||||
if (canDamage(blocker, first)) {
|
||||
|
@ -365,7 +364,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
int damage = getDamageValueFromPermanent(blocker, game);
|
||||
|
||||
if (canDamage(blocker, first)) {
|
||||
Map<UUID, Integer> assigned = new HashMap<UUID, Integer>();
|
||||
Map<UUID, Integer> assigned = new HashMap<>();
|
||||
for (UUID attackerId: attackerOrder) {
|
||||
Permanent attacker = game.getPermanent(attackerId);
|
||||
int lethalDamage;
|
||||
|
@ -437,7 +436,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
return;
|
||||
}
|
||||
Player player = game.getPlayer(playerId);
|
||||
List<UUID> blockerList = new ArrayList<UUID>(blockers);
|
||||
List<UUID> blockerList = new ArrayList<>(blockers);
|
||||
blockerOrder.clear();
|
||||
while (true) {
|
||||
if (blockerList.size() == 1) {
|
||||
|
@ -445,7 +444,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
break;
|
||||
}
|
||||
else {
|
||||
List<Permanent> blockerPerms = new ArrayList<Permanent>();
|
||||
List<Permanent> blockerPerms = new ArrayList<>();
|
||||
for (UUID blockerId: blockerList) {
|
||||
blockerPerms.add(game.getPermanent(blockerId));
|
||||
}
|
||||
|
@ -461,7 +460,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
return;
|
||||
}
|
||||
Player player = game.getPlayer(playerId);
|
||||
List<UUID> attackerList = new ArrayList<UUID>(attackers);
|
||||
List<UUID> attackerList = new ArrayList<>(attackers);
|
||||
attackerOrder.clear();
|
||||
while (true) {
|
||||
if (attackerList.size() == 1) {
|
||||
|
@ -469,7 +468,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
break;
|
||||
}
|
||||
else {
|
||||
List<Permanent> attackerPerms = new ArrayList<Permanent>();
|
||||
List<Permanent> attackerPerms = new ArrayList<>();
|
||||
for (UUID attackerId: attackerList) {
|
||||
attackerPerms.add(game.getPermanent(attackerId));
|
||||
}
|
||||
|
@ -532,7 +531,7 @@ public class CombatGroup implements Serializable, Copyable<CombatGroup> {
|
|||
return blockWasLegal;
|
||||
}
|
||||
if (blockersCount == 1) {
|
||||
List<UUID> toBeRemoved = new ArrayList<UUID>();
|
||||
List<UUID> toBeRemoved = new ArrayList<>();
|
||||
for (UUID blockerId: getBlockers()) {
|
||||
Permanent blocker = game.getPermanent(blockerId);
|
||||
if (blocker != null && blocker.getAbilities().containsKey(CantBlockAloneAbility.getInstance().getId())) {
|
||||
|
|
|
@ -46,7 +46,7 @@ import mage.game.events.GameEvent.EventType;
|
|||
public abstract class Phase implements Serializable {
|
||||
|
||||
protected TurnPhase type;
|
||||
protected List<Step> steps = new ArrayList<Step>();
|
||||
protected List<Step> steps = new ArrayList<>();
|
||||
protected EventType event;
|
||||
protected EventType preEvent;
|
||||
protected EventType postEvent;
|
||||
|
@ -194,6 +194,7 @@ public abstract class Phase implements Serializable {
|
|||
|
||||
protected void playStep(Game game) {
|
||||
if (!currentStep.skipStep(game, activePlayerId)) {
|
||||
game.getState().increaseStepNum();
|
||||
prePriority(game, activePlayerId);
|
||||
if (!game.isPaused() && !game.gameOver(null)) {
|
||||
currentStep.priority(game, activePlayerId, false);
|
||||
|
|
Loading…
Reference in a new issue