I am writing a card game and have been using the following method to get the next Player who's turn it is
There is a direction to the game which could be forwards or backwards, and it needs to respect this too
private Player GetNextPlayer()
{
int currentPlayerIndex = Players.FindIndex(o => o.IsThisPlayersTurn);
Player nextPlayer;
if (_direction.Equals(Direction.Forwards))
{
nextPlayer = currentPlayerIndex == Players.Count - 1 ? Players[0] : Players[currentPlayerIndex + 1];
}
else
{
nextPlayer = currentPlayerIndex == 0 ? Players[Players.Count - 1] : Players[currentPlayerIndex - 1];
}
return nextPlayer;
}
This works fine until a player has finished the game. Then it can potentially return a player who is no longer in the game.
When a player has finished the game their PlayerState is HasNoCards
So I changed it to this, but it seems to be buggy in certain cases
public Player GetNextPlayer()
{
var players = Players.Where(o => o.PlayerState != PlayerState.HasNoCards);
if (Direction.Equals(Direction.Backwards))
{
players = players.Reverse();
}
bool selectNextPlayer = false;
foreach (Player player in players)
{
if (selectNextPlayer)
{
return player;
}
if (player.IsThisPlayersTurn)
{
selectNextPlayer = true;
}
}
return players.First();
}
I reckon there must be a smart way with linq to say "get the next player , where the Player.PlayerState is not PlayerState.HasNoCards"
Any ideas?
I should add that I can't remove the player from the list to solve the problem as it would screw my databinding
EDIT
I have a failing unit test for the scenario that the second method can't handle. It is when a player plays their last card when the direction is backwards. As I immediately filter the current player from the list, with
var players = Players.Where(o => o.PlayerState != PlayerState.HasNoCards);