From e090b26240e3ef26d2274f34d8cb0ca5d6a8bff9 Mon Sep 17 00:00:00 2001 From: LevelX2 Date: Thu, 18 May 2017 23:42:32 +0200 Subject: [PATCH] * Urborg Justice - Fixed that tokens going to graveyard were not counted. --- .../src/mage/cards/b/BontuTheGlorified.java | 292 +++++++++--------- Mage.Sets/src/mage/cards/f/FreshMeat.java | 2 +- .../src/mage/cards/k/KuonOgreAscendant.java | 2 +- Mage.Sets/src/mage/cards/u/UrborgJustice.java | 29 +- .../common/CreaturesDiedThisTurnCount.java | 2 +- .../watchers/common/CreaturesDiedWatcher.java | 18 +- 6 files changed, 168 insertions(+), 177 deletions(-) diff --git a/Mage.Sets/src/mage/cards/b/BontuTheGlorified.java b/Mage.Sets/src/mage/cards/b/BontuTheGlorified.java index 574cc827bc..179ff976b2 100644 --- a/Mage.Sets/src/mage/cards/b/BontuTheGlorified.java +++ b/Mage.Sets/src/mage/cards/b/BontuTheGlorified.java @@ -1,146 +1,146 @@ -/* - * Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without modification, are - * permitted provided that the following conditions are met: - * - * 1. Redistributions of source code must retain the above copyright notice, this list of - * conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright notice, this list - * of conditions and the following disclaimer in the documentation and/or other materials - * provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND - * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON - * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - * - * The views and conclusions contained in the software and documentation are those of the - * authors and should not be interpreted as representing official policies, either expressed - * or implied, of BetaSteward_at_googlemail.com. - */ -package mage.cards.b; - -import java.util.UUID; -import mage.MageInt; -import mage.abilities.Ability; -import mage.abilities.common.SimpleActivatedAbility; -import mage.abilities.common.SimpleStaticAbility; -import mage.abilities.costs.common.SacrificeTargetCost; -import mage.abilities.costs.mana.ManaCostsImpl; -import mage.abilities.effects.Effect; -import mage.abilities.effects.RestrictionEffect; -import mage.abilities.effects.common.GainLifeEffect; -import mage.abilities.effects.common.LoseLifeOpponentsEffect; -import mage.abilities.effects.keyword.ScryEffect; -import mage.abilities.keyword.IndestructibleAbility; -import mage.abilities.keyword.MenaceAbility; -import mage.cards.CardImpl; -import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.Duration; -import mage.constants.SuperType; -import mage.constants.Zone; -import mage.filter.common.FilterControlledCreaturePermanent; -import mage.filter.predicate.permanent.AnotherPredicate; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.players.Player; -import mage.target.common.TargetControlledPermanent; -import mage.watchers.common.CreaturesDiedWatcher; - -/** - * - * @author jeffwadsworth - */ -public class BontuTheGlorified extends CardImpl { - - private static final FilterControlledCreaturePermanent filter = new FilterControlledCreaturePermanent("another creature"); - - static { - filter.add(new AnotherPredicate()); - } - - public BontuTheGlorified(UUID ownerId, CardSetInfo setInfo) { - super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}"); - addSuperType(SuperType.LEGENDARY); - this.subtype.add("God"); - this.power = new MageInt(4); - this.toughness = new MageInt(6); - - //Menace - this.addAbility(new MenaceAbility()); - - //Indestructible - this.addAbility(IndestructibleAbility.getInstance()); - - //Bontu the Glorified can't attack or block unless a creature died under your control this turn. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BontuTheGlorifiedRestrictionEffect()), new CreaturesDiedWatcher()); - - //{1}{B}, Sacrifice another creature: Scry 1. Each opponent loses 1 life and you gain 1 life. - Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, new ScryEffect(1), new ManaCostsImpl("{1}{B}")); - ability.addEffect(new LoseLifeOpponentsEffect(1)); - Effect effect = new GainLifeEffect(1); - effect.setText("and you gain 1 life"); - ability.addEffect(effect); - ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); - this.addAbility(ability); - - } - - public BontuTheGlorified(final BontuTheGlorified card) { - super(card); - } - - @Override - public BontuTheGlorified copy() { - return new BontuTheGlorified(this); - } -} - -class BontuTheGlorifiedRestrictionEffect extends RestrictionEffect { - - public BontuTheGlorifiedRestrictionEffect() { - super(Duration.WhileOnBattlefield); - staticText = "{this} can't attack or block unless a creature died under your control this turn"; - } - - public BontuTheGlorifiedRestrictionEffect(final BontuTheGlorifiedRestrictionEffect effect) { - super(effect); - } - - @Override - public BontuTheGlorifiedRestrictionEffect copy() { - return new BontuTheGlorifiedRestrictionEffect(this); - } - - @Override - public boolean canAttack(Game game) { - return false; - } - - @Override - public boolean canBlock(Permanent attacker, Permanent blocker, Ability source, Game game) { - return false; - } - - @Override - public boolean applies(Permanent permanent, Ability source, Game game) { - if (permanent.getId().equals(source.getSourceId())) { - Player controller = game.getPlayer(source.getControllerId()); - CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); - if (controller != null - && watcher != null) { - return (watcher.getAmountOfCreaturesDiesThisTurn(controller.getId()) == 0); - } - return true; - } // do not apply to other creatures. - return false; - } -} +/* + * Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, are + * permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, this list of + * conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright notice, this list + * of conditions and the following disclaimer in the documentation and/or other materials + * provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR + * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON + * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING + * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF + * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * The views and conclusions contained in the software and documentation are those of the + * authors and should not be interpreted as representing official policies, either expressed + * or implied, of BetaSteward_at_googlemail.com. + */ +package mage.cards.b; + +import java.util.UUID; +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.Effect; +import mage.abilities.effects.RestrictionEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.LoseLifeOpponentsEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.abilities.keyword.IndestructibleAbility; +import mage.abilities.keyword.MenaceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SuperType; +import mage.constants.Zone; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.common.TargetControlledPermanent; +import mage.watchers.common.CreaturesDiedWatcher; + +/** + * + * @author jeffwadsworth + */ +public class BontuTheGlorified extends CardImpl { + + private static final FilterControlledCreaturePermanent filter = new FilterControlledCreaturePermanent("another creature"); + + static { + filter.add(new AnotherPredicate()); + } + + public BontuTheGlorified(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}"); + addSuperType(SuperType.LEGENDARY); + this.subtype.add("God"); + this.power = new MageInt(4); + this.toughness = new MageInt(6); + + //Menace + this.addAbility(new MenaceAbility()); + + //Indestructible + this.addAbility(IndestructibleAbility.getInstance()); + + //Bontu the Glorified can't attack or block unless a creature died under your control this turn. + this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BontuTheGlorifiedRestrictionEffect()), new CreaturesDiedWatcher()); + + //{1}{B}, Sacrifice another creature: Scry 1. Each opponent loses 1 life and you gain 1 life. + Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, new ScryEffect(1), new ManaCostsImpl("{1}{B}")); + ability.addEffect(new LoseLifeOpponentsEffect(1)); + Effect effect = new GainLifeEffect(1); + effect.setText("and you gain 1 life"); + ability.addEffect(effect); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); + this.addAbility(ability); + + } + + public BontuTheGlorified(final BontuTheGlorified card) { + super(card); + } + + @Override + public BontuTheGlorified copy() { + return new BontuTheGlorified(this); + } +} + +class BontuTheGlorifiedRestrictionEffect extends RestrictionEffect { + + public BontuTheGlorifiedRestrictionEffect() { + super(Duration.WhileOnBattlefield); + staticText = "{this} can't attack or block unless a creature died under your control this turn"; + } + + public BontuTheGlorifiedRestrictionEffect(final BontuTheGlorifiedRestrictionEffect effect) { + super(effect); + } + + @Override + public BontuTheGlorifiedRestrictionEffect copy() { + return new BontuTheGlorifiedRestrictionEffect(this); + } + + @Override + public boolean canAttack(Game game) { + return false; + } + + @Override + public boolean canBlock(Permanent attacker, Permanent blocker, Ability source, Game game) { + return false; + } + + @Override + public boolean applies(Permanent permanent, Ability source, Game game) { + if (permanent.getId().equals(source.getSourceId())) { + Player controller = game.getPlayer(source.getControllerId()); + CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); + if (controller != null + && watcher != null) { + return (watcher.getAmountOfCreaturesDiedThisTurnByController(controller.getId()) == 0); + } + return true; + } // do not apply to other creatures. + return false; + } +} diff --git a/Mage.Sets/src/mage/cards/f/FreshMeat.java b/Mage.Sets/src/mage/cards/f/FreshMeat.java index 0151843f27..bbe3539dd1 100644 --- a/Mage.Sets/src/mage/cards/f/FreshMeat.java +++ b/Mage.Sets/src/mage/cards/f/FreshMeat.java @@ -70,7 +70,7 @@ class FreshMeatDynamicValue implements DynamicValue { public int calculate(Game game, Ability sourceAbility, Effect effect) { CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); if (watcher != null) { - return watcher.getAmountOfCreaturesDiesThisTurn(sourceAbility.getControllerId()); + return watcher.getAmountOfCreaturesDiedThisTurnByController(sourceAbility.getControllerId()); } return 0; } diff --git a/Mage.Sets/src/mage/cards/k/KuonOgreAscendant.java b/Mage.Sets/src/mage/cards/k/KuonOgreAscendant.java index 7c80355ae9..034869093f 100644 --- a/Mage.Sets/src/mage/cards/k/KuonOgreAscendant.java +++ b/Mage.Sets/src/mage/cards/k/KuonOgreAscendant.java @@ -111,7 +111,7 @@ enum KuonOgreAscendantCondition implements Condition { public boolean apply(Game game, Ability source) { CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); if (watcher != null) { - return watcher.getAmountOfCreaturesDiesThisTurn() > 2; + return watcher.getAmountOfCreaturesDiedThisTurn() > 2; } return false; } diff --git a/Mage.Sets/src/mage/cards/u/UrborgJustice.java b/Mage.Sets/src/mage/cards/u/UrborgJustice.java index 528e7f2130..72068f62d9 100644 --- a/Mage.Sets/src/mage/cards/u/UrborgJustice.java +++ b/Mage.Sets/src/mage/cards/u/UrborgJustice.java @@ -27,23 +27,19 @@ */ package mage.cards.u; -import java.util.Set; import java.util.UUID; -import mage.MageObjectReference; import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.effects.Effect; import mage.abilities.effects.common.SacrificeEffect; -import mage.cards.Card; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.filter.common.FilterCreaturePermanent; import mage.game.Game; -import mage.players.Player; import mage.target.common.TargetOpponent; -import mage.watchers.common.CardsPutIntoGraveyardWatcher; +import mage.watchers.common.CreaturesDiedWatcher; /** * @@ -52,10 +48,10 @@ import mage.watchers.common.CardsPutIntoGraveyardWatcher; public class UrborgJustice extends CardImpl { public UrborgJustice(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.INSTANT},"{B}{B}"); + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{B}{B}"); // Target opponent sacrifices a creature for each creature put into your graveyard from the battlefield this turn. - this.getSpellAbility().addWatcher(new CardsPutIntoGraveyardWatcher()); + this.getSpellAbility().addWatcher(new CreaturesDiedWatcher()); SacrificeEffect sacrificeEffect = new SacrificeEffect(new FilterCreaturePermanent(), new UrborgJusticeDynamicValue(), ""); sacrificeEffect.setText("Target opponent sacrifices a creature for each creature put into your graveyard from the battlefield this turn"); @@ -92,21 +88,10 @@ class UrborgJusticeDynamicValue implements DynamicValue { @Override public int calculate(Game game, Ability sourceAbility, Effect effect) { - CardsPutIntoGraveyardWatcher watcher = (CardsPutIntoGraveyardWatcher) game.getState().getWatchers().get(CardsPutIntoGraveyardWatcher.class.getSimpleName()); - - int count = 0; - Player controller = game.getPlayer(sourceAbility.getControllerId()); - if (controller != null && watcher != null) { - Set cardsInGraveyard = watcher.getCardsPutToGraveyardFromBattlefield(); - for (MageObjectReference mor : cardsInGraveyard) { - if (game.getState().getZoneChangeCounter(mor.getSourceId()) == mor.getZoneChangeCounter()) { - Card card = game.getCard(mor.getSourceId()); - if (card != null && card.getOwnerId().equals(sourceAbility.getControllerId()) && card.isCreature()) { - count++; - } - } - } + CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); + if (watcher != null) { + return watcher.getAmountOfCreaturesDiedThisTurnByOwner(sourceAbility.getControllerId()); } - return count; + return 0; } } diff --git a/Mage/src/main/java/mage/abilities/dynamicvalue/common/CreaturesDiedThisTurnCount.java b/Mage/src/main/java/mage/abilities/dynamicvalue/common/CreaturesDiedThisTurnCount.java index fbeee8f1c4..70603c01aa 100644 --- a/Mage/src/main/java/mage/abilities/dynamicvalue/common/CreaturesDiedThisTurnCount.java +++ b/Mage/src/main/java/mage/abilities/dynamicvalue/common/CreaturesDiedThisTurnCount.java @@ -42,7 +42,7 @@ public class CreaturesDiedThisTurnCount implements DynamicValue { public int calculate(Game game, Ability sourceAbility, Effect effect) { CreaturesDiedWatcher watcher = (CreaturesDiedWatcher) game.getState().getWatchers().get(CreaturesDiedWatcher.class.getSimpleName()); if (watcher != null) { - return watcher.getAmountOfCreaturesDiesThisTurn(); + return watcher.getAmountOfCreaturesDiedThisTurn(); } return 0; } diff --git a/Mage/src/main/java/mage/watchers/common/CreaturesDiedWatcher.java b/Mage/src/main/java/mage/watchers/common/CreaturesDiedWatcher.java index dfcf40f640..4707d9c96d 100644 --- a/Mage/src/main/java/mage/watchers/common/CreaturesDiedWatcher.java +++ b/Mage/src/main/java/mage/watchers/common/CreaturesDiedWatcher.java @@ -29,8 +29,6 @@ package mage.watchers.common; import java.util.HashMap; import java.util.UUID; -import java.util.stream.Collectors; - import mage.constants.WatcherScope; import mage.game.Game; import mage.game.events.GameEvent; @@ -43,6 +41,7 @@ import mage.watchers.Watcher; public class CreaturesDiedWatcher extends Watcher { private final HashMap amountOfCreaturesThatDiedByController = new HashMap<>(); + private final HashMap amountOfCreaturesThatDiedByOwner = new HashMap<>(); public CreaturesDiedWatcher() { super(CreaturesDiedWatcher.class.getSimpleName(), WatcherScope.GAME); @@ -51,6 +50,7 @@ public class CreaturesDiedWatcher extends Watcher { public CreaturesDiedWatcher(final CreaturesDiedWatcher watcher) { super(watcher); this.amountOfCreaturesThatDiedByController.putAll(watcher.amountOfCreaturesThatDiedByController); + this.amountOfCreaturesThatDiedByOwner.putAll(watcher.amountOfCreaturesThatDiedByOwner); } @Override @@ -60,8 +60,10 @@ public class CreaturesDiedWatcher extends Watcher { if (zEvent.isDiesEvent() && zEvent.getTarget() != null && zEvent.getTarget().isCreature()) { - int amount = getAmountOfCreaturesDiesThisTurn(zEvent.getTarget().getControllerId()); + int amount = getAmountOfCreaturesDiedThisTurnByController(zEvent.getTarget().getControllerId()); amountOfCreaturesThatDiedByController.put(zEvent.getTarget().getControllerId(), amount + 1); + amount = getAmountOfCreaturesDiedThisTurnByOwner(zEvent.getTarget().getOwnerId()); + amountOfCreaturesThatDiedByOwner.put(zEvent.getTarget().getOwnerId(), amount + 1); } } } @@ -69,19 +71,23 @@ public class CreaturesDiedWatcher extends Watcher { @Override public void reset() { amountOfCreaturesThatDiedByController.clear(); + amountOfCreaturesThatDiedByOwner.clear(); } - - public int getAmountOfCreaturesDiesThisTurn(UUID playerId) { + public int getAmountOfCreaturesDiedThisTurnByController(UUID playerId) { return amountOfCreaturesThatDiedByController.getOrDefault(playerId, 0); } + public int getAmountOfCreaturesDiedThisTurnByOwner(UUID playerId) { + return amountOfCreaturesThatDiedByOwner.getOrDefault(playerId, 0); + } + @Override public CreaturesDiedWatcher copy() { return new CreaturesDiedWatcher(this); } - public int getAmountOfCreaturesDiesThisTurn() { + public int getAmountOfCreaturesDiedThisTurn() { return amountOfCreaturesThatDiedByController.values().stream().mapToInt(x -> x).sum(); } }