mirror of
https://github.com/magefree/mage.git
synced 2025-12-25 21:12:04 -08:00
Phyrexian mana now correctly a payment choice.
Per rule 601.2b, it is not determined at the pay costs step, but at the "choice" step, long before costs are determined. This fixes trinisphere interactions and should be consistent with the rules.
This commit is contained in:
parent
209e2d13c1
commit
ce1f4a3bf8
47 changed files with 234 additions and 222 deletions
|
|
@ -31,11 +31,9 @@ import mage.MageObject;
|
|||
import mage.MageObjectReference;
|
||||
import mage.Mana;
|
||||
import mage.abilities.costs.*;
|
||||
import mage.abilities.costs.common.PayLifeCost;
|
||||
import mage.abilities.costs.common.TapSourceCost;
|
||||
import mage.abilities.costs.mana.ManaCost;
|
||||
import mage.abilities.costs.mana.ManaCosts;
|
||||
import mage.abilities.costs.mana.ManaCostsImpl;
|
||||
import mage.abilities.costs.mana.VariableManaCost;
|
||||
import mage.abilities.costs.mana.*;
|
||||
import mage.abilities.effects.ContinuousEffect;
|
||||
import mage.abilities.effects.Effect;
|
||||
import mage.abilities.effects.Effects;
|
||||
|
|
@ -62,6 +60,7 @@ import mage.watchers.Watcher;
|
|||
import org.apache.log4j.Logger;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -298,6 +297,9 @@ public abstract class AbilityImpl implements Ability {
|
|||
&& game.replaceEvent(GameEvent.getEvent(GameEvent.EventType.CAST_SPELL_LATE, getId(), getSourceId(), getControllerId()), this)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
handlePhyrexianManaCosts(game, sourceId, controller);
|
||||
|
||||
for (UUID modeId : this.getModes().getSelectedModes()) {
|
||||
this.getModes().setActiveMode(modeId);
|
||||
//20121001 - 601.2c
|
||||
|
|
@ -503,6 +505,27 @@ public abstract class AbilityImpl implements Ability {
|
|||
return announceString.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* 601.2b
|
||||
* If a cost that will be paid as the spell is being cast includes Phyrexian mana symbols,
|
||||
* the player announces whether he or she intends to pay 2 life or the corresponding colored mana cost for each of those symbols.
|
||||
*/
|
||||
private void handlePhyrexianManaCosts(Game game, UUID sourceId, Player controller) {
|
||||
Iterator<ManaCost> costIterator = manaCostsToPay.iterator();
|
||||
while(costIterator.hasNext()) {
|
||||
ManaCost cost = costIterator.next();
|
||||
if(cost instanceof PhyrexianManaCost) {
|
||||
PhyrexianManaCost phyrexianManaCost = (PhyrexianManaCost)cost;
|
||||
PayLifeCost payLifeCost = new PayLifeCost(2);
|
||||
if(payLifeCost.canPay(this, sourceId, controller.getId(), game) &&
|
||||
controller.chooseUse(Outcome.LoseLife, "Pay 2 life instead of " + phyrexianManaCost.getBaseText() + "?", this, game)) {
|
||||
costIterator.remove();
|
||||
costs.add(payLifeCost);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles X mana costs and sets manaCostsToPay.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -50,34 +50,20 @@ public class PhyrexianManaCost extends ColoredManaCost {
|
|||
super(manaCost);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void assignPayment(Game game, Ability ability, ManaPool pool, Cost costToPay) {
|
||||
assignColored(ability, game, pool, this.mana, costToPay);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getText() {
|
||||
return '{' + mana.toString() + "P}";
|
||||
return '{' + mana.toString() + "/P}";
|
||||
}
|
||||
|
||||
public String getBaseText() {
|
||||
return super.getText();
|
||||
}
|
||||
|
||||
@Override
|
||||
public PhyrexianManaCost getUnpaid() {
|
||||
return this;
|
||||
public ColoredManaCost getUnpaid() {
|
||||
return new ColoredManaCost(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean canPay(Ability ability, UUID sourceId, UUID controllerId, Game game) {
|
||||
if (!game.getPlayer(controllerId).isLifeTotalCanChange()) {
|
||||
return false;
|
||||
}
|
||||
return game.getPlayer(controllerId).getLife() >= 2;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean pay(Ability ability, Game game, UUID sourceId, UUID controllerId, boolean noMana, Cost costToPay) {
|
||||
this.paid = game.getPlayer(controllerId).loseLife(2, game, false) == 2;
|
||||
return paid;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PhyrexianManaCost copy() {
|
||||
|
|
|
|||
|
|
@ -29,8 +29,13 @@ package mage.abilities.effects;
|
|||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.costs.Cost;
|
||||
import mage.abilities.costs.Costs;
|
||||
import mage.abilities.costs.CostsImpl;
|
||||
import mage.abilities.costs.common.PayLifeCost;
|
||||
import mage.abilities.costs.mana.ManaCost;
|
||||
import mage.abilities.costs.mana.ManaCosts;
|
||||
import mage.abilities.costs.mana.ManaCostsImpl;
|
||||
import mage.abilities.costs.mana.PhyrexianManaCost;
|
||||
import mage.constants.Duration;
|
||||
import mage.constants.Outcome;
|
||||
import mage.game.Game;
|
||||
|
|
@ -38,6 +43,9 @@ import mage.game.events.GameEvent;
|
|||
import mage.game.events.GameEvent.EventType;
|
||||
import mage.players.Player;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author LevelX2
|
||||
|
|
@ -141,6 +149,7 @@ public abstract class PayCostToAttackBlockEffectImpl extends ReplacementEffectIm
|
|||
attackBlockManaTax.clearPaid();
|
||||
if (attackBlockManaTax.canPay(source, source.getSourceId(), player.getId(), game)
|
||||
&& player.chooseUse(Outcome.Neutral, chooseText, source, game)) {
|
||||
handlePhyrexianManaCosts(manaCosts, player, source, game);
|
||||
if (attackBlockManaTax instanceof ManaCostsImpl) {
|
||||
if (attackBlockManaTax.payOrRollback(source, game, source.getSourceId(), event.getPlayerId())) {
|
||||
return false;
|
||||
|
|
@ -152,6 +161,27 @@ public abstract class PayCostToAttackBlockEffectImpl extends ReplacementEffectIm
|
|||
return false;
|
||||
}
|
||||
|
||||
private void handlePhyrexianManaCosts(ManaCosts<ManaCost> manaCosts, Player player, Ability source, Game game) {
|
||||
Iterator<ManaCost> manaCostIterator = manaCosts.iterator();
|
||||
Costs<PayLifeCost> costs = new CostsImpl<>();
|
||||
|
||||
while(manaCostIterator.hasNext()) {
|
||||
ManaCost manaCost = manaCostIterator.next();
|
||||
if(manaCost instanceof PhyrexianManaCost) {
|
||||
PhyrexianManaCost phyrexianManaCost = (PhyrexianManaCost)manaCost;
|
||||
PayLifeCost payLifeCost = new PayLifeCost(2);
|
||||
if(payLifeCost.canPay(source, source.getSourceId(), player.getId(), game) &&
|
||||
player.chooseUse(Outcome.LoseLife, "Pay 2 life instead of " + phyrexianManaCost.getBaseText() + "?", source, game)) {
|
||||
manaCostIterator.remove();
|
||||
costs.add(payLifeCost);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
costs.pay(source, game, source.getSourceId(), player.getId(), false, null);
|
||||
}
|
||||
|
||||
|
||||
private boolean handleOtherCosts(Cost attackBlockOtherTax, GameEvent event, Ability source, Game game) {
|
||||
Player player = game.getPlayer(event.getPlayerId());
|
||||
if (player != null) {
|
||||
|
|
|
|||
|
|
@ -2438,7 +2438,9 @@ public abstract class PlayerImpl implements Player, Serializable {
|
|||
if (!copy.canActivate(playerId, game)) {
|
||||
return false;
|
||||
}
|
||||
game.getContinuousEffects().costModification(copy, game);
|
||||
if(available != null) {
|
||||
game.getContinuousEffects().costModification(copy, game);
|
||||
}
|
||||
|
||||
Card card = game.getCard(ability.getSourceId());
|
||||
if (card != null) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue