forked from External/mage
game: fixed miss state triggers check in multi-steps abilities/effects (#10564)
This commit is contained in:
parent
b66189d3da
commit
f26b1470fa
4 changed files with 31 additions and 8 deletions
|
|
@ -214,16 +214,14 @@ public abstract class AbilityImpl implements Ability {
|
|||
} else {
|
||||
game.addEffect((ContinuousEffect) effect, this);
|
||||
}
|
||||
|
||||
/**
|
||||
* All restrained trigger events are fired now. To restrain the
|
||||
* events is mainly neccessary because of the movement of multiple
|
||||
* object at once. If the event is fired directly as one object
|
||||
* moved, other objects are not already in the correct zone to check
|
||||
* for their effects. (e.g. Valakut, the Molten Pinnacle)
|
||||
*/
|
||||
game.getState().handleSimultaneousEvent(game);
|
||||
game.resetShortLivingLKI();
|
||||
/**
|
||||
* <p>
|
||||
* game.applyEffects() has to be done at least for every effect that
|
||||
* moves cards/permanent between zones, or changes control of
|
||||
* objects so Static effects work as intended if dependant from the
|
||||
|
|
@ -231,8 +229,7 @@ public abstract class AbilityImpl implements Ability {
|
|||
* abilities with replacement effects deactivated too late Example:
|
||||
* {@link org.mage.test.cards.replacement.DryadMilitantTest#testDiesByDestroy testDiesByDestroy}
|
||||
*/
|
||||
game.applyEffects();
|
||||
game.getState().getTriggers().checkStateTriggers(game);
|
||||
game.getState().processAction(game);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,6 +8,15 @@ import mage.game.events.GameEvent;
|
|||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* 603.8.
|
||||
* Some triggered abilities trigger when a game state (such as a player controlling no permanents of
|
||||
* a particular card type) is true, rather than triggering when an event occurs. These abilities trigger
|
||||
* as soon as the game state matches the condition. They'll go onto the stack at the next available opportunity.
|
||||
* These are called state triggers. (Note that state triggers aren't the same as state-based actions.)
|
||||
* A state-triggered ability doesn't trigger again until the ability has resolved, has been countered,
|
||||
* or has otherwise left the stack. Then, if the object with the ability is still in the same zone and
|
||||
* the game state still matches its trigger condition, the ability will trigger again.
|
||||
*
|
||||
* @author BetaSteward_at_googlemail.com
|
||||
*/
|
||||
public abstract class StateTriggeredAbility extends TriggeredAbilityImpl {
|
||||
|
|
@ -21,7 +30,8 @@ public abstract class StateTriggeredAbility extends TriggeredAbilityImpl {
|
|||
}
|
||||
|
||||
public boolean canTrigger(Game game) {
|
||||
//20100716 - 603.8
|
||||
// 603.8 - A state-triggered ability doesn't trigger again until the ability has resolved,
|
||||
// has been countered, or has otherwise left the stack
|
||||
return !Boolean.TRUE.equals(game.getState().getValue(getSourceId().toString() + "triggered"));
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -465,6 +465,13 @@ public interface Game extends MageItem, Serializable, Copyable<Game> {
|
|||
|
||||
UUID fireReflexiveTriggeredAbility(ReflexiveTriggeredAbility reflexiveAbility, Ability source);
|
||||
|
||||
/**
|
||||
* Inner game engine call to reset game objects to actual versions
|
||||
* (reset all objects and apply all effects due layer system)
|
||||
* <p>
|
||||
* Warning, if you need to process object moves in the middle of the effect/ability
|
||||
* then call game.getState().processAction(game) instead
|
||||
*/
|
||||
void applyEffects();
|
||||
|
||||
boolean checkStateAndTriggered();
|
||||
|
|
|
|||
|
|
@ -655,10 +655,19 @@ public class GameState implements Serializable, Copyable<GameState> {
|
|||
this.gameOver = true;
|
||||
}
|
||||
|
||||
// 608.2e
|
||||
/**
|
||||
* Must be called between effects/steps in the ability's resolve
|
||||
* <p>
|
||||
* 608.2e
|
||||
* Some spells and abilities have multiple steps or actions, denoted by separate sentences or clauses,
|
||||
* that involve multiple players. In these cases, the choices for the first action are made in APNAP order,
|
||||
* and then the first action is processed simultaneously. Then the choices for the second action are made in
|
||||
* APNAP order, and then that action is processed simultaneously, and so on. See rule 101.4.
|
||||
*/
|
||||
public void processAction(Game game) {
|
||||
game.getState().handleSimultaneousEvent(game);
|
||||
game.applyEffects();
|
||||
game.getState().getTriggers().checkStateTriggers(game);
|
||||
}
|
||||
|
||||
public void applyEffects(Game game) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue