use of mage.abilities.effects.RequirementEffect in project mage by magefree.
the class MasterWarcraftChooseAttackersEffect method applies.
@Override
public boolean applies(GameEvent event, Ability source, Game game) {
if (!ControlCombatRedundancyWatcher.checkAttackingController(source.getControllerId(), game)) {
game.informPlayers(source.getSourceObject(game).getIdName() + " didn't apply");
return false;
}
Player controller = game.getPlayer(source.getControllerId());
Player attackingPlayer = game.getPlayer(game.getCombat().getAttackingPlayerId());
if (controller == null || attackingPlayer == null || attackingPlayer.getAvailableAttackers(game).isEmpty()) {
// the attack declaration resumes for the active player as normal
return false;
}
Target target = new TargetCreaturePermanent(0, Integer.MAX_VALUE, filter, true);
if (!controller.chooseTarget(Outcome.Benefit, target, source, game)) {
// the attack declaration resumes for the active player as normal
return false;
}
for (Permanent permanent : game.getBattlefield().getActivePermanents(new FilterCreaturePermanent(), source.getControllerId(), source.getSourceId(), game)) {
// Choose creatures that will be attacking this combat
if (target.getTargets().contains(permanent.getId())) {
RequirementEffect effect = new AttacksIfAbleTargetEffect(Duration.EndOfCombat);
effect.setText("");
effect.setTargetPointer(new FixedTarget(permanent, game));
game.addEffect(effect, source);
game.informPlayers(controller.getLogName() + " has decided that " + permanent.getLogName() + " attacks this combat if able");
// All other creatures can't attack (unless they must attack)
} else {
boolean hasToAttack = false;
for (Map.Entry<RequirementEffect, Set<Ability>> entry : game.getContinuousEffects().getApplicableRequirementEffects(permanent, false, game).entrySet()) {
RequirementEffect effect2 = entry.getKey();
if (effect2.mustAttack(game)) {
hasToAttack = true;
}
}
if (!hasToAttack) {
RestrictionEffect effect = new CantAttackTargetEffect(Duration.EndOfCombat);
effect.setText("");
effect.setTargetPointer(new FixedTarget(permanent, game));
game.addEffect(effect, source);
}
}
}
// the attack declaration resumes for the active player as normal
return false;
}
use of mage.abilities.effects.RequirementEffect in project mage by magefree.
the class InstigatorEffect method apply.
@Override
public boolean apply(Game game, Ability source) {
Player player = game.getPlayer(this.getTargetPointer().getFirst(game, source));
if (player != null) {
FilterCreaturePermanent filter = new FilterCreaturePermanent();
filter.add(new ControllerIdPredicate(player.getId()));
RequirementEffect effect = new AttacksIfAbleAllEffect(filter, Duration.EndOfTurn);
game.addEffect(effect, source);
return true;
}
return false;
}
use of mage.abilities.effects.RequirementEffect in project mage by magefree.
the class WalkingDesecrationEffect method apply.
@Override
public boolean apply(Game game, Ability source) {
Player player = game.getPlayer(source.getControllerId());
MageObject sourceObject = game.getObject(source.getSourceId());
if (player != null) {
if (sourceObject != null) {
Choice typeChoice = new ChoiceCreatureType(sourceObject);
if (player.choose(outcome, typeChoice, game)) {
game.informPlayers(sourceObject.getLogName() + " chosen type: " + typeChoice.getChoice());
FilterCreaturePermanent filter = new FilterCreaturePermanent();
filter.add(SubType.byDescription(typeChoice.getChoice()).getPredicate());
RequirementEffect effect = new AttacksIfAbleAllEffect(filter, Duration.EndOfTurn);
game.addEffect(effect, source);
return true;
}
}
}
return false;
}
use of mage.abilities.effects.RequirementEffect in project mage by magefree.
the class Combat method checkAttackRequirements.
protected void checkAttackRequirements(Player player, Game game) {
// 20101001 - 508.1d
for (Permanent creature : player.getAvailableAttackers(game)) {
boolean mustAttack = false;
Set<UUID> defendersForcedToAttack = new HashSet<>();
if (creature.getGoadingPlayers().isEmpty()) {
// check if a creature has to attack
for (Map.Entry<RequirementEffect, Set<Ability>> entry : game.getContinuousEffects().getApplicableRequirementEffects(creature, false, game).entrySet()) {
RequirementEffect effect = entry.getKey();
if (!effect.mustAttack(game)) {
continue;
}
mustAttack = true;
for (Ability ability : entry.getValue()) {
UUID defenderId = effect.mustAttackDefender(ability, game);
if (defenderId != null && defenders.contains(defenderId)) {
defendersForcedToAttack.add(defenderId);
}
break;
}
}
} else {
// if creature is goaded then we start with assumption that it needs to attack any player
mustAttack = true;
defendersForcedToAttack.addAll(defenders);
}
if (!mustAttack) {
continue;
}
// check which defenders the forced to attack creature can attack without paying a cost
Set<UUID> defendersCostlessAttackable = new HashSet<>(defenders);
for (UUID defenderId : defenders) {
if (game.getContinuousEffects().checkIfThereArePayCostToAttackBlockEffects(new DeclareAttackerEvent(defenderId, creature.getId(), creature.getControllerId()), game)) {
defendersCostlessAttackable.remove(defenderId);
defendersForcedToAttack.remove(defenderId);
continue;
}
for (Map.Entry<RestrictionEffect, Set<Ability>> entry : game.getContinuousEffects().getApplicableRestrictionEffects(creature, game).entrySet()) {
if (entry.getValue().stream().anyMatch(ability -> entry.getKey().canAttack(creature, defenderId, ability, game, false))) {
continue;
}
defendersCostlessAttackable.remove(defenderId);
defendersForcedToAttack.remove(defenderId);
break;
}
}
// then they attack one of those players, otherwise they attack any player
if (!defendersForcedToAttack.stream().allMatch(creature.getGoadingPlayers()::contains)) {
defendersForcedToAttack.removeAll(creature.getGoadingPlayers());
}
// force attack only if a defender can be attacked without paying a cost
if (defendersCostlessAttackable.isEmpty()) {
continue;
}
creaturesForcedToAttack.put(creature.getId(), defendersForcedToAttack);
// No need to attack a special defender
Set<UUID> defendersToChooseFrom = defendersForcedToAttack.isEmpty() ? defendersCostlessAttackable : defendersForcedToAttack;
if (defendersToChooseFrom.size() == 1) {
player.declareAttacker(creature.getId(), defendersToChooseFrom.iterator().next(), game, false);
continue;
}
TargetDefender target = new TargetDefender(defendersToChooseFrom, creature.getId());
target.setRequired(true);
target.setTargetName("planeswalker or player for " + creature.getLogName() + " to attack (must attack effect)");
if (player.chooseTarget(Outcome.Damage, target, null, game)) {
player.declareAttacker(creature.getId(), target.getFirstTarget(), game, false);
}
}
}
use of mage.abilities.effects.RequirementEffect in project mage by magefree.
the class Combat method retrieveMustBlockAttackerRequirements.
/**
* Retrieves all requirements that apply and creates a Map with blockers and
* attackers it contains only records if attackers can be retrieved //
* Map<creature that can block,
* Set< all attackers the creature can block and force it to block the attacker>>
*
* @param attackingPlayer - attacker
* @param game
*/
private void retrieveMustBlockAttackerRequirements(Player attackingPlayer, Game game) {
if (attackingPlayer == null) {
return;
}
if (!game.getContinuousEffects().existRequirementEffects()) {
return;
}
for (Permanent possibleBlocker : game.getBattlefield().getActivePermanents(filterBlockers, attackingPlayer.getId(), game)) {
for (Map.Entry<RequirementEffect, Set<Ability>> requirementEntry : game.getContinuousEffects().getApplicableRequirementEffects(possibleBlocker, false, game).entrySet()) {
if (requirementEntry.getKey().mustBlock(game)) {
for (Ability ability : requirementEntry.getValue()) {
UUID attackingCreatureId = requirementEntry.getKey().mustBlockAttacker(ability, game);
Player defender = game.getPlayer(possibleBlocker.getControllerId());
if (attackingCreatureId != null && defender != null && possibleBlocker.canBlock(attackingCreatureId, game)) {
Permanent attackingCreature = game.getPermanent(attackingCreatureId);
if (attackingCreature == null || !attackingCreature.isAttacking()) {
// creature that must be blocked is not attacking
continue;
}
// check if the possible blocker has to pay cost to block, if so don't force
if (game.getContinuousEffects().checkIfThereArePayCostToAttackBlockEffects(new DeclareBlockerEvent(attackingCreatureId, possibleBlocker.getId(), possibleBlocker.getControllerId()), game)) {
// has cost to block to pay so remove this attacker
continue;
}
if (!getDefendingPlayerId(attackingCreatureId, game).equals(possibleBlocker.getControllerId())) {
// Creature can't block if not the controller or a planeswalker of the controller of the possible blocker is attacked
continue;
}
if (creatureMustBlockAttackers.containsKey(possibleBlocker.getId())) {
creatureMustBlockAttackers.get(possibleBlocker.getId()).add(attackingCreatureId);
} else {
Set<UUID> forcingAttackers = new HashSet<>();
forcingAttackers.add(attackingCreatureId);
creatureMustBlockAttackers.put(possibleBlocker.getId(), forcingAttackers);
// assign block to the first forcing attacker automatically
defender.declareBlocker(defender.getId(), possibleBlocker.getId(), attackingCreatureId, game, false);
}
}
}
}
}
}
}
Aggregations