public GameState( IGameLog gameLog, IPlayerAction[] players, GameConfig gameConfig, Random random, IEnumerable<CardCountPair>[] startingDeckPerPlayer = null) { int playerCount = players.Length; this.gameLog = gameLog; this.cardGameSubset = gameConfig.cardGameSubset; this.supplyPiles = gameConfig.GetSupplyPiles(playerCount, random); this.nonSupplyPiles = gameConfig.GetNonSupplyPiles(); this.mapCardToPile = new MapOfCards<PileOfCards>(this.cardGameSubset); this.BuildMapOfCardToPile(); this.players = new PlayerCircle(playerCount, players, this.gameLog, random, this.cardGameSubset); this.hasPileEverBeenGained = new MapPileOfCardsToProperty<bool>(this.supplyPiles); this.pileEmbargoTokenCount = new MapPileOfCardsToProperty<int>(this.supplyPiles); this.trash = new BagOfCards(this.cardGameSubset); this.GainStartingCards(gameConfig); this.players.AllPlayersDrawInitialCards(gameConfig); foreach (PileOfCards cardPile in this.supplyPiles) { cardPile.ProtoTypeCard.DoSpecializedSetupIfInSupply(this); } }
internal PlayerState(IPlayerAction actions, int playerIndex, IGameLog gameLog, Random random, CardGameSubset gameSubset) { this.gameLog = gameLog; this.actions = new PlayerActionWithSelf(actions, this); this.playPhase = PlayPhase.NotMyTurn; this.random = random; this.playerIndex = playerIndex; // duplicates this.allOwnedCards = new BagOfCards(gameSubset); this.cardsInPlay = new BagOfCards(gameSubset, this.allOwnedCards); this.cardsInPlayAtBeginningOfCleanupPhase = new BagOfCards(gameSubset); // partition this.islandMat = new BagOfCards(gameSubset, this.allOwnedCards); this.nativeVillageMat = new BagOfCards(gameSubset, this.allOwnedCards); this.deck = new ListOfCards(gameSubset, this.allOwnedCards); this.discard = new BagOfCards(gameSubset, this.allOwnedCards); this.cardsBeingPlayed = new ListOfCards(gameSubset, this.allOwnedCards); // a stack for recursion this.cardsBeingRevealed = new BagOfCards(gameSubset, this.allOwnedCards); this.hand = new BagOfCards(gameSubset, this.allOwnedCards); this.cardsPlayed = new BagOfCards(gameSubset, this.cardsInPlay); this.durationCards = new BagOfCards(gameSubset, this.cardsInPlay); this.cardsToReturnToHandAtStartOfTurn = new BagOfCards(gameSubset, this.allOwnedCards); this.cardToPass = new SingletonCardHolder(this.allOwnedCards); this.cardBeingDiscarded = new ListOfCards(gameSubset, this.allOwnedCards); this.turnCounters = new PlayerTurnCounters(gameSubset); }
private static void InsertCardData( HtmlRenderer htmlWriter, string title, CardGameSubset gameSubset, MapOfCardsForGameSubset <ForwardAndReversePerTurnPlayerCounters> statsPerCard, ForwardAndReversePerTurnPlayerCounters turnCounts, int playerIndex, int throughTurn) { Card[] cards = gameSubset.OrderBy(card => card.DefaultCoinCost).ToArray(); string[] seriesLabel = new string[cards.Length]; int[] xAxis = Enumerable.Range(1, throughTurn).ToArray(); float[][] seriesData = new float[cards.Length][]; for (int i = 0; i < cards.Length; i++) { seriesLabel[i] = cards[i].name; seriesData[i] = statsPerCard[cards[i]].forwardTotal.GetAveragePerTurn(playerIndex, throughTurn, turnCounts.forwardTotal); } htmlWriter.InsertExpander(title, delegate() { htmlWriter.InsertLineGraph(title, "Turn", seriesLabel, xAxis, seriesData); }, collapseByDefault: true); }
private PlayerState[] players; // circular list, higher numbers to the left; #endregion Fields #region Constructors public PlayerCircle(int playerCount, IPlayerAction[] players, IGameLog gameLog, Random random, CardGameSubset gameSubset) { this.players = new PlayerState[playerCount]; for (int playerIndex = 0; playerIndex < this.players.Length; ++playerIndex) { this.players[playerIndex] = new PlayerState(players[playerIndex], playerIndex, gameLog, random, gameSubset); } this.currentPlayerIndex = 0; }
private static void Add(CardGameSubset gameSubset, List<PileOfCards> cardPiles, int initialCount, Card protoType) { if (gameSubset.isInitializing) { gameSubset.AddCard(protoType); } else { cardPiles.Add(new PileOfCards(gameSubset, protoType, initialCount)); } }
public GameConfig( GameDescription gameDescription, MapPlayerGameConfigToCardSet startingDecks = null, MapPlayerGameConfigToCardSet startingHands = null) { this.gameDescription = gameDescription; this.startingDeck = startingDecks; this.startingHand = startingHands; this.cardGameSubset = new CardGameSubset(); var availabilities = GetCardAvailability(1, CardAvailabilityType.AllPossibleCardsInGame); foreach(var availability in availabilities) this.cardGameSubset.AddCard(availability.card); }
public GameConfig( Card[] supplyPiles, bool useShelters, bool useColonyAndPlatinum, MapPlayerGameConfigToCardSet startingDecks = null, MapPlayerGameConfigToCardSet startingHands = null) { this.useShelters = useShelters; this.useColonyAndPlatinum = useColonyAndPlatinum; this.kingdomPiles = supplyPiles; this.startingDeck = startingDecks; this.startingHand = startingHands; this.cardGameSubset = new CardGameSubset(); GetSupplyPiles(1, null, this.cardGameSubset); GetNonSupplyPiles(this.cardGameSubset); this.cardGameSubset.isInitializing = false; }
private static PileOfCards CreateRuins(CardGameSubset gameSubset, int ruinsCount, Random random) { if (gameSubset.isInitializing) { gameSubset.AddCard(Cards.Ruins); gameSubset.AddCard(Cards.AbandonedMine); gameSubset.AddCard(Cards.RuinedMarket); gameSubset.AddCard(Cards.RuinedLibrary); gameSubset.AddCard(Cards.RuinedVillage); gameSubset.AddCard(Cards.Survivors); return null; } else { int ruinCountPerPile = 10; var allRuinsCards = new ListOfCards(gameSubset); allRuinsCards.AddNCardsToTop(Cards.AbandonedMine, ruinCountPerPile); allRuinsCards.AddNCardsToTop(Cards.RuinedMarket, ruinCountPerPile); allRuinsCards.AddNCardsToTop(Cards.RuinedLibrary, ruinCountPerPile); allRuinsCards.AddNCardsToTop(Cards.RuinedVillage, ruinCountPerPile); allRuinsCards.AddNCardsToTop(Cards.Survivors, ruinCountPerPile); allRuinsCards.Shuffle(random); var result = new PileOfCards(gameSubset, Cards.Ruins); for (int i = 0; i < ruinsCount; ++i) { Card card = allRuinsCards.DrawCardFromTop(); if (card == null) { throw new Exception("Not enough ruins available."); } result.AddCardToTop(card); } result.EraseKnownCountKnowledge(); return result; } }
public StatsPerTurnGameLog(int playerCount, CardGameSubset gameSubset) { this.turnCounters = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.coinToSpend = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.cardsGained = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.ruinsGained = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.cursesGained = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.cursesTrashed = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.victoryPointTotal = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.deckShuffleCount = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.oddsOfBeingAheadOnRoundEnd = new ForwardAndReversePerTurnPlayerCounters(playerCount); this.oddsOfHittingAtLeastACoinAmount = new ForwardAndReversePerTurnPlayerCounters[9]; for (int i = 0; i < this.oddsOfHittingAtLeastACoinAmount.Length; ++i) { this.oddsOfHittingAtLeastACoinAmount[i] = new ForwardAndReversePerTurnPlayerCounters(playerCount); } this.cardGameSubset = gameSubset; this.cardsTotalCount = ContstructCounterPerTurn(playerCount, gameSubset); this.carsGainedOnTurn = ContstructCounterPerTurn(playerCount, gameSubset); this.endOfGameCardCount = ContstructCounter(playerCount, gameSubset); }
public ListOfCards(CardGameSubset gameSubset) : base(gameSubset, null) { }
public BagOfCards(CardGameSubset gameSubset) : this(gameSubset, null) { }
internal PlayerTurnCounters(CardGameSubset gameSubset) { cardsBannedFromPurchase = new SetOfCards(gameSubset); cardsBoughtThisTurn = new SetOfCards(gameSubset); cardsGainedThisTurn = new SetOfCards(gameSubset); }
public PileOfCards(CardGameSubset gameSubset, Card protoType, int count) : base(gameSubset) { this.AddNCardsToTop(protoType, count); this.protoType = protoType; }
private static void InsertCardData(HtmlRenderer htmlWriter, MapOfCardsForGameSubset<PlayerCounterSeparatedByGame> map, CardGameSubset gameSubset, PlayerAction player1, PlayerAction player2) { var cards = gameSubset.OrderBy(c => c.DefaultCoinCost); var player1Data = new List<float>(); var player2Data = new List<float>(); foreach (Card card in cards) { player1Data.Add(map[card].GetAverage(playerIndex: 0)); player2Data.Add(map[card].GetAverage(playerIndex: 1)); } htmlWriter.InsertExpander("Cards Report", delegate() { htmlWriter.InsertColumnChart( "Average Count of Cards Owned at End of Game", "Card", new string[] { player1.PlayerName, player2.PlayerName}, cards.Select(c => c.name).ToArray(), new float[][] { player1Data.ToArray(), player2Data.ToArray() }); }, collapseByDefault: false); }
public PileOfCards(CardGameSubset gameSubset, Card protoType) : base(gameSubset) { this.protoType = protoType; }
private MapOfCardsForGameSubset<PlayerCounterSeparatedByGame> ContstructCounter(int playerCount, CardGameSubset gameSubset) { var result = new MapOfCardsForGameSubset<PlayerCounterSeparatedByGame>(gameSubset); foreach (Card card in gameSubset) { result[card] = new PlayerCounterSeparatedByGame(playerCount); } return result; }
private MapOfCardsForGameSubset <ForwardAndReversePerTurnPlayerCounters> ContstructCounterPerTurn(int playerCount, CardGameSubset gameSubset) { var result = new MapOfCardsForGameSubset <ForwardAndReversePerTurnPlayerCounters>(gameSubset); foreach (Card card in gameSubset) { result[card] = new ForwardAndReversePerTurnPlayerCounters(playerCount); } return(result); }
private MapOfCardsForGameSubset <PlayerCounterSeparatedByGame> ContstructCounter(int playerCount, CardGameSubset gameSubset) { var result = new MapOfCardsForGameSubset <PlayerCounterSeparatedByGame>(gameSubset); foreach (Card card in gameSubset) { result[card] = new PlayerCounterSeparatedByGame(playerCount); } return(result); }
public ListOfCards(CardGameSubset gameSubset, BagOfCards parent) : base(gameSubset, parent) { }
private MapOfCardsForGameSubset<ForwardAndReversePerTurnPlayerCounters> ContstructCounterPerTurn(int playerCount, CardGameSubset gameSubset) { var result = new MapOfCardsForGameSubset<ForwardAndReversePerTurnPlayerCounters>(gameSubset); foreach (Card card in gameSubset) { result[card] = new ForwardAndReversePerTurnPlayerCounters(playerCount); } return result; }
private PileOfCards[] GetNonSupplyPiles(CardGameSubset gameSubset) { var nonSupplyCardPiles = new List<PileOfCards>(); if (this.useShelters) { gameSubset.AddCard(Cards.Necropolis); gameSubset.AddCard(Cards.Hovel); gameSubset.AddCard(Cards.OvergrownEstate); } if (this.kingdomPiles.Where(card => card.requiresSpoils).Any()) { Add(gameSubset, nonSupplyCardPiles, 16, Cards.Spoils); } if (this.kingdomPiles.Where(card => card == Cards.Hermit).Any()) { Add(gameSubset, nonSupplyCardPiles, 10, Cards.Madman); } if (this.kingdomPiles.Where(card => card == Cards.Urchin).Any()) { Add(gameSubset, nonSupplyCardPiles, 10, Cards.Mercenary); } return nonSupplyCardPiles.ToArray(); }
internal PlayerTurnCounters(CardGameSubset gameSubset) { cardsBannedFromPurchase = new SetOfCards(gameSubset); }
private PileOfCards[] GetSupplyPiles(int playerCount, Random random, CardGameSubset gameSubset) { var supplyCardPiles = new List<PileOfCards>(capacity: 20); int curseCount = (playerCount - 1) * 10; int ruinsCount = curseCount; int victoryCount = (playerCount == 2) ? 8 : 12; // cards always in the supply Add(gameSubset, supplyCardPiles, 60, Cards.Copper); Add(gameSubset, supplyCardPiles, 40, Cards.Silver); Add(gameSubset, supplyCardPiles, 30, Cards.Gold); Add(gameSubset, supplyCardPiles, curseCount, Cards.Curse); Add(gameSubset, supplyCardPiles, victoryCount + (!this.useShelters ? playerCount * 3 : 0), Cards.Estate); Add(gameSubset, supplyCardPiles, victoryCount, Cards.Duchy); Add(gameSubset, supplyCardPiles, victoryCount, Cards.Province); if (this.useColonyAndPlatinum) { Add(gameSubset, supplyCardPiles, victoryCount, Cards.Colony); Add(gameSubset, supplyCardPiles, 20, Cards.Platinum); } if (this.kingdomPiles.Where(card => card.potionCost != 0).Any()) { Add(gameSubset, supplyCardPiles, 16, Cards.Potion); } else { gameSubset.AddCard(Cards.Potion); } if (this.kingdomPiles.Where(card => card.requiresRuins).Any()) { supplyCardPiles.Add(CreateRuins(gameSubset, ruinsCount, random)); } foreach (Card card in this.kingdomPiles) { if (card.isVictory) { Add(gameSubset, supplyCardPiles, victoryCount, card); } else { Add(gameSubset, supplyCardPiles, card.defaultSupplyCount, card); } } return supplyCardPiles.ToArray(); }
private static void InsertCardData(HtmlRenderer htmlWriter, MapOfCardsForGameSubset <PlayerCounterSeparatedByGame> map, CardGameSubset gameSubset, PlayerAction player1, PlayerAction player2) { var cards = gameSubset.OrderBy(c => c.DefaultCoinCost); var player1Data = new List <float>(); var player2Data = new List <float>(); foreach (Card card in cards) { player1Data.Add(map[card].GetAverage(playerIndex: 0)); player2Data.Add(map[card].GetAverage(playerIndex: 1)); } htmlWriter.InsertExpander("Cards Report", delegate() { htmlWriter.InsertColumnChart( "Average Count of Cards Owned at End of Game", "Card", new string[] { player1.PlayerName, player2.PlayerName }, cards.Select(c => c.name).ToArray(), new float[][] { player1Data.ToArray(), player2Data.ToArray() }); }, collapseByDefault: false); }
private static void InsertCardData( HtmlRenderer htmlWriter, string title, CardGameSubset gameSubset, MapOfCardsForGameSubset<ForwardAndReversePerTurnPlayerCounters> statsPerCard, ForwardAndReversePerTurnPlayerCounters turnCounts, int playerIndex, int throughTurn) { Card[] cards = gameSubset.OrderBy(card => card.DefaultCoinCost).ToArray(); string[] seriesLabel = new string[cards.Length]; int[] xAxis = Enumerable.Range(1, throughTurn).ToArray(); float[][] seriesData = new float[cards.Length][]; for (int i = 0; i < cards.Length; i++) { seriesLabel[i] = cards[i].name; seriesData[i] = statsPerCard[cards[i]].forwardTotal.GetAveragePerTurn(playerIndex, throughTurn, turnCounts.forwardTotal); } htmlWriter.InsertExpander(title, delegate() { htmlWriter.InsertLineGraph(title, "Turn", seriesLabel, xAxis, seriesData); }, collapseByDefault: true); }