mirror of
https://github.com/Card-Forge/forge.git
synced 2025-11-15 18:28:00 +00:00
Fix ChangeZone* not always shuffling (#4976)
* Support nicknames for non-rebranded * Fix ChangeZone* not always shuffling
This commit is contained in:
@@ -30,6 +30,8 @@ import forge.item.PaperCard;
|
||||
import forge.util.CollectionSuppliers;
|
||||
import forge.util.Lang;
|
||||
import forge.util.TextUtil;
|
||||
import forge.util.lang.LangEnglish;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.commons.lang3.tuple.Pair;
|
||||
|
||||
@@ -371,6 +373,11 @@ public final class CardDb implements ICardDatabase, IDeckGenPool {
|
||||
}
|
||||
|
||||
private void buildRenamedCards() {
|
||||
Lang lang = Lang.getInstance();
|
||||
if (lang == null) {
|
||||
// for some tests
|
||||
lang = new LangEnglish();
|
||||
}
|
||||
// for now just check Universes Within
|
||||
for (CardInSet cis : editions.get("SLX").getCards()) {
|
||||
String orgName = alternateName.get(cis.name);
|
||||
@@ -382,7 +389,10 @@ public final class CardDb implements ICardDatabase, IDeckGenPool {
|
||||
renamedMain.setName(renamedMain.getAltName());
|
||||
renamedMain.setAltName(null);
|
||||
// TODO this could mess up some "named ..." cardname literals but there's no printing like that currently
|
||||
renamedMain.setOracleText(renamedMain.getOracleText().replace(orgName, renamedMain.getName()));
|
||||
renamedMain.setOracleText(renamedMain.getOracleText()
|
||||
.replace(orgName, renamedMain.getName())
|
||||
.replace(lang.getNickName(orgName), lang.getNickName(renamedMain.getName()))
|
||||
);
|
||||
facesByName.put(renamedMain.getName(), renamedMain);
|
||||
CardFace renamedOther = null;
|
||||
if (org.getOtherPart() != null) {
|
||||
@@ -390,7 +400,10 @@ public final class CardDb implements ICardDatabase, IDeckGenPool {
|
||||
orgName = renamedOther.getName();
|
||||
renamedOther.setName(renamedOther.getAltName());
|
||||
renamedOther.setAltName(null);
|
||||
renamedOther.setOracleText(renamedOther.getOracleText().replace(orgName, renamedOther.getName()));
|
||||
renamedOther.setOracleText(renamedOther.getOracleText()
|
||||
.replace(orgName, renamedOther.getName())
|
||||
.replace(lang.getNickName(orgName), lang.getNickName(renamedOther.getName()))
|
||||
);
|
||||
facesByName.put(renamedOther.getName(), renamedOther);
|
||||
}
|
||||
|
||||
|
||||
@@ -36,12 +36,11 @@ public class ChangeZoneAllEffect extends SpellAbilityEffect {
|
||||
|
||||
@Override
|
||||
public void resolve(SpellAbility sa) {
|
||||
final Card source = sa.getHostCard();
|
||||
|
||||
if (!checkValidDuration(sa.getParam("Duration"), sa)) {
|
||||
return;
|
||||
}
|
||||
|
||||
final Card source = sa.getHostCard();
|
||||
final ZoneType destination = ZoneType.smartValueOf(sa.getParam("Destination"));
|
||||
final List<ZoneType> origin = ZoneType.listValueOf(sa.getParam("Origin"));
|
||||
|
||||
@@ -239,14 +238,12 @@ public class ChangeZoneAllEffect extends SpellAbilityEffect {
|
||||
addUntilCommand(sa, untilHostLeavesPlayCommand(triggerList, sa));
|
||||
}
|
||||
|
||||
// if Shuffle parameter exists, and any amount of cards were owned by
|
||||
// that player, then shuffle that library
|
||||
// CR 701.20d If an effect would cause a player to shuffle a set of objects into a library,
|
||||
// that library is shuffled even if there are no objects in that set.
|
||||
if (sa.hasParam("Shuffle")) {
|
||||
for (Player p : game.getPlayers()) {
|
||||
if (Iterables.any(cards, CardPredicates.isOwner(p))) {
|
||||
for (Player p : tgtPlayers) {
|
||||
p.shuffle(sa);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -450,9 +450,9 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
*/
|
||||
private void changeKnownOriginResolve(final SpellAbility sa) {
|
||||
CardCollectionView tgtCards = getTargetCards(sa);
|
||||
final Player player = sa.getActivatingPlayer();
|
||||
final Player activator = sa.getActivatingPlayer();
|
||||
final Card hostCard = sa.getHostCard();
|
||||
final Game game = player.getGame();
|
||||
final Game game = activator.getGame();
|
||||
final CardCollection commandCards = new CardCollection();
|
||||
|
||||
ZoneType destination = ZoneType.smartValueOf(sa.getParam("Destination"));
|
||||
@@ -464,7 +464,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
int libraryPosition = sa.hasParam("LibraryPosition") ?
|
||||
AbilityUtils.calculateAmount(hostCard, sa.getParam("LibraryPosition"), sa) : 0;
|
||||
if (sa.hasParam("DestinationAlternative")) {
|
||||
Pair<ZoneType, Integer> pair = handleAltDest(sa, hostCard, destination, libraryPosition, player);
|
||||
Pair<ZoneType, Integer> pair = handleAltDest(sa, hostCard, destination, libraryPosition, activator);
|
||||
destination = pair.getKey();
|
||||
libraryPosition = pair.getValue();
|
||||
}
|
||||
@@ -503,7 +503,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
final boolean shuffle = sa.hasParam("Shuffle") && "True".equals(sa.getParam("Shuffle"));
|
||||
boolean combatChanged = false;
|
||||
|
||||
Player chooser = player;
|
||||
Player chooser = activator;
|
||||
if (sa.hasParam("Chooser")) {
|
||||
chooser = AbilityUtils.getDefinedPlayers(hostCard, sa.getParam("Chooser"), sa).get(0);
|
||||
}
|
||||
@@ -588,11 +588,11 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (sa.hasParam("WithCountersType")) {
|
||||
CounterType cType = CounterType.getType(sa.getParam("WithCountersType"));
|
||||
int cAmount = AbilityUtils.calculateAmount(hostCard, sa.getParamOrDefault("WithCountersAmount", "1"), sa);
|
||||
gameCard.addEtbCounter(cType, cAmount, player);
|
||||
gameCard.addEtbCounter(cType, cAmount, activator);
|
||||
}
|
||||
if (sa.hasParam("GainControl")) {
|
||||
final String g = sa.getParam("GainControl");
|
||||
Player newController = g.equals("True") ? player :
|
||||
Player newController = g.equals("True") ? activator :
|
||||
AbilityUtils.getDefinedPlayers(hostCard, g, sa).get(0);
|
||||
if (newController != null) {
|
||||
if (newController != gameCard.getController()) {
|
||||
@@ -615,7 +615,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (!list.isEmpty()) {
|
||||
Map<String, Object> params = Maps.newHashMap();
|
||||
params.put("Attach", gameCard);
|
||||
Card attachedTo = player.getController().chooseSingleEntityForEffect(list, sa, Localizer.getInstance().getMessage("lblSelectACardAttachSourceTo", gameCard.toString()), params);
|
||||
Card attachedTo = activator.getController().chooseSingleEntityForEffect(list, sa, Localizer.getInstance().getMessage("lblSelectACardAttachSourceTo", gameCard.toString()), params);
|
||||
|
||||
// TODO can't attach later or moveToPlay would attach indirectly
|
||||
// bypass canBeAttached to skip Protection checks when trying to attach multiple auras that would grant protection
|
||||
@@ -630,7 +630,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (!list.isEmpty()) {
|
||||
Map<String, Object> params = Maps.newHashMap();
|
||||
params.put("Attach", gameCard);
|
||||
Player attachedTo = player.getController().chooseSingleEntityForEffect(list, sa, Localizer.getInstance().getMessage("lblSelectAPlayerAttachSourceTo", gameCard.toString()), params);
|
||||
Player attachedTo = activator.getController().chooseSingleEntityForEffect(list, sa, Localizer.getInstance().getMessage("lblSelectAPlayerAttachSourceTo", gameCard.toString()), params);
|
||||
gameCard.attachToEntity(attachedTo, sa);
|
||||
}
|
||||
else { // When it should enter the battlefield attached to an illegal player it fails
|
||||
@@ -715,7 +715,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
|
||||
if (ZoneType.Hand.equals(destination) && ZoneType.Command.equals(originZone.getZoneType())) {
|
||||
StringBuilder sb = new StringBuilder();
|
||||
sb.append(movedCard.getName()).append(" has moved from Command Zone to ").append(player).append("'s hand.");
|
||||
sb.append(movedCard.getName()).append(" has moved from Command Zone to ").append(activator).append("'s hand.");
|
||||
game.getGameLog().add(GameLogEntryType.ZONE_CHANGE, sb.toString());
|
||||
commandCards.add(movedCard); //add to list to reveal the commandzone cards
|
||||
}
|
||||
@@ -732,7 +732,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (sa.hasParam("WithCountersType")) {
|
||||
CounterType cType = CounterType.getType(sa.getParam("WithCountersType"));
|
||||
int cAmount = AbilityUtils.calculateAmount(hostCard, sa.getParamOrDefault("WithCountersAmount", "1"), sa);
|
||||
movedCard.addCounter(cType, cAmount, player, counterTable);
|
||||
movedCard.addCounter(cType, cAmount, activator, counterTable);
|
||||
}
|
||||
|
||||
if (sa.hasParam("ExileFaceDown") || sa.hasParam("FaceDown")) {
|
||||
@@ -744,7 +744,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
movedCard.setForetoldCostByEffect(true);
|
||||
}
|
||||
// look at the exiled card
|
||||
movedCard.addMayLookTemp(player);
|
||||
movedCard.addMayLookTemp(activator);
|
||||
}
|
||||
|
||||
// CR 400.7k
|
||||
@@ -759,7 +759,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (sa.hasParam("WithCountersType")) {
|
||||
CounterType cType = CounterType.getType(sa.getParam("WithCountersType"));
|
||||
int cAmount = AbilityUtils.calculateAmount(hostCard, sa.getParamOrDefault("WithCountersAmount", "1"), sa);
|
||||
meld.addCounter(cType, cAmount, player, counterTable);
|
||||
meld.addCounter(cType, cAmount, activator, counterTable);
|
||||
}
|
||||
}
|
||||
if (gameCard.hasMergedCard()) {
|
||||
@@ -768,7 +768,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
if (sa.hasParam("WithCountersType")) {
|
||||
CounterType cType = CounterType.getType(sa.getParam("WithCountersType"));
|
||||
int cAmount = AbilityUtils.calculateAmount(hostCard, sa.getParamOrDefault("WithCountersAmount", "1"), sa);
|
||||
c.addCounter(cType, cAmount, player, counterTable);
|
||||
c.addCounter(cType, cAmount, activator, counterTable);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -819,7 +819,7 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
|
||||
//reveal command cards that changes zone from command zone to player's hand
|
||||
if (!commandCards.isEmpty()) {
|
||||
game.getAction().reveal(commandCards, player, true, "Revealed cards in ");
|
||||
game.getAction().reveal(commandCards, activator, true, "Revealed cards in ");
|
||||
}
|
||||
|
||||
triggerList.triggerChangesZoneAll(game, sa);
|
||||
@@ -848,8 +848,10 @@ public class ChangeZoneEffect extends SpellAbilityEffect {
|
||||
// FCollection already does use set.
|
||||
pl.add(tgtC.getOwner());
|
||||
}
|
||||
if (pl.isEmpty()) {
|
||||
pl.add(activator);
|
||||
}
|
||||
}
|
||||
|
||||
for (final Player p : pl) {
|
||||
p.shuffle(sa);
|
||||
}
|
||||
|
||||
@@ -491,7 +491,6 @@ public class DigEffect extends SpellAbilityEffect {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -25,8 +25,7 @@ public abstract class ManifestBaseEffect extends SpellAbilityEffect {
|
||||
final Player activator = sa.getActivatingPlayer();
|
||||
final Game game = source.getGame();
|
||||
// Usually a number leaving possibility for X, Sacrifice X land: Manifest X creatures.
|
||||
final int amount = sa.hasParam("Amount") ? AbilityUtils.calculateAmount(source,
|
||||
sa.getParam("Amount"), sa) : 1;
|
||||
final int amount = sa.hasParam("Amount") ? AbilityUtils.calculateAmount(source, sa.getParam("Amount"), sa) : 1;
|
||||
|
||||
for (final Player p : getTargetPlayers(sa, "DefinedPlayer")) {
|
||||
CardCollection tgtCards;
|
||||
|
||||
@@ -4,7 +4,7 @@ Types:Sorcery
|
||||
A:SP$ Draw | Defined$ Player | Upto$ True | NumCards$ 2 | SubAbility$ DBRepeat | AILogic$ GainLife | SpellDescription$ Each player may draw up to two cards. For each card less than two a player draws this way, that player gains 2 life.
|
||||
SVar:DBRepeat:DB$ RepeatEach | RepeatPlayers$ Player | RepeatSubAbility$ DBGainLife | StackDescription$ For each card less than two a player draws this way, that player gains 2 life.
|
||||
SVar:DBGainLife:DB$ GainLife | LifeAmount$ AFNotDrawnNum | Defined$ Player.IsRemembered
|
||||
SVar:Y:Count$SVar$AFNotDrawnNum/NMinus.2
|
||||
SVar:Y:SVar$AFNotDrawnNum/NMinus.2
|
||||
SVar:X:SVar$Y/Twice
|
||||
AI:RemoveDeck:All
|
||||
Oracle:Each player may draw up to two cards. For each card less than two a player draws this way, that player gains 2 life.
|
||||
|
||||
@@ -4,7 +4,7 @@ Types:Instant
|
||||
A:SP$ Draw | Defined$ Player | Upto$ True | NumCards$ 2 | SubAbility$ DBRepeat | AILogic$ GainLife | SpellDescription$ Each player may draw up to two cards. For each card less than two a player draws this way, that player gains 2 life.
|
||||
SVar:DBRepeat:DB$ RepeatEach | RepeatPlayers$ Player | RepeatSubAbility$ DBGainLife | StackDescription$ For each card less than two a player draws this way, that player gains 2 life.
|
||||
SVar:DBGainLife:DB$ GainLife | LifeAmount$ AFNotDrawnNum | Defined$ Player.IsRemembered
|
||||
SVar:Y:Count$SVar$AFNotDrawnNum/NMinus.2
|
||||
SVar:Y:SVar$AFNotDrawnNum/NMinus.2
|
||||
SVar:X:SVar$Y/Twice
|
||||
AI:RemoveDeck:All
|
||||
Oracle:Each player may draw up to two cards. For each card less than two a player draws this way, that player gains 2 life.
|
||||
|
||||
Reference in New Issue
Block a user