/// <summary>Entry point of the program.</summary> public static void Main(string[] args) { Console.Title = "5-Tic-Tac-Toe"; Console.CursorVisible = false; WinUtil.DisableMouse(); Display.AdjustSize(false); Display.PlayIntro(); Display.DrawBorders(); Display.DrawOrnaments(); bool vsAI = OpenTitle(); OpenInstructions(); var next = Player.One; var scores = new Dictionary <Player, int>() { { Player.One, 0 }, { Player.Two, 0 }, { Player.Tie, 0 }, }; while (true) // Program loop { var game = new Game(next); var ai = vsAI ? new GameAI(game) : null; Pos selectedCell = new Pos(2, 2); bool forceQuit = false; Display.AdjustSize(); Display.DrawMatch(game, selectedCell, scores); while (game.Winner == Player.None) // Game loop { var oldSelection = selectedCell; if (ai != null && game.Turn == Player.Two) { var aiSelection = ai.GetNextPosition(); selectedCell = aiSelection; Display.DrawCell(game, oldSelection); Display.DrawCell(game, aiSelection, true); Thread.Sleep(100); Beep(game.Turn); Thread.Sleep(100); game.DoTurn(aiSelection); Display.DrawCell(game, aiSelection, true); Display.DrawTurn(game); } else { ClearKeys(); switch (Console.ReadKey(true).Key) { case ConsoleKey.LeftArrow: selectedCell += (-1, 0); break; case ConsoleKey.UpArrow: selectedCell += (0, -1); break; case ConsoleKey.RightArrow: selectedCell += (1, 0); break; case ConsoleKey.DownArrow: selectedCell += (0, 1); break; case ConsoleKey.Enter: case ConsoleKey.Spacebar: if (game.Board[selectedCell] == Player.None) { Beep(game.Turn); game.DoTurn(selectedCell); Display.DrawTurn(game); } break; case ConsoleKey.F1: Beep(600, 50); OpenInstructions(); Display.AdjustSize(); Display.DrawMatch(game, selectedCell, scores); break; case ConsoleKey.F5: Beep(300, 250); forceQuit = true; break; case ConsoleKey.F10: Beep(400, 50); Beep(300, 500); forceQuit = true; scores = new Dictionary <Player, int>() { { Player.One, 0 }, { Player.Two, 0 }, { Player.Tie, 0 }, }; vsAI = OpenTitle(); break; } if (forceQuit) { break; } selectedCell = game.Board.Wrap(selectedCell); if (Display.AdjustSize()) { Display.DrawMatch(game, selectedCell, scores); } else { Display.DrawCell(game, oldSelection); Display.DrawCell(game, selectedCell, true); } } } if (forceQuit) { continue; } scores[game.Winner]++; if (game.Winner == Player.None) { break; } else if (game.Winner == Player.Tie) { next = next.Opponent; } else { next = game.Winner.Opponent; } Display.DrawGameOver(game, scores); Beep(400, 100); Beep(300, 100); Beep(500, 500); ClearKeys(); Console.ReadKey(true); } }
/// <summary>Finds lines of a certain length in the board and marks them in <see cref="Highlights"/>.</summary> private int FindLines(Player player, int length) { int count = 0; List <Pos> line = new List <Pos>(); void CheckCell(int x, int y) { Pos pos = (x, y); if (Board[pos] == player) { line.Add(pos); if (line.Count >= length) { if (line.Count == length) { count++; } foreach (Pos p in line) { Highlights[p] = player; } } } else { line = new List <Pos>(); } } for (int y = 0; y < Board.Height; y++) // Horizontals { for (int x = 0; x < Board.Width; x++) { CheckCell(x, y); } line = new List <Pos>(); } for (int x = 0; x < Board.Width; x++) // Verticals { for (int y = 0; y < Board.Height; y++) { CheckCell(x, y); } line = new List <Pos>(); } for (int d = length - 1; d <= Board.Width + Board.Height - length; d++) // Top-to-left diagonals { for (int x, y = 0; y <= d; y++) { if (y < Board.Height && (x = d - y) < Board.Width) { CheckCell(x, y); } } line = new List <Pos>(); } for (int d = length - 1; d <= Board.Width + Board.Height - length; d++) // Top-to-right diagonals { for (int x, y = 0; y <= d; y++) { if (y < Board.Height && (x = Board.Width - 1 - d + y) >= 0) { CheckCell(x, y); } } line = new List <Pos>(); } return(count); }