mirror of
https://github.com/Card-Forge/forge.git
synced 2025-11-13 01:08:06 +00:00
Misc cleanup (#6767)
* Restore identical checkstyle until it can be cleaned up
This commit is contained in:
@@ -30,7 +30,6 @@ import forge.card.CardType;
|
|||||||
import forge.card.MagicColor;
|
import forge.card.MagicColor;
|
||||||
import forge.card.mana.ManaAtom;
|
import forge.card.mana.ManaAtom;
|
||||||
import forge.card.mana.ManaCost;
|
import forge.card.mana.ManaCost;
|
||||||
import forge.card.mana.ManaCostShard;
|
|
||||||
import forge.deck.Deck;
|
import forge.deck.Deck;
|
||||||
import forge.deck.DeckSection;
|
import forge.deck.DeckSection;
|
||||||
import forge.game.*;
|
import forge.game.*;
|
||||||
@@ -500,6 +499,8 @@ public class AiController {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
landList = ComputerUtilCard.dedupeCards(landList);
|
||||||
|
|
||||||
CardCollection nonLandsInHand = CardLists.filter(player.getCardsIn(ZoneType.Hand), CardPredicates.NON_LANDS);
|
CardCollection nonLandsInHand = CardLists.filter(player.getCardsIn(ZoneType.Hand), CardPredicates.NON_LANDS);
|
||||||
|
|
||||||
// Some considerations for Momir/MoJhoSto
|
// Some considerations for Momir/MoJhoSto
|
||||||
@@ -542,15 +543,12 @@ public class AiController {
|
|||||||
|
|
||||||
// try to skip lands that enter the battlefield tapped if we might want to play something this turn
|
// try to skip lands that enter the battlefield tapped if we might want to play something this turn
|
||||||
if (!nonLandsInHand.isEmpty()) {
|
if (!nonLandsInHand.isEmpty()) {
|
||||||
// get the tapped and non-tapped lands
|
|
||||||
CardCollection tappedLands = new CardCollection();
|
|
||||||
CardCollection nonTappedLands = new CardCollection();
|
CardCollection nonTappedLands = new CardCollection();
|
||||||
for (Card land : landList) {
|
for (Card land : landList) {
|
||||||
// check replacement effects if land would enter tapped or not
|
// check replacement effects if land would enter tapped or not
|
||||||
final Map<AbilityKey, Object> repParams = AbilityKey.mapFromAffected(land);
|
final Map<AbilityKey, Object> repParams = AbilityKey.mapFromAffected(land);
|
||||||
repParams.put(AbilityKey.Origin, land.getZone().getZoneType());
|
repParams.put(AbilityKey.Origin, land.getZone().getZoneType());
|
||||||
repParams.put(AbilityKey.Destination, ZoneType.Battlefield);
|
repParams.put(AbilityKey.Destination, ZoneType.Battlefield);
|
||||||
repParams.put(AbilityKey.Source, land);
|
|
||||||
|
|
||||||
// add Params for AddCounter Replacements
|
// add Params for AddCounter Replacements
|
||||||
GameEntityCounterTable table = new GameEntityCounterTable();
|
GameEntityCounterTable table = new GameEntityCounterTable();
|
||||||
@@ -581,28 +579,28 @@ public class AiController {
|
|||||||
|
|
||||||
// if we have the choice, see if we can play an untapped land
|
// if we have the choice, see if we can play an untapped land
|
||||||
if (!nonTappedLands.isEmpty()) {
|
if (!nonTappedLands.isEmpty()) {
|
||||||
|
// If we have a lot of mana, prefer untapped lands.
|
||||||
|
// We're either topdecking or have drawn enough the tempo no longer matters.
|
||||||
|
int mana_available = getAvailableManaEstimate(player);
|
||||||
|
if (mana_available > 6) {
|
||||||
|
landList = nonTappedLands;
|
||||||
|
} else {
|
||||||
// get the costs of the nonland cards in hand and the mana we have available.
|
// get the costs of the nonland cards in hand and the mana we have available.
|
||||||
// If adding one won't make something new castable, then pick a tapland.
|
// If adding one won't make something new castable, then pick a tapland.
|
||||||
int max_inc = 0;
|
int max_inc = 0;
|
||||||
for (Card c : nonTappedLands) {
|
for (Card c : nonTappedLands) {
|
||||||
max_inc = max(max_inc, c.getMaxManaProduced());
|
max_inc = max(max_inc, c.getMaxManaProduced());
|
||||||
}
|
}
|
||||||
// If we have a lot of mana, prefer untapped lands.
|
|
||||||
// We're either topdecking or have drawn enough the tempo no longer matters.
|
|
||||||
int mana_available = getAvailableManaEstimate(player);
|
|
||||||
if (mana_available > 6) {
|
|
||||||
landList = nonTappedLands;
|
|
||||||
}
|
|
||||||
// check for lands with no mana abilities
|
// check for lands with no mana abilities
|
||||||
else if (max_inc > 0) {
|
if (max_inc > 0) {
|
||||||
boolean found = false;
|
boolean found = false;
|
||||||
for (Card c : nonLandsInHand) {
|
for (Card c : nonLandsInHand) {
|
||||||
// TODO make this work better with split cards and Monocolored Hybrid
|
// TODO make this work better with split cards and Monocolored Hybrid
|
||||||
ManaCost cost = c.getManaCost();
|
ManaCost cost = c.getManaCost();
|
||||||
// check for incremental cmc
|
// check for incremental cmc
|
||||||
// check for X cost spells
|
// check for X cost spells
|
||||||
if (cost.getCMC() == max_inc + mana_available ||
|
if ((cost.getCMC() - mana_available) * (cost.getCMC() - mana_available - max_inc - 1) < 0 ||
|
||||||
(cost.getShardCount(ManaCostShard.X) > 0 && cost.getCMC() >= mana_available)) {
|
(cost.countX() > 0 && cost.getCMC() >= mana_available)) {
|
||||||
found = true;
|
found = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@@ -614,6 +612,7 @@ public class AiController {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Early out if we only have one card left
|
// Early out if we only have one card left
|
||||||
if (landList.size() == 1) {
|
if (landList.size() == 1) {
|
||||||
@@ -719,7 +718,8 @@ public class AiController {
|
|||||||
|
|
||||||
return score;
|
return score;
|
||||||
}));
|
}));
|
||||||
return toReturn; }
|
return toReturn;
|
||||||
|
}
|
||||||
|
|
||||||
// if return true, go to next phase
|
// if return true, go to next phase
|
||||||
private SpellAbility chooseCounterSpell(final List<SpellAbility> possibleCounters) {
|
private SpellAbility chooseCounterSpell(final List<SpellAbility> possibleCounters) {
|
||||||
|
|||||||
@@ -120,7 +120,6 @@ public class AiDeckStatistics {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return fromDeck(deck, player);
|
return fromDeck(deck, player);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2079,6 +2079,7 @@ public class ComputerUtilCard {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// use this function to skip expensive calculations on identical cards
|
||||||
public static CardCollection dedupeCards(CardCollection cc) {
|
public static CardCollection dedupeCards(CardCollection cc) {
|
||||||
if (cc.size() <= 1) {
|
if (cc.size() <= 1) {
|
||||||
return cc;
|
return cc;
|
||||||
|
|||||||
@@ -277,11 +277,7 @@ public class DigUntilEffect extends SpellAbilityEffect {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Allow ordering the rest of the revealed cards
|
// Allow ordering the rest of the revealed cards
|
||||||
if (finalDest.isKnown() && revealed.size() >= 2) {
|
if ((finalDest.isKnown() || (finalDest == ZoneType.Library && !shuffle && !sa.hasParam("RevealRandomOrder"))) && revealed.size() >= 2) {
|
||||||
revealed = (CardCollection)p.getController().orderMoveToZoneList(revealed, finalDest, sa);
|
|
||||||
}
|
|
||||||
if (finalDest == ZoneType.Library && !shuffle
|
|
||||||
&& !sa.hasParam("RevealRandomOrder") && revealed.size() >= 2) {
|
|
||||||
revealed = (CardCollection)p.getController().orderMoveToZoneList(revealed, finalDest, sa);
|
revealed = (CardCollection)p.getController().orderMoveToZoneList(revealed, finalDest, sa);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -842,7 +842,9 @@ public final class StaticAbilityContinuous {
|
|||||||
for (Card c : cards) {
|
for (Card c : cards) {
|
||||||
for (final Trigger trig : c.getTriggers()) {
|
for (final Trigger trig : c.getTriggers()) {
|
||||||
final Trigger newTrigger = affectedCard.addTriggerForStaticAbility(trig, stAb);
|
final Trigger newTrigger = affectedCard.addTriggerForStaticAbility(trig, stAb);
|
||||||
|
if (newTrigger.getKeyword() != null) {
|
||||||
newTrigger.removeParam("Secondary");
|
newTrigger.removeParam("Secondary");
|
||||||
|
}
|
||||||
addedTrigger.add(newTrigger);
|
addedTrigger.add(newTrigger);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,8 +0,0 @@
|
|||||||
This file contains the current build notes for Forge.
|
|
||||||
|
|
||||||
-- Compiling Forge for Android: Pre-requisites --
|
|
||||||
When compiling Forge for Android, make sure the following prerequisites are met:
|
|
||||||
Java 17, either Oracle or OpenJDK.
|
|
||||||
Android SDK 35
|
|
||||||
Android Build-Tools 35.0.0 (this is important, build-tools 33 and below do not work with Java 17)
|
|
||||||
Proguard 7.6.0 (proguard.jar included under "forge-gui-android/tools").
|
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
Name:Calibrated Blast
|
Name:Calibrated Blast
|
||||||
ManaCost:2 R
|
ManaCost:2 R
|
||||||
Types:Instant
|
Types:Instant
|
||||||
A:SP$ DigUntil | Valid$ Card.nonLand | ValidDescription$ nonland | RevealedDestination$ Library | RevealedLibraryPosition$ -1 | RevealRandomOrder$ True | RememberFound$ True | SubAbility$ DBImmediateTrigger | StackDescription$ Reveal cards from the top of your library until you reveal a nonland card. Put the revealed cards on the bottom of your library in a random order. | SpellDescription$ Reveal cards from the top of your library until you reveal a nonland card. Put the revealed cards on the bottom of your library in a random order.
|
A:SP$ DigUntil | Valid$ Card.nonLand | ValidDescription$ nonland | RevealedDestination$ Library | RevealedLibraryPosition$ -1 | RevealRandomOrder$ True | RememberFound$ True | SubAbility$ DBImmediateTrigger | StackDescription$ SpellDescription | SpellDescription$ Reveal cards from the top of your library until you reveal a nonland card. Put the revealed cards on the bottom of your library in a random order.
|
||||||
SVar:DBImmediateTrigger:DB$ ImmediateTrigger | ConditionDefined$ Remembered | ConditionPresent$ Card.nonLand | Execute$ TrigDamage | SpellDescription$ When you reveal a nonland card this way, CARDNAME deals damage equal to that card's mana value to any target.
|
SVar:DBImmediateTrigger:DB$ ImmediateTrigger | ConditionDefined$ Remembered | ConditionPresent$ Card.nonLand | Execute$ TrigDamage | SpellDescription$ When you reveal a nonland card this way, CARDNAME deals damage equal to that card's mana value to any target.
|
||||||
SVar:TrigDamage:DB$ DealDamage | ValidTgts$ Any | NumDmg$ X | SubAbility$ DBCleanup
|
SVar:TrigDamage:DB$ DealDamage | ValidTgts$ Any | NumDmg$ X | SubAbility$ DBCleanup
|
||||||
SVar:DBCleanup:DB$ Cleanup | ClearRemembered$ True
|
SVar:DBCleanup:DB$ Cleanup | ClearRemembered$ True
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ Types:Creature Crab Demon
|
|||||||
PT:5/5
|
PT:5/5
|
||||||
K:Emerge:5 B B:Artifact
|
K:Emerge:5 B B:Artifact
|
||||||
T:Mode$ ChangesZone | Origin$ Any | Destination$ Battlefield | ValidCard$ Card.Self | Execute$ ExileTop | TriggerDescription$ When CARDNAME enters, target opponent exiles the top card of their library, a card at random from their graveyard, and a card at random from their hand. You may cast a spell from among cards exiled this way without paying its mana cost.
|
T:Mode$ ChangesZone | Origin$ Any | Destination$ Battlefield | ValidCard$ Card.Self | Execute$ ExileTop | TriggerDescription$ When CARDNAME enters, target opponent exiles the top card of their library, a card at random from their graveyard, and a card at random from their hand. You may cast a spell from among cards exiled this way without paying its mana cost.
|
||||||
SVar:ExileTop:DB$ Dig | ValidTgts$ Opponent | DigNum$ 1 | ChangeNum$ All | DestinationZone$ Exile | SubAbility$ RandomGraveyard
|
SVar:ExileTop:DB$ Dig | ValidTgts$ Opponent | DigNum$ 1 | ChangeNum$ All | DestinationZone$ Exile | RememberChanged$ True | SubAbility$ RandomGraveyard
|
||||||
SVar:RandomGraveyard:DB$ ChangeZone | Origin$ Graveyard | Destination$ Exile | DefinedPlayer$ Targeted | Mandatory$ True | ChangeNum$ 1 | Hidden$ True | IsCurse$ True | AtRandom$ True | RememberChanged$ True | SubAbility$ RandomHand
|
SVar:RandomGraveyard:DB$ ChangeZone | Origin$ Graveyard | Destination$ Exile | DefinedPlayer$ Targeted | Mandatory$ True | ChangeNum$ 1 | Hidden$ True | IsCurse$ True | AtRandom$ True | RememberChanged$ True | SubAbility$ RandomHand
|
||||||
SVar:RandomHand:DB$ ChangeZone | Origin$ Hand | Destination$ Exile | DefinedPlayer$ Targeted | Mandatory$ True | ChangeNum$ 1 | Hidden$ True | IsCurse$ True | AtRandom$ True | RememberChanged$ True | SubAbility$ CastOneExiled
|
SVar:RandomHand:DB$ ChangeZone | Origin$ Hand | Destination$ Exile | DefinedPlayer$ Targeted | Mandatory$ True | ChangeNum$ 1 | Hidden$ True | IsCurse$ True | AtRandom$ True | RememberChanged$ True | SubAbility$ CastOneExiled
|
||||||
SVar:CastOneExiled:DB$ Play | Valid$ Card.IsRemembered | ValidSA$ Spell | ValidZone$ Exile | Amount$ 1 | Optional$ True | WithoutManaCost$ True | SubAbility$ DBCleanup
|
SVar:CastOneExiled:DB$ Play | Valid$ Card.IsRemembered | ValidSA$ Spell | ValidZone$ Exile | Amount$ 1 | Optional$ True | WithoutManaCost$ True | SubAbility$ DBCleanup
|
||||||
|
|||||||
@@ -2,7 +2,7 @@ Name:Judith, Carnage Connoisseur
|
|||||||
ManaCost:3 B R
|
ManaCost:3 B R
|
||||||
Types:Legendary Creature Human Shaman
|
Types:Legendary Creature Human Shaman
|
||||||
PT:3/4
|
PT:3/4
|
||||||
T:Mode$ SpellCast | TriggerZones$ Battlefield | ValidCard$ Instant,Sorcery | ValidActivatingPlayer$ You | NoResolvingCheck$ True | Execute$ TrigCharm | TriggerDescription$ Whenever you cast an instant or sorcery spell, ABILITY
|
T:Mode$ SpellCast | TriggerZones$ Battlefield | ValidCard$ Instant,Sorcery | ValidActivatingPlayer$ You | Execute$ TrigCharm | TriggerDescription$ Whenever you cast an instant or sorcery spell, ABILITY
|
||||||
SVar:TrigCharm:DB$ Charm | Choices$ DBPump,DBToken
|
SVar:TrigCharm:DB$ Charm | Choices$ DBPump,DBToken
|
||||||
SVar:DBPump:DB$ Pump | Defined$ TriggeredCard | KW$ Deathtouch & Lifelink | PumpZone$ Stack | SpellDescription$ That spell gains deathtouch and lifelink.
|
SVar:DBPump:DB$ Pump | Defined$ TriggeredCard | KW$ Deathtouch & Lifelink | PumpZone$ Stack | SpellDescription$ That spell gains deathtouch and lifelink.
|
||||||
SVar:DBToken:DB$ Token | TokenAmount$ 1 | TokenScript$ r_2_2_imp_burn_opp | TokenOwner$ You | SpellDescription$ Create a 2/2 red Imp creature token with "When this creature dies, it deals 2 damage to each opponent."
|
SVar:DBToken:DB$ Token | TokenAmount$ 1 | TokenScript$ r_2_2_imp_burn_opp | TokenOwner$ You | SpellDescription$ Create a 2/2 red Imp creature token with "When this creature dies, it deals 2 damage to each opponent."
|
||||||
|
|||||||
@@ -4,8 +4,8 @@ Types:Legendary Creature Vampire Wizard
|
|||||||
PT:4/4
|
PT:4/4
|
||||||
T:Mode$ BecomesTarget | ValidTarget$ You,Permanent.YouCtrl+inZoneBattlefield | ValidSource$ SpellAbility.OppCtrl | TriggerZones$ Battlefield | Execute$ TrigCounter | TriggerDescription$ Whenever you or a permanent you control becomes the target of a spell or ability an opponent controls, counter that spell or ability unless that player pays 4 life.
|
T:Mode$ BecomesTarget | ValidTarget$ You,Permanent.YouCtrl+inZoneBattlefield | ValidSource$ SpellAbility.OppCtrl | TriggerZones$ Battlefield | Execute$ TrigCounter | TriggerDescription$ Whenever you or a permanent you control becomes the target of a spell or ability an opponent controls, counter that spell or ability unless that player pays 4 life.
|
||||||
SVar:TrigCounter:DB$ Counter | Defined$ TriggeredSourceSA | UnlessCost$ PayLife<4> | UnlessPayer$ TriggeredSourceSAController
|
SVar:TrigCounter:DB$ Counter | Defined$ TriggeredSourceSA | UnlessCost$ PayLife<4> | UnlessPayer$ TriggeredSourceSAController
|
||||||
T:Mode$ SpellCopy | ValidActivatingPlayer$ You | NoResolvingCheck$ True | TriggerZones$ Battlefield | Execute$ TrigTarget | TriggerDescription$ Whenever you copy a spell, up to one target opponent may also copy that spell. They may choose new targets for that copy.
|
T:Mode$ SpellCopy | ValidActivatingPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigTarget | TriggerDescription$ Whenever you copy a spell, up to one target opponent may also copy that spell. They may choose new targets for that copy.
|
||||||
SVar:TrigTarget:DB$ Pump | ValidTgts$ Opponent | SubAbility$ DBCopy
|
SVar:TrigTarget:DB$ Pump | ValidTgts$ Opponent | TargetMin$ 0 | TargetMax$ 1 | SubAbility$ DBCopy
|
||||||
SVar:DBCopy:DB$ CopySpellAbility | TargetMin$ 0 | TargetMax$ 1 | Defined$ TriggeredSpellAbility | AILogic$ Always | Controller$ Targeted | Optional$ True | MayChooseTarget$ True
|
SVar:DBCopy:DB$ CopySpellAbility | Defined$ TriggeredSpellAbility | AILogic$ Always | Controller$ Targeted | Optional$ True | MayChooseTarget$ True
|
||||||
AI:RemoveDeck:Random
|
AI:RemoveDeck:Random
|
||||||
Oracle:Whenever you or a permanent you control becomes the target of a spell or ability an opponent controls, counter that spell or ability unless that player pays 4 life.\nWhenever you copy a spell, up to one target opponent may also copy that spell. They may choose new targets for that copy.
|
Oracle:Whenever you or a permanent you control becomes the target of a spell or ability an opponent controls, counter that spell or ability unless that player pays 4 life.\nWhenever you copy a spell, up to one target opponent may also copy that spell. They may choose new targets for that copy.
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ Types:Legendary Creature Time Lord Doctor
|
|||||||
PT:4/4
|
PT:4/4
|
||||||
S:Mode$ Continuous | Affected$ Card.YouCtrl+!wasCastFromYourHand | AffectedZone$ Stack | CheckSVar$ X | SVarCompare$ EQ0 | AddKeyword$ Demonstrate | Description$ The first spell you cast from anywhere other than your hand each turn has demonstrate. (When you cast that spell, you may copy it. If you do, choose an opponent to also copy it. A copy of a permanent spell becomes a token.)
|
S:Mode$ Continuous | Affected$ Card.YouCtrl+!wasCastFromYourHand | AffectedZone$ Stack | CheckSVar$ X | SVarCompare$ EQ0 | AddKeyword$ Demonstrate | Description$ The first spell you cast from anywhere other than your hand each turn has demonstrate. (When you cast that spell, you may copy it. If you do, choose an opponent to also copy it. A copy of a permanent spell becomes a token.)
|
||||||
SVar:X:Count$ThisTurnCast_Card.YouCtrl+!wasCastFromYourHand
|
SVar:X:Count$ThisTurnCast_Card.YouCtrl+!wasCastFromYourHand
|
||||||
T:Mode$ SpellCopy | ValidActivatingPlayer$ You | NoResolvingCheck$ True | TriggerZones$ Battlefield | Execute$ TrigPutCounter | TriggerDescription$ Whenever you copy a spell, put a +1/+1 counter on CARDNAME.
|
T:Mode$ SpellCopy | ValidActivatingPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigPutCounter | TriggerDescription$ Whenever you copy a spell, put a +1/+1 counter on CARDNAME.
|
||||||
SVar:TrigPutCounter:DB$ PutCounter | Defined$ Self | CounterType$ P1P1 | CounterNum$ 1
|
SVar:TrigPutCounter:DB$ PutCounter | Defined$ Self | CounterType$ P1P1 | CounterNum$ 1
|
||||||
DeckHas:Ability$Counters
|
DeckHas:Ability$Counters
|
||||||
Oracle:The first spell you cast from anywhere other than your hand each turn has demonstrate. (When you cast that spell, you may copy it. If you do, choose an opponent to also copy it. A copy of a permanent spell becomes a token.)\nWhenever you copy a spell, put a +1/+1 counter on The Twelfth Doctor.
|
Oracle:The first spell you cast from anywhere other than your hand each turn has demonstrate. (When you cast that spell, you may copy it. If you do, choose an opponent to also copy it. A copy of a permanent spell becomes a token.)\nWhenever you copy a spell, put a +1/+1 counter on The Twelfth Doctor.
|
||||||
|
|||||||
Reference in New Issue
Block a user