Search in sources :

Example 1 with CreatedTokenEvent

use of mage.game.events.CreatedTokenEvent in project mage by magefree.

the class TokenImpl method putOntoBattlefieldHelper.

private static void putOntoBattlefieldHelper(CreateTokenEvent event, Game game, Ability source, boolean tapped, boolean attacking, UUID attackedPlayer, boolean created) {
    Player controller = game.getPlayer(event.getPlayerId());
    if (controller == null) {
        return;
    }
    for (Map.Entry<Token, Integer> entry : event.getTokens().entrySet()) {
        Token token = entry.getKey();
        int amount = entry.getValue();
        String setCode = token instanceof TokenImpl ? ((TokenImpl) token).getSetCode(game, event.getSourceId()) : null;
        List<Permanent> needTokens = new ArrayList<>();
        List<Permanent> allowedTokens = new ArrayList<>();
        // prepare tokens to enter
        for (int i = 0; i < amount; i++) {
            // use event.getPlayerId() as controller cause it can be replaced by replacement effect
            PermanentToken newPermanent = new PermanentToken(token, event.getPlayerId(), setCode, game);
            game.getState().addCard(newPermanent);
            needTokens.add(newPermanent);
            game.getPermanentsEntering().put(newPermanent.getId(), newPermanent);
            newPermanent.setTapped(tapped);
            ZoneChangeEvent emptyEvent = new ZoneChangeEvent(newPermanent, newPermanent.getControllerId(), Zone.OUTSIDE, Zone.BATTLEFIELD);
            // tokens zcc must simulate card's zcc too keep copied card/spell settings
            // (example: etb's kicker ability of copied creature spell, see tests with Deathforge Shaman)
            newPermanent.updateZoneChangeCounter(game, emptyEvent);
        }
        // check ETB effects
        game.setScopeRelevant(true);
        for (Permanent permanent : needTokens) {
            if (permanent.entersBattlefield(source, game, Zone.OUTSIDE, true)) {
                allowedTokens.add(permanent);
            } else {
                game.getPermanentsEntering().remove(permanent.getId());
            }
        }
        game.setScopeRelevant(false);
        // put allowed tokens to play
        int createOrder = game.getState().getNextPermanentOrderNumber();
        for (Permanent permanent : allowedTokens) {
            game.addPermanent(permanent, createOrder);
            permanent.setZone(Zone.BATTLEFIELD, game);
            game.getPermanentsEntering().remove(permanent.getId());
            // keep tokens ids
            if (token instanceof TokenImpl) {
                ((TokenImpl) token).lastAddedTokenIds.add(permanent.getId());
                ((TokenImpl) token).lastAddedTokenId = permanent.getId();
            }
            // created token events
            ZoneChangeEvent zccEvent = new ZoneChangeEvent(permanent, permanent.getControllerId(), Zone.OUTSIDE, Zone.BATTLEFIELD);
            game.addSimultaneousEvent(zccEvent);
            if (permanent instanceof PermanentToken && created) {
                game.addSimultaneousEvent(new CreatedTokenEvent(source, (PermanentToken) permanent));
            }
            // code refactored from CopyPermanentEffect
            if (permanent.getSubtype().contains(SubType.AURA)) {
                Outcome auraOutcome = Outcome.BoostCreature;
                Target auraTarget = null;
                // attach - search effect in spell ability (example: cast Utopia Sprawl, cast Estrid's Invocation on it)
                for (Ability ability : permanent.getAbilities()) {
                    if (!(ability instanceof SpellAbility)) {
                        continue;
                    }
                    auraOutcome = ability.getEffects().getOutcome(ability);
                    for (Effect effect : ability.getEffects()) {
                        if (!(effect instanceof AttachEffect)) {
                            continue;
                        }
                        if (permanent.getSpellAbility().getTargets().size() > 0) {
                            auraTarget = permanent.getSpellAbility().getTargets().get(0);
                        }
                    }
                }
                // enchant - search in all abilities (example: cast Estrid's Invocation on enchanted creature by Estrid, the Masked second ability, cast Estrid's Invocation on it)
                if (auraTarget == null) {
                    for (Ability ability : permanent.getAbilities()) {
                        if (!(ability instanceof EnchantAbility)) {
                            continue;
                        }
                        auraOutcome = ability.getEffects().getOutcome(ability);
                        if (ability.getTargets().size() > 0) {
                            // Animate Dead don't have targets
                            auraTarget = ability.getTargets().get(0);
                        }
                    }
                }
                // if this is a copy of a copy, the copy's target has been copied and needs to be cleared
                if (auraTarget == null) {
                    break;
                }
                // clear selected target
                if (auraTarget.getFirstTarget() != null) {
                    auraTarget.remove(auraTarget.getFirstTarget());
                }
                // select new target
                auraTarget.setNotTarget(true);
                if (!controller.choose(auraOutcome, auraTarget, source.getSourceId(), game)) {
                    break;
                }
                UUID targetId = auraTarget.getFirstTarget();
                Permanent targetPermanent = game.getPermanent(targetId);
                Player targetPlayer = game.getPlayer(targetId);
                if (targetPermanent != null) {
                    targetPermanent.addAttachment(permanent.getId(), source, game);
                } else if (targetPlayer != null) {
                    targetPlayer.addAttachment(permanent.getId(), source, game);
                }
            }
            // must attack
            if (attacking && game.getCombat() != null && game.getActivePlayerId().equals(permanent.getControllerId())) {
                game.getCombat().addAttackingCreature(permanent.getId(), game, attackedPlayer);
            }
            // game logs
            if (created) {
                game.informPlayers(controller.getLogName() + " creates a " + permanent.getLogName() + " token");
            } else {
                game.informPlayers(permanent.getLogName() + " enters the battlefield as a token under " + controller.getLogName() + "'s control'");
            }
        }
    }
    // Needed to do it here without LKIReset i.e. do get SwordOfTheMeekTest running correctly.
    game.getState().applyEffects(game);
}
Also used : EnchantAbility(mage.abilities.keyword.EnchantAbility) SpellAbility(mage.abilities.SpellAbility) Ability(mage.abilities.Ability) Player(mage.players.Player) Permanent(mage.game.permanent.Permanent) CreatedTokenEvent(mage.game.events.CreatedTokenEvent) PermanentToken(mage.game.permanent.PermanentToken) PermanentToken(mage.game.permanent.PermanentToken) SpellAbility(mage.abilities.SpellAbility) EnchantAbility(mage.abilities.keyword.EnchantAbility) AttachEffect(mage.abilities.effects.common.AttachEffect) ZoneChangeEvent(mage.game.events.ZoneChangeEvent) Target(mage.target.Target) Outcome(mage.constants.Outcome) Effect(mage.abilities.effects.Effect) AttachEffect(mage.abilities.effects.common.AttachEffect)

Aggregations

Ability (mage.abilities.Ability)1 SpellAbility (mage.abilities.SpellAbility)1 Effect (mage.abilities.effects.Effect)1 AttachEffect (mage.abilities.effects.common.AttachEffect)1 EnchantAbility (mage.abilities.keyword.EnchantAbility)1 Outcome (mage.constants.Outcome)1 CreatedTokenEvent (mage.game.events.CreatedTokenEvent)1 ZoneChangeEvent (mage.game.events.ZoneChangeEvent)1 Permanent (mage.game.permanent.Permanent)1 PermanentToken (mage.game.permanent.PermanentToken)1 Player (mage.players.Player)1 Target (mage.target.Target)1