/// <summary> /// Refreshes the cache monitor screen ouput with the current state of the cache. /// </summary> public void updateTableUI() { lock (locker) { if (genericCache == null) { //Just clear everything and wait for the cache to be set. resetAllTableElements(); } else { #region updatingNow //Prevent any more changes from happening to the cache while the table is updated genericCache.startRead(); //Update hands played handsPlayed.Text = genericCache.getNumHandsPlayed().ToString(); //It's possible the table tries to update exactly after a hand has finished //In this particular case for now we are just going to exit updateTableUI if (genericCache.currentHandExists()) { currentHandDetails = genericCache.getCurrentHandDetails(); currentPlayerDetails = genericCache.getPlayerDetails(); //Disable unused seats disableUnusedSeats(genericCache.NumSeats); //Get any new actions if (lastLocalIndex[0] == -1) { playActions = genericCache.getAllHandActions(); } else { playActions = genericCache.getHandActionsBasedOnLocalIndex(lastLocalIndex[0], (byte)lastLocalIndex[1]); } //Once we have actions we record the last one we go if (playActions.Length > 0) { lastLocalIndex[0] = playActions.Last().handId; lastLocalIndex[1] = playActions.Last().localIndex; } //Only update hand information if a current hand exists if (currentHandDetails.currentHandExists) { if (currentHandId != currentHandDetails.handId) { currentHandId = currentHandDetails.handId; handHistory.AppendText("\n\nNew Hand Started - HandId " + currentHandId.ToString() + "\n\n"); echoHoleCards = 0; resetAllTableElements(); } moveDealerButton(currentHandDetails.dealerPosition); potValue.Text = currentHandDetails.potValue.ToString(); if (currentHandDetails.tableCard1 != (byte)Card.NoCard) { setCard(currentHandDetails.tableCard1, tableCard1); } if (currentHandDetails.tableCard2 != (byte)Card.NoCard) { setCard(currentHandDetails.tableCard2, tableCard2); } if (currentHandDetails.tableCard3 != (byte)Card.NoCard) { setCard(currentHandDetails.tableCard3, tableCard3); } if (currentHandDetails.tableCard4 != (byte)Card.NoCard) { setCard(currentHandDetails.tableCard4, tableCard4); } if (currentHandDetails.tableCard5 != (byte)Card.NoCard) { setCard(currentHandDetails.tableCard5, tableCard5); } } //Actions which also update the useraction box //Call, Raise & Check //Big & Little Blind //Fold //Wins //Need to update actions //Add all actions in playActions to chat window for (int i = 0; i < playActions.GetLength(0); i++) { actionString = "Player Name: " + genericCache.getPlayerName(playActions.ElementAt(i).playerId) + ", Action: " + playActions.ElementAt(i).actionType.ToString() + ", Action Value: " + playActions.ElementAt(i).actionValue.ToString() + "\n"; #region actionStringSwtich switch (playActions.ElementAt(i).actionType) { case PokerAction.JoinTable: actionString = "[Dealer] " + genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " sits down at the table."; break; case PokerAction.LeaveTable: actionString = "[Dealer] " + genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " leaves the table."; break; case PokerAction.SitOut: sitInOutPlayer(genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), false); actionString = "[Dealer] " + genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " is now sitting out."; break; case PokerAction.SitIn: sitInOutPlayer(genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), true); actionString = "[Dealer] " + genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " is now playing again."; break; case PokerAction.LittleBlind: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " posts the little blind."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "LB - " + genericCache.LittleBlind.ToString(); break; case PokerAction.BigBlind: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " posts the big blind."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "BB - " + genericCache.BigBlind.ToString(); break; case PokerAction.Fold: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " folds."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Fold"; clearCard((PictureBox)playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 2]); clearCard((PictureBox)playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 3]); break; case PokerAction.Check: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " checks."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Check"; break; case PokerAction.Call: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " calls " + playActions.ElementAt(i).actionValue.ToString() + "."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Call - " + playActions.ElementAt(i).actionValue.ToString(); break; case PokerAction.Raise: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " raises to " + playActions.ElementAt(i).actionValue.ToString() + "."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Raise - " + playActions.ElementAt(i).actionValue.ToString(); break; case PokerAction.WinPot: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " wins " + playActions.ElementAt(i).actionValue.ToString() + "."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Wins " + playActions.ElementAt(i).actionValue.ToString(); echoHoleCards = 1; break; case PokerAction.AddStackCash: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " adds " + playActions.ElementAt(i).actionValue.ToString() + " to their stack."; break; case PokerAction.DeadBlind: actionString = genericCache.getPlayerName(playActions.ElementAt(i).playerId) + " posts a dead blind."; playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "DB - " + playActions.ElementAt(i).actionValue.ToString(); break; case PokerAction.ReturnBet: actionString = "Uncalled bet of " + playActions.ElementAt(i).actionValue.ToString() + " returned to " + genericCache.getPlayerName(playActions.ElementAt(i).playerId); playerControls[genericCache.getPlayerPosition(playActions.ElementAt(i).playerId), 4].Text = "Bet Returned - " + playActions.ElementAt(i).actionValue.ToString(); break; case PokerAction.DealFlop: actionString = "[Dealer] Flop Cards Revealed (" + ((Card)genericCache.getCurrentHandDetails().tableCard1).ToString() + "), (" + ((Card)genericCache.getCurrentHandDetails().tableCard2).ToString() + "), (" + ((Card)genericCache.getCurrentHandDetails().tableCard3).ToString() + ")."; newRoundTableRefresh(); break; case PokerAction.DealTurn: actionString = "[Dealer] Turn Card Revealed (" + ((Card)genericCache.getCurrentHandDetails().tableCard4).ToString() + ")."; newRoundTableRefresh(); break; case PokerAction.DealRiver: actionString = "[Dealer] River Card Revealed (" + ((Card)genericCache.getCurrentHandDetails().tableCard5).ToString() + ")."; newRoundTableRefresh(); break; case PokerAction.TableRake: actionString = "[Dealer] Table rake of " + playActions.ElementAt(i).actionValue.ToString("#0.00"); break; } #endregion actionStringSwtich handHistory.AppendText(actionString + "\n"); //lastActionTime = playActions.ElementAt(i).actionTime; } activePositions = genericCache.getActivePositions(); //Only update player details if they exist if (activePositions.Length != 0) { bool endOfHand = false; if (genericCache.getBettingRound() == 3 && genericCache.getActivePositionsLeftToAct().Length == 0) { endOfHand = true; } for (int i = 0; i < currentPlayerDetails.Length; i++) { //{player0Name, player0Stack, player0Card1, player0Card2, player0Action}, playerControls[currentPlayerDetails[i].position, 0].Text = currentPlayerDetails[i].playerName; playerControls[currentPlayerDetails[i].position, 1].Text = currentPlayerDetails[i].stack.ToString(); //If echoHoleCards is set to true then echo out any known hole cards if (echoHoleCards == 1) { if (genericCache.getPlayerHoleCards(currentPlayerDetails[i].playerId).holeCard1 != 0) { actionString = "[Hole Cards] " + currentPlayerDetails[i].playerName + " (" + (Card)genericCache.getPlayerHoleCards(currentPlayerDetails[i].playerId).holeCard1 + ", " + (Card)genericCache.getPlayerHoleCards(currentPlayerDetails[i].playerId).holeCard2 + ")."; handHistory.AppendText(actionString + "\n"); } } var isActive = from ac in activePositions where ac == currentPlayerDetails[i].position select ac; var currentActivePosition = genericCache.getCurrentActiveTablePosition(); if (onlyShowCardsForPlayerId != -1 && currentPlayerDetails[i].playerId == onlyShowCardsForPlayerId) { setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard1, (PictureBox)playerControls[currentPlayerDetails[i].position, 2]); setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard2, (PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } else if (isActive.Count() == 1 && onlyShowCardsForPlayerId != -1 && currentPlayerDetails[i].playerId != onlyShowCardsForPlayerId) { blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 2]); blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } else if ((showNonBotPlayerCardsOnly && isActive.Count() == 1 && !currentPlayerDetails[i].isBot) || (endOfHand && isActive.Count() == 1)) { //We are only showing non bot player cards and we are currently at a non bot position. //It is the end of the hand and this position is still active (it's a showdown folks). setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard1, (PictureBox)playerControls[currentPlayerDetails[i].position, 2]); setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard2, (PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } else if (showNonBotPlayerCardsOnly && isActive.Count() == 1 && currentPlayerDetails[i].isBot) { //We are only showing non bot player cards and we are currently at a bot position. blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 2]); blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } else if ((!showActivePlayerCardsOnly && isActive.Count() == 1) || (showActivePlayerCardsOnly && currentActivePosition == currentPlayerDetails[i].position)) { //show cards if we are showing everyones cards and this current position is active //show cards if we are only showing active positions and we are currently in the active position. setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard1, (PictureBox)playerControls[currentPlayerDetails[i].position, 2]); setCard(genericCache.getPlayerHoleCards((long)currentPlayerDetails[i].playerId).holeCard2, (PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } else if (isActive.Count() == 1) { //If we get here just show the back of the cards blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 2]); blankCard((PictureBox)playerControls[currentPlayerDetails[i].position, 3]); } //Player might be dead if (currentPlayerDetails[i].isDead) { sitInOutPlayer(currentPlayerDetails[i].position, false); } else if (currentActivePosition == currentPlayerDetails[i].position) { setPlayerTurn(currentPlayerDetails[i].position); } else { sitInOutPlayer(currentPlayerDetails[i].position, true); } } echoHoleCards = 2; } } genericCache.endRead(); #endregion } //lastLocalIndex = genericCache.getMostRecentLocalIndex(); //Call garbage collection to keep memory usage under control (without this it will quite happily hit 0.5Gb usage) GC.Collect(); } this.Invalidate(); }