예제 #1
0
  /**
   * Once any non-basic lands are added, add basic lands until the deck is filled.
   *
   * @param landsNeeded how many remaining lands are needed.
   * @param percentage the percentage needed for each color in the final deck.
   * @param count how many of each color can be produced by non-basic lands.
   * @param basicLands list of information about basic lands from the database.
   */
  private static void addBasicLands(
      int landsNeeded,
      Map<String, Double> percentage,
      Map<String, Integer> count,
      Map<String, List<CardInfo>> basicLands) {
    int colorTotal = 0;
    ColoredManaSymbol colorToAdd = null;

    // Add up the totals for all colors, to keep track of the percentage a color is.
    for (Map.Entry<String, Integer> c : count.entrySet()) {
      colorTotal += c.getValue();
    }

    // Keep adding basic lands until we fill the deck
    while (landsNeeded > 0) {

      double minPercentage = Integer.MIN_VALUE;

      for (ColoredManaSymbol color : ColoredManaSymbol.values()) {
        // What percentage of this color is requested
        double neededPercentage = percentage.get(color.toString());
        // If there is a 0% need for basic lands of this color, skip it
        if (neededPercentage <= 0) {
          continue;
        }
        int currentCount = count.get(color.toString());
        double thisPercentage = 0.0;
        // Calculate the percentage of lands so far that produce this color
        if (currentCount > 0) thisPercentage = (currentCount / (double) colorTotal) * 100.0;
        // Check if the color is the most "needed" (highest percentage) we have seen so far
        if (neededPercentage - thisPercentage > minPercentage) {
          // Put this color land forward to be added
          colorToAdd = color;
          minPercentage = (neededPercentage - thisPercentage);
        }
      }
      if (colorToAdd != null) {
        genPool.addCard(getBasicLand(colorToAdd, basicLands));
        count.put(colorToAdd.toString(), count.get(colorToAdd.toString()) + 1);
        colorTotal++;
        landsNeeded--;
      }
    }
  }
예제 #2
0
  /**
   * Generates all the lands for the deck. Generates non-basic if selected by the user and if the
   * deck isn't monocolored. Will fetch non-basic lands if required and then fill up the remaining
   * space with basic lands. Basic lands are adjusted according to the mana symbols seen in the
   * cards used in this deck. Usually the lands will be well balanced relative to the color of
   * cards.
   *
   * @param criteria the criteria of the lands to search for in the database.
   * @param landsCount the amount of lands required for this deck.
   * @param basicLands information about the basic lands from the sets used.
   */
  private static void generateLands(
      CardCriteria criteria, int landsCount, Map<String, List<CardInfo>> basicLands) {

    int tries = 0;
    int countNonBasic = 0;
    // Store the nonbasic lands (if any) we'll add
    List<Card> deckLands = new ArrayList<>();

    // Calculates the percentage of colored mana symbols over all spells in the deck
    Map<String, Double> percentage = genPool.calculateSpellColorPercentages();

    // Only dual/tri color lands are generated for now, and not non-basic lands that only produce
    // colorless mana.
    if (!genPool.isMonoColoredDeck() && genDialog.useNonBasicLand()) {
      List<Card> landCards = genPool.filterLands(CardRepository.instance.findCards(criteria));
      int allCount = landCards.size();
      Random random = new Random();
      if (allCount > 0) {
        while (countNonBasic < landsCount / 2) {
          Card card = landCards.get(random.nextInt(allCount));
          if (genPool.isValidLandCard(card)) {
            Card addedCard = card.copy();
            deckLands.add(addedCard);
            genPool.addCard(addedCard);
            countNonBasic++;
          }
          tries++;
          // to avoid infinite loop
          if (tries > MAX_TRIES) {
            // Not a problem, just use what we have
            break;
          }
        }
      }
    }
    // Calculate the amount of colored mana already can be produced by the non-basic lands
    Map<String, Integer> count = genPool.countManaProduced(deckLands);
    // Fill up the rest of the land quota with basic lands adjusted to fit the deck's mana costs
    addBasicLands(landsCount - countNonBasic, percentage, count, basicLands);
  }
예제 #3
0
 /**
  * Generates all spells for the deck. Each card is retrieved from the database and checked against
  * the converted mana cost (CMC) needed for the current card pool. If a card's CMC matches the CMC
  * range required by the pool, it is added to the deck. This ensures that the majority of cards
  * fit a fixed mana curve for the deck, and it is playable. Creatures and non-creatures are
  * retrieved separately to ensure the deck contains a reasonable mix of both.
  *
  * @param criteria the criteria to search for in the database.
  * @param spellCount the number of spells that match the criteria needed in the deck.
  */
 private static void generateSpells(CardCriteria criteria, int spellCount) {
   List<CardInfo> cardPool = CardRepository.instance.findCards(criteria);
   int retrievedCount = cardPool.size();
   List<DeckGeneratorCMC> deckCMCs = genPool.getCMCsForSpellCount(spellCount);
   Random random = new Random();
   int count = 0;
   int reservesAdded = 0;
   if (retrievedCount > 0 && retrievedCount >= spellCount) {
     int tries = 0;
     while (count < spellCount) {
       Card card = cardPool.get(random.nextInt(retrievedCount)).getMockCard();
       if (genPool.isValidSpellCard(card)) {
         int cardCMC = card.getManaCost().convertedManaCost();
         for (DeckGeneratorCMC deckCMC : deckCMCs) {
           if (cardCMC >= deckCMC.min && cardCMC <= deckCMC.max) {
             int currentAmount = deckCMC.getAmount();
             if (currentAmount > 0) {
               deckCMC.setAmount(currentAmount - 1);
               genPool.addCard(card.copy());
               count++;
             }
           } else {
             if (reservesAdded < genPool.getDeckSize() / 2) {
               genPool.tryAddReserve(card, cardCMC);
               reservesAdded++;
             }
           }
         }
       }
       tries++;
       if (tries > MAX_TRIES) {
         // Break here, we'll fill in random missing ones later
         break;
       }
     }
   } else {
     throw new IllegalStateException("Not enough cards to generate deck.");
   }
 }