Merge branch 'BrawlFormat' into 'master'

Brawl format

See merge request core-developers/forge!324
This commit is contained in:
Michael Kamensky
2018-03-30 06:35:07 +00:00
31 changed files with 458 additions and 81 deletions

View File

@@ -15,6 +15,7 @@ public class ConstructedAchievements extends AchievementCollection {
add(new VariantWins(GameType.MomirBasic, 25, 50, 100));
add(new VariantWins(GameType.Commander, 25, 50, 100));
add(new VariantWins(GameType.TinyLeaders, 25, 50, 100));
add(new VariantWins(GameType.Brawl, 25, 50, 100));
add(new VariantWins(GameType.Planechase, 25, 50, 100));
add(new VariantWins(GameType.Archenemy, 25, 50, 100));
add(new Poisoned(15, 25, 40));

View File

@@ -23,6 +23,9 @@ import java.util.Map;
*/
public class CommanderDeckGenerator extends DeckProxy implements Comparable<CommanderDeckGenerator> {
public static List<DeckProxy> getCommanderDecks(final DeckFormat format, boolean isForAi, boolean isCardGen){
if(format.equals(DeckFormat.Brawl)){
return getBrawlDecks(format, isForAi, isCardGen);
}
ItemPool uniqueCards;
if(isCardGen){
uniqueCards = new ItemPool<PaperCard>(PaperCard.class);
@@ -50,6 +53,31 @@ public class CommanderDeckGenerator extends DeckProxy implements Comparable<Comm
return decks;
}
public static List<DeckProxy> getBrawlDecks(final DeckFormat format, boolean isForAi, boolean isCardGen){
ItemPool uniqueCards;
if(isCardGen){
uniqueCards = new ItemPool<PaperCard>(PaperCard.class);
//TODO: upate to actual Brawl model from real Brawl decks
Iterable<String> legendNames=CardRelationMatrixGenerator.cardPools.get(FModel.getFormats().getStandard().getName()).keySet();
for(String legendName:legendNames) {
uniqueCards.add(FModel.getMagicDb().getCommonCards().getUniqueByName(legendName));
}
}else {
uniqueCards = ItemPool.createFrom(FModel.getMagicDb().getCommonCards().getUniqueCards(), PaperCard.class);
}
Predicate<CardRules> canPlay = isForAi ? DeckGeneratorBase.AI_CAN_PLAY : DeckGeneratorBase.HUMAN_CAN_PLAY;
@SuppressWarnings("unchecked")
Iterable<PaperCard> legends = Iterables.filter(uniqueCards.toFlatList(), Predicates.and(format.isLegalCardPredicate(),
Predicates.compose(Predicates.and(
CardRulesPredicates.Presets.CAN_BE_BRAWL_COMMANDER,
canPlay), PaperCard.FN_GET_RULES)));
final List<DeckProxy> decks = new ArrayList<DeckProxy>();
for(PaperCard legend: legends) {
decks.add(new CommanderDeckGenerator(legend, format, isForAi, isCardGen));
}
return decks;
}
private final PaperCard legend;
private final int index;
private final DeckFormat format;

View File

@@ -370,6 +370,21 @@ public class DeckProxy implements InventoryItem {
return result;
}
public static Iterable<DeckProxy> getAllBrawlDecks() {
return getAllBrawlDecks(null);
}
public static Iterable<DeckProxy> getAllBrawlDecks(Predicate<Deck> filter) {
final List<DeckProxy> result = new ArrayList<DeckProxy>();
if (filter == null) {
filter = DeckFormat.Brawl.hasLegalCardsPredicate();
}
else {
filter = Predicates.and(DeckFormat.Brawl.hasLegalCardsPredicate(), filter);
}
addDecksRecursivelly("Brawl", GameType.Brawl, result, "", FModel.getDecks().getBrawl(), filter);
return result;
}
public static Iterable<DeckProxy> getAllSchemeDecks() {
return getAllSchemeDecks(null);
}

View File

@@ -10,6 +10,7 @@ public enum DeckType {
RANDOM_COMMANDER_DECK ("Random Commander Decks"),
RANDOM_CARDGEN_COMMANDER_DECK ("Random Commander Card-based Decks"),
TINY_LEADERS_DECKS ("Tiny Leaders Decks"),
BRAWL_DECKS ("Brawl Decks"),
SCHEME_DECKS ("Scheme Decks"),
PLANAR_DECKS ("Planar Decks"),
DRAFT_DECKS ("Draft Decks"),

View File

@@ -498,40 +498,18 @@ public class DeckgenUtil {
final DeckFormat format = gameType.getDeckFormat();
Predicate<CardRules> canPlay = forAi ? DeckGeneratorBase.AI_CAN_PLAY : DeckGeneratorBase.HUMAN_CAN_PLAY;
@SuppressWarnings("unchecked")
Iterable<PaperCard> legends = cardDb.getAllCards(Predicates.compose(Predicates.and(
Iterable<PaperCard> legends = cardDb.getAllCards(Predicates.and(format.isLegalCardPredicate(),
Predicates.compose(Predicates.and(
new Predicate<CardRules>() {
@Override
public boolean apply(CardRules rules) {
return format.isLegalCommander(rules);
}
},
canPlay), PaperCard.FN_GET_RULES));
canPlay), PaperCard.FN_GET_RULES)));
do {
commander = Aggregates.random(legends);
colorID = commander.getRules().getColorIdentity();
} while (colorID.countColors() != 2);
List<String> comColors = new ArrayList<String>(2);
if (colorID.hasWhite()) { comColors.add("White"); }
if (colorID.hasBlue()) { comColors.add("Blue"); }
if (colorID.hasBlack()) { comColors.add("Black"); }
if (colorID.hasRed()) { comColors.add("Red"); }
if (colorID.hasGreen()) { comColors.add("Green"); }
DeckGeneratorBase gen = null;
gen = new DeckGenerator2Color(cardDb, format, comColors.get(0), comColors.get(1));
gen.setSingleton(true);
gen.setUseArtifacts(!FModel.getPreferences().getPrefBoolean(FPref.DECKGEN_ARTIFACTS));
CardPool cards = gen.getDeck(gameType.getDeckFormat().getMainRange().getMaximum(), forAi);
// After generating card lists, build deck.
deck = new Deck("Generated " + gameType.toString() + " deck (" + commander.getName() + ")");
deck.setDirectory("generated/commander");
deck.getMain().addAll(cards);
deck.getOrCreate(DeckSection.Commander).add(commander);
return deck;
commander = Aggregates.random(legends);
return generateRandomCommanderDeck(commander, format, forAi, false);
}
/** Generate a ramdom Commander deck. */
@@ -542,7 +520,11 @@ public class DeckgenUtil {
PaperCard selectedPartner=null;
if(isCardGen){
List<Map.Entry<PaperCard,Integer>> potentialCards = new ArrayList<>();
potentialCards.addAll(CardRelationMatrixGenerator.cardPools.get(DeckFormat.Commander.toString()).get(commander.getName()));
if(format.equals(DeckFormat.Brawl)){//TODO: replace with actual Brawl based data
potentialCards.addAll(CardRelationMatrixGenerator.cardPools.get(FModel.getFormats().getStandard().getName()).get(commander.getName()));
}else {
potentialCards.addAll(CardRelationMatrixGenerator.cardPools.get(DeckFormat.Commander.toString()).get(commander.getName()));
}
Random r = new Random();
//Collections.shuffle(potentialCards, r);
List<PaperCard> preSelectedCards = new ArrayList<>();
@@ -588,11 +570,21 @@ public class DeckgenUtil {
cardDb = FModel.getMagicDb().getCommonCards();
//shuffle first 400 random cards
Iterable<PaperCard> colorList = Iterables.filter(format.getCardPool(cardDb).getAllCards(),
Predicates.compose(Predicates.or(new CardThemedDeckBuilder.MatchColorIdentity(commander.getRules().getColorIdentity()),
DeckGeneratorBase.COLORLESS_CARDS), PaperCard.FN_GET_RULES));
Predicates.and(format.isLegalCardPredicate(),Predicates.compose(Predicates.or(
new CardThemedDeckBuilder.MatchColorIdentity(commander.getRules().getColorIdentity()),
DeckGeneratorBase.COLORLESS_CARDS), PaperCard.FN_GET_RULES)));
if(format.equals(DeckFormat.Brawl)){//for Brawl - add additional filterprinted rule to remove old reprints for a consistent look
Iterable<PaperCard> colorListFiltered = Iterables.filter(colorList,FModel.getFormats().getStandard().getFilterPrinted());
colorList=colorListFiltered;
}
List<PaperCard> cardList = Lists.newArrayList(colorList);
Collections.shuffle(cardList, new Random());
List<PaperCard> shortList = cardList.subList(1, 400);
int shortlistlength=400;
if(cardList.size()<shortlistlength){
shortlistlength=cardList.size();
}
List<PaperCard> shortList = cardList.subList(1, shortlistlength);
shortList.remove(commander);
gen = new CardThemedCommanderDeckBuilder(commander, selectedPartner,shortList,forAi,format);
}

View File

@@ -80,6 +80,8 @@ public class RandomDeckGenerator extends DeckProxy implements Comparable<RandomD
return DeckgenUtil.generateCommanderDeck(isAi, GameType.Commander);
case TinyLeaders:
return DeckgenUtil.generateCommanderDeck(isAi, GameType.TinyLeaders);
case Brawl:
return DeckgenUtil.generateCommanderDeck(isAi, GameType.Brawl);
case Archenemy:
return DeckgenUtil.generateSchemeDeck();
case Planechase:
@@ -135,6 +137,9 @@ public class RandomDeckGenerator extends DeckProxy implements Comparable<RandomD
case TinyLeaders:
decks = DeckProxy.getAllTinyLeadersDecks(DeckFormat.TinyLeaders.isLegalDeckPredicate());
break;
case Brawl:
decks = DeckProxy.getAllBrawlDecks(DeckFormat.Brawl.isLegalDeckPredicate());
break;
case Archenemy:
decks = DeckProxy.getAllSchemeDecks(DeckFormat.Archenemy.isLegalDeckPredicate());
break;

View File

@@ -21,7 +21,7 @@ import org.w3c.dom.NodeList;
*
*/
public class DeckPreferences {
private static String currentDeck = "", draftDeck = "", sealedDeck = "", commanderDeck = "", tinyLeadersDeck = "", planarDeck = "", schemeDeck = "";
private static String currentDeck = "", draftDeck = "", sealedDeck = "", commanderDeck = "", tinyLeadersDeck = "", brawlDeck = "", planarDeck = "", schemeDeck = "";
private static Map<String, DeckPreferences> allPrefs = new HashMap<String, DeckPreferences>();
public static String getCurrentDeck() {
@@ -69,6 +69,15 @@ public class DeckPreferences {
save();
}
public static String getBrawlDeck() {
return brawlDeck;
}
public static void setBrawlDeck(String brawlDeck0) {
if (brawlDeck.equals(brawlDeck0)) { return; }
brawlDeck = brawlDeck0;
save();
}
public static String getPlanarDeck() {
return planarDeck;
}

View File

@@ -232,10 +232,17 @@ public abstract class GameLobby implements IHasGameType {
break;
case Commander:
data.appliedVariants.remove(GameType.TinyLeaders);
data.appliedVariants.remove(GameType.Brawl);
data.appliedVariants.remove(GameType.MomirBasic);
break;
case TinyLeaders:
data.appliedVariants.remove(GameType.Commander);
data.appliedVariants.remove(GameType.Brawl);
data.appliedVariants.remove(GameType.MomirBasic);
break;
case Brawl:
data.appliedVariants.remove(GameType.Commander);
data.appliedVariants.remove(GameType.TinyLeaders);
data.appliedVariants.remove(GameType.MomirBasic);
break;
case Vanguard:
@@ -244,6 +251,7 @@ public abstract class GameLobby implements IHasGameType {
case MomirBasic:
data.appliedVariants.remove(GameType.Commander);
data.appliedVariants.remove(GameType.TinyLeaders);
data.appliedVariants.remove(GameType.Brawl);
data.appliedVariants.remove(GameType.Vanguard);
break;
default:
@@ -263,6 +271,8 @@ public abstract class GameLobby implements IHasGameType {
currentGameType = GameType.Commander;
} else if (hasVariant(GameType.TinyLeaders)) {
currentGameType = GameType.TinyLeaders;
} else if (hasVariant(GameType.Brawl)) {
currentGameType = GameType.Brawl;
} else {
currentGameType = GameType.Constructed;
}
@@ -326,7 +336,7 @@ public abstract class GameLobby implements IHasGameType {
SOptionPane.showMessageDialog(TextUtil.concatNoSpace("Please specify a deck for ", slot.getName()));
return null;
}
if (hasVariant(GameType.Commander) || hasVariant(GameType.TinyLeaders)) {
if (hasVariant(GameType.Commander) || hasVariant(GameType.TinyLeaders) || hasVariant(GameType.Brawl)) {
if (!slot.getDeck().has(DeckSection.Commander)) {
SOptionPane.showMessageDialog(TextUtil.concatNoSpace(slot.getName(), " doesn't have a commander"));
return null;
@@ -339,9 +349,11 @@ public abstract class GameLobby implements IHasGameType {
GameType autoGenerateVariant = null;
boolean isCommanderMatch = false;
boolean isTinyLeadersMatch = false;
boolean isBrawlMatch = false;
if (!variantTypes.isEmpty()) {
isTinyLeadersMatch = variantTypes.contains(GameType.TinyLeaders);
isCommanderMatch = isTinyLeadersMatch || variantTypes.contains(GameType.Commander);
isBrawlMatch = variantTypes.contains(GameType.Brawl);
isCommanderMatch = isBrawlMatch || isTinyLeadersMatch || variantTypes.contains(GameType.Commander);
if (!isCommanderMatch) {
for (final GameType variant : variantTypes) {
if (variant.isAutoGenerated()) {
@@ -403,7 +415,7 @@ public abstract class GameLobby implements IHasGameType {
else {
PaperCard vanguardAvatar = null;
if (isCommanderMatch) {
final GameType commanderGameType = isTinyLeadersMatch ? GameType.TinyLeaders : GameType.Commander;
final GameType commanderGameType = isTinyLeadersMatch ? GameType.TinyLeaders : isBrawlMatch ? GameType.Brawl : GameType.Commander;
if (checkLegality) {
final String errMsg = commanderGameType.getDeckFormat().getDeckConformanceProblem(deck);
if (errMsg != null) {

View File

@@ -42,6 +42,7 @@ public class CardCollections {
private IStorage<Deck> plane;
private IStorage<Deck> commander;
private IStorage<Deck> tinyLeaders;
private IStorage<Deck> brawl;
public CardCollections() {
}
@@ -118,4 +119,12 @@ public class CardCollections {
}
return tinyLeaders;
}
public IStorage<Deck> getBrawl() {
if (brawl == null) {
brawl = new StorageImmediatelySerialized<Deck>("Brawl decks",
new DeckStorage(new File(ForgeConstants.DECK_BRAWL_DIR), ForgeConstants.DECK_BASE_DIR));
}
return brawl;
}
}

View File

@@ -173,6 +173,9 @@ public final class FModel {
formats.add(format);
}
magicDb.setStandardPredicate(formats.getStandard().getFilterRules());
magicDb.setModernPredicate(formats.getModern().getFilterRules());
blocks = new StorageBase<>("Block definitions", new CardBlock.Reader(ForgeConstants.BLOCK_DATA_DIR + "blocks.txt", magicDb.getEditions()));
questPreferences = new QuestPreferences();
conquestPreferences = new ConquestPreferences();

View File

@@ -219,6 +219,7 @@ public final class ForgeConstants {
public static final String QUEST_SAVE_DIR = USER_QUEST_DIR + "saves" + PATH_SEPARATOR;
public static final String CONQUEST_SAVE_DIR = USER_CONQUEST_DIR + "saves" + PATH_SEPARATOR;
public static final String DECK_TINY_LEADERS_DIR= DECK_BASE_DIR + "tiny_leaders" + PATH_SEPARATOR;
public static final String DECK_BRAWL_DIR = DECK_BASE_DIR + "brawl" + PATH_SEPARATOR;
public static final String MAIN_PREFS_FILE = USER_PREFS_DIR + "forge.preferences";
public static final String CARD_PREFS_FILE = USER_PREFS_DIR + "card.preferences";
public static final String DECK_PREFS_FILE = USER_PREFS_DIR + "deck.preferences";

View File

@@ -50,6 +50,14 @@ public class ForgePreferences extends PreferencesStore<ForgePreferences.FPref> {
TINY_LEADER_P6_DECK_STATE(""),
TINY_LEADER_P7_DECK_STATE(""),
TINY_LEADER_P8_DECK_STATE(""),
BRAWL_P1_DECK_STATE(""),
BRAWL_P2_DECK_STATE(""),
BRAWL_P3_DECK_STATE(""),
BRAWL_P4_DECK_STATE(""),
BRAWL_P5_DECK_STATE(""),
BRAWL_P6_DECK_STATE(""),
BRAWL_P7_DECK_STATE(""),
BRAWL_P8_DECK_STATE(""),
UI_LANDSCAPE_MODE ("false"),
UI_COMPACT_MAIN_MENU ("false"),
UI_USE_OLD ("false"),
@@ -240,6 +248,12 @@ public class ForgePreferences extends PreferencesStore<ForgePreferences.FPref> {
TINY_LEADER_P5_DECK_STATE, TINY_LEADER_P6_DECK_STATE,
TINY_LEADER_P7_DECK_STATE, TINY_LEADER_P8_DECK_STATE };
public static FPref[] BRAWL_DECK_STATES = {
BRAWL_P1_DECK_STATE, BRAWL_P2_DECK_STATE,
BRAWL_P3_DECK_STATE, BRAWL_P4_DECK_STATE,
BRAWL_P5_DECK_STATE, BRAWL_P6_DECK_STATE,
BRAWL_P7_DECK_STATE, BRAWL_P8_DECK_STATE };
}
/** Instantiates a ForgePreferences object. */