Search in sources :

Example 41 with CombatGroup

use of mage.game.combat.CombatGroup in project mage by magefree.

the class AetherplasmEffect method apply.

@Override
public boolean apply(Game game, Ability source) {
    Player player = game.getPlayer(source.getControllerId());
    if (player == null) {
        return false;
    }
    if (player.chooseUse(Outcome.PutCardInPlay, "Put a creature card from your hand onto the battlefield?", source, game)) {
        TargetCardInHand target = new TargetCardInHand(StaticFilters.FILTER_CARD_CREATURE_A);
        if (player.choose(Outcome.PutCardInPlay, target, source.getSourceId(), game)) {
            Card card = game.getCard(target.getFirstTarget());
            if (card != null) {
                Permanent blockedCreature = game.getPermanent(getTargetPointer().getFirst(game, source));
                if (player.moveCards(card, Zone.BATTLEFIELD, source, game, false, false, false, null) && game.getCombat() != null && blockedCreature != null) {
                    CombatGroup attacker = game.getCombat().findGroup(blockedCreature.getId());
                    Permanent putIntoPlay = game.getPermanent(target.getFirstTarget());
                    if (putIntoPlay != null && putIntoPlay.isCreature(game) && attacker != null) {
                        game.getCombat().findGroup(blockedCreature.getId()).addBlocker(putIntoPlay.getId(), source.getControllerId(), game);
                    }
                }
            }
        }
    }
    return true;
}
Also used : Player(mage.players.Player) Permanent(mage.game.permanent.Permanent) TargetCardInHand(mage.target.common.TargetCardInHand) CombatGroup(mage.game.combat.CombatGroup) Card(mage.cards.Card)

Example 42 with CombatGroup

use of mage.game.combat.CombatGroup in project mage by magefree.

the class HumanPlayer method checkIfAttackersValid.

private boolean checkIfAttackersValid(Game game) {
    if (!game.getCombat().getCreaturesForcedToAttack().isEmpty()) {
        if (!game.getCombat().getAttackers().containsAll(game.getCombat().getCreaturesForcedToAttack().keySet())) {
            int forcedAttackers = 0;
            StringBuilder sb = new StringBuilder();
            for (UUID creatureId : game.getCombat().getCreaturesForcedToAttack().keySet()) {
                boolean validForcedAttacker = false;
                if (game.getCombat().getAttackers().contains(creatureId)) {
                    Set<UUID> possibleDefender = game.getCombat().getCreaturesForcedToAttack().get(creatureId);
                    if (possibleDefender.isEmpty() || possibleDefender.contains(game.getCombat().getDefenderId(creatureId))) {
                        validForcedAttacker = true;
                    }
                }
                if (validForcedAttacker) {
                    forcedAttackers++;
                } else {
                    Permanent creature = game.getPermanent(creatureId);
                    if (creature != null) {
                        sb.append(creature.getIdName()).append(' ');
                    }
                }
            }
            if (game.getCombat().getMaxAttackers() > forcedAttackers) {
                int requireToAttack = Math.min(game.getCombat().getMaxAttackers() - forcedAttackers, game.getCombat().getCreaturesForcedToAttack().size() - forcedAttackers);
                String message = (requireToAttack == 1 ? " more attacker that is " : " more attackers that are ") + "forced to attack.\nCreature" + (requireToAttack == 1 ? "" : "s") + " forced to attack: ";
                game.informPlayer(this, sb.insert(0, message).insert(0, requireToAttack).insert(0, "You have to attack with ").toString());
                return false;
            }
        }
    }
    // check if enough attackers are declared
    // check if players have to be attacked
    Set<UUID> playersToAttackIfAble = new HashSet<>();
    for (Map.Entry<RequirementEffect, Set<Ability>> entry : game.getContinuousEffects().getApplicableRequirementEffects(null, true, game).entrySet()) {
        RequirementEffect effect = entry.getKey();
        for (Ability ability : entry.getValue()) {
            UUID playerToAttack = effect.playerMustBeAttackedIfAble(ability, game);
            if (playerToAttack != null) {
                playersToAttackIfAble.add(playerToAttack);
            }
        }
    }
    if (!playersToAttackIfAble.isEmpty()) {
        Set<UUID> checkPlayersToAttackIfAble = new HashSet<>(playersToAttackIfAble);
        for (CombatGroup combatGroup : game.getCombat().getGroups()) {
            checkPlayersToAttackIfAble.remove(combatGroup.getDefendingPlayerId());
        }
        for (UUID forcedToAttackId : checkPlayersToAttackIfAble) {
            Player forcedToAttack = game.getPlayer(forcedToAttackId);
            for (Permanent attacker : game.getBattlefield().getAllActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, getId(), game)) {
                if (game.getContinuousEffects().checkIfThereArePayCostToAttackBlockEffects(new DeclareAttackerEvent(forcedToAttackId, attacker.getId(), attacker.getControllerId()), game)) {
                    continue;
                }
                // if attacker needs a specific defender to attack so select that one instead
                if (game.getCombat().getCreaturesForcedToAttack().containsKey(attacker.getId())) {
                    Set<UUID> possibleDefenders = game.getCombat().getCreaturesForcedToAttack().get(attacker.getId());
                    if (!possibleDefenders.isEmpty() && !possibleDefenders.contains(forcedToAttackId)) {
                        continue;
                    }
                }
                UUID defendingPlayerId = game.getCombat().getDefendingPlayerId(attacker.getId(), game);
                if (playersToAttackIfAble.contains(defendingPlayerId)) {
                    // already attacks other player taht has to be attacked
                    continue;
                }
                if (defendingPlayerId != null || attacker.canAttackInPrinciple(forcedToAttackId, game)) {
                    game.informPlayer(this, "You are forced to attack " + forcedToAttack.getName() + " or a controlled planeswalker e.g. with " + attacker.getIdName() + ".");
                    return false;
                }
            }
        }
    }
    return true;
}
Also used : ManaAbility(mage.abilities.mana.ManaAbility) Player(mage.players.Player) Permanent(mage.game.permanent.Permanent) TargetPermanent(mage.target.TargetPermanent) DeclareAttackerEvent(mage.game.events.DeclareAttackerEvent) RequirementEffect(mage.abilities.effects.RequirementEffect) CombatGroup(mage.game.combat.CombatGroup)

Example 43 with CombatGroup

use of mage.game.combat.CombatGroup in project mage by magefree.

the class HumanPlayer method selectCombatGroup.

protected void selectCombatGroup(UUID defenderId, UUID blockerId, Game game) {
    if (gameInCheckPlayableState(game)) {
        return;
    }
    TargetAttackingCreature target = new TargetAttackingCreature();
    // TODO: add canRespond cycle?
    if (!canRespond()) {
        return;
    }
    updateGameStatePriority("selectCombatGroup", game);
    prepareForResponse(game);
    if (!isExecutingMacro()) {
        // possible attackers to block
        Set<UUID> attackers = target.possibleTargets(null, playerId, game);
        Permanent blocker = game.getPermanent(blockerId);
        Set<UUID> possibleTargets = new HashSet<>();
        for (UUID attackerId : attackers) {
            CombatGroup group = game.getCombat().findGroup(attackerId);
            if (group != null && blocker != null && group.canBlock(blocker, game)) {
                possibleTargets.add(attackerId);
            }
        }
        game.fireSelectTargetEvent(playerId, new MessageToClient("Select attacker to block", getRelatedObjectName(blockerId, game)), possibleTargets, false, getOptions(target, null));
    }
    waitForResponse(game);
    UUID responseId = getFixedResponseUUID(game);
    if (response.getBoolean() != null) {
    // do nothing
    } else if (responseId != null) {
        CombatGroup group = game.getCombat().findGroup(responseId);
        if (group != null) {
            // check if already blocked, if not add
            if (!group.getBlockers().contains(blockerId)) {
                declareBlocker(defenderId, blockerId, responseId, game);
            } else {
                // else remove from block
                game.getCombat().removeBlockerGromGroup(blockerId, group, game);
            }
        }
    }
}
Also used : TargetAttackingCreature(mage.target.common.TargetAttackingCreature) Permanent(mage.game.permanent.Permanent) TargetPermanent(mage.target.TargetPermanent) MessageToClient(mage.util.MessageToClient) CombatGroup(mage.game.combat.CombatGroup)

Example 44 with CombatGroup

use of mage.game.combat.CombatGroup in project mage by magefree.

the class ComputerPlayer3 method simulateAttackers.

protected int simulateAttackers(Game game, SimulationNode node, UUID attackerId, int alpha, int beta, boolean counter) {
    if (Thread.interrupted()) {
        Thread.currentThread().interrupt();
        logger.debug(indent(node.depth) + "interrupted");
        return GameStateEvaluator.evaluate(playerId, game);
    }
    Integer val = null;
    SimulationNode bestNode = null;
    SimulatedPlayer attacker = (SimulatedPlayer) game.getPlayer(attackerId);
    UUID defenderId = game.getOpponents(attackerId).iterator().next();
    if (logger.isDebugEnabled()) {
        logger.debug(indent(node.depth) + attacker.getName() + "'s possible attackers: " + attacker.getAvailableAttackers(defenderId, game));
    }
    List<Combat> engagements = attacker.addAttackers(game);
    for (Combat engagement : engagements) {
        if (alpha >= beta) {
            logger.debug(indent(node.depth) + "simulating -- pruning attackers");
            break;
        }
        Game sim = game.copy();
        for (CombatGroup group : engagement.getGroups()) {
            for (UUID attackId : group.getAttackers()) {
                sim.getPlayer(attackerId).declareAttacker(attackId, defenderId, sim, false);
            }
        }
        sim.fireEvent(GameEvent.getEvent(GameEvent.EventType.DECLARED_ATTACKERS, attackerId, attackerId));
        SimulationNode newNode = new SimulationNode(node, sim, attackerId);
        if (logger.isDebugEnabled()) {
            logger.debug(indent(node.depth) + "simulating attack for player:" + game.getPlayer(attackerId).getName());
        }
        sim.checkStateAndTriggered();
        while (!sim.getStack().isEmpty()) {
            sim.getStack().resolve(sim);
            logger.debug(indent(node.depth) + "resolving triggered abilities");
            sim.applyEffects();
        }
        sim.fireEvent(GameEvent.getEvent(GameEvent.EventType.DECLARE_ATTACKERS_STEP_POST, sim.getActivePlayerId(), sim.getActivePlayerId()));
        Combat simCombat = sim.getCombat().copy();
        sim.getPhase().setStep(new DeclareBlockersStep());
        val = simulateCombat(sim, newNode, alpha, beta, counter);
        if (!attackerId.equals(playerId)) {
            if (val < beta) {
                beta = val;
                bestNode = newNode;
                node.setCombat(simCombat);
            }
        } else {
            if (val > alpha) {
                alpha = val;
                bestNode = newNode;
                node.setCombat(simCombat);
            }
        }
    }
    if (val == null) {
        val = GameStateEvaluator.evaluate(playerId, game);
    }
    if (bestNode != null) {
        node.children.clear();
        node.children.add(bestNode);
    }
    if (logger.isDebugEnabled()) {
        logger.debug(indent(node.depth) + "returning -- combat attacker score: " + val + " depth:" + node.depth + " for player:" + game.getPlayer(node.getPlayerId()).getName());
    }
    return val;
}
Also used : Game(mage.game.Game) Combat(mage.game.combat.Combat) UUID(java.util.UUID) CombatGroup(mage.game.combat.CombatGroup)

Aggregations

CombatGroup (mage.game.combat.CombatGroup)44 Permanent (mage.game.permanent.Permanent)39 UUID (java.util.UUID)25 Player (mage.players.Player)23 FilterCreaturePermanent (mage.filter.common.FilterCreaturePermanent)9 FixedTarget (mage.target.targetpointer.FixedTarget)9 TargetPermanent (mage.target.TargetPermanent)8 TargetCreaturePermanent (mage.target.common.TargetCreaturePermanent)8 HashSet (java.util.HashSet)7 OneShotEffect (mage.abilities.effects.OneShotEffect)6 Game (mage.game.Game)6 ArrayList (java.util.ArrayList)5 List (java.util.List)5 Combat (mage.game.combat.Combat)5 BlockerDeclaredEvent (mage.game.events.BlockerDeclaredEvent)5 Target (mage.target.Target)5 MageObjectReference (mage.MageObjectReference)4 Ability (mage.abilities.Ability)4 PermanentInListPredicate (mage.filter.predicate.permanent.PermanentInListPredicate)4 BlockedByOnlyOneCreatureThisCombatWatcher (mage.watchers.common.BlockedByOnlyOneCreatureThisCombatWatcher)4