Ejemplo n.º 1
0
        private void ConfigureComputer()
        {
            game.RegisterEngine(Player.One, engines.GetEngine(cbPlayerOne.Text));
            game.RegisterEngine(Player.Two, engines.GetEngine(cbPlayerTwo.Text));

            game.ComputerPlay();
        }
Ejemplo n.º 2
0
        public void Draw(VolcanoGame game, Point mouseLocation, int moveNumber, bool highlightLastMove, bool displayHeatmap)
        {
            Resize();

            if (GraphicsSettings.IdealPanelWidth <= 100 || GraphicsSettings.IdealPanelHeight <= 20)
            {
                using (Graphics g3 = _panel.CreateGraphics())
                {
                    g3.Clear(SystemColors.ControlDark);
                    g3.DrawString(":)", new Font("Tahoma", 8f * _fontScale, FontStyle.Regular), Brushes.White, new Point(1, 1));
                }

                return;
            }

            bool reviewMode = game.MoveHistory.Count > 0 && moveNumber != game.MoveHistory.Count;

            int   hoverTile = GetTileIndex(mouseLocation);
            Board gameState = reviewMode ? game.GetPreviousState(moveNumber) : game.CurrentState;

            Point mouse = GetOffsetPoint(mouseLocation);

            int lastPlayIndex = GetTileIndexFromBoardIndex(game.MoveHistory.Count >= moveNumber && moveNumber - 1 >= 0 ? game.MoveHistory[moveNumber - 1] : -1);

            Color background = reviewMode ? GraphicsSettings.ReviewBackgroundColor : GraphicsSettings.BackgroundColor;

            if (displayHeatmap)
            {
                if (gameState.Turn != analysisMove)
                {
                    EndAnalysis();
                    analysisMove   = gameState.Turn;
                    analysisEngine = new VolcanoGame();
                    analysisEngine.SecondsPerEngineMove = 1000000;
                    analysisEngine.RegisterEngine(Player.One, new MonteCarloTreeSearchEngine(false, true, true, ""));
                    analysisEngine.RegisterEngine(Player.Two, new MonteCarloTreeSearchEngine(false, true, true, ""));
                    analysisEngine.OnEngineStatus += AnalysisEngine_OnEngineStatus;
                    analysisEngine.CurrentState    = new Board(gameState);
                    analysisEngine.ComputerPlay();
                }
            }
            else
            {
                EndAnalysis();
            }

            using (Bitmap b = new Bitmap(GraphicsSettings.IdealPanelWidth, GraphicsSettings.IdealPanelHeight))
                using (Graphics g = Graphics.FromImage(b))
                {
                    g.SmoothingMode      = SmoothingMode.AntiAlias;
                    g.CompositingQuality = CompositingQuality.HighQuality;
                    g.InterpolationMode  = InterpolationMode.HighQualityBicubic;

                    g.Clear(background);

                    // Draw equator
                    if (GraphicsSettings.ShowEquator)
                    {
                        var allPoints = new List <PointF>();
                        for (int i = 0; i < 80; i++)
                        {
                            // If this is a northern tile
                            if (Constants.TileNames[boardIndexFromTileIndex[i]].Contains("N"))
                            {
                                foreach (int adjacent in Constants.AdjacentIndexes[i])
                                {
                                    // If this northern tile has an adjacent southern tile
                                    if (Constants.TileNames[boardIndexFromTileIndex[adjacent]].Contains("S"))
                                    {
                                        var rect   = _tiles[adjacent].Path.GetBounds();
                                        var center = new PointF(rect.X + rect.Width / 2, rect.Y + rect.Height / 2);

                                        // Find two points closest to the adjacent tile
                                        var points         = _tiles[i].Path.PathPoints.OrderBy(x => Math.Sqrt(Math.Pow(x.X - center.X, 2) + Math.Pow(x.Y - center.Y, 2))).ToList();
                                        var pointsAdjacent = _tiles[adjacent].Path.PathPoints.OrderBy(x => Math.Sqrt(Math.Pow(x.X - points[0].X, 2) + Math.Pow(x.Y - points[0].Y, 2))).ToList();

                                        // Average them to get a line exactly halfway between the two tiles
                                        var centerOne = new PointF((points[0].X + pointsAdjacent[0].X) / 2, (points[0].Y + pointsAdjacent[0].Y) / 2);
                                        var centerTwo = new PointF((points[1].X + pointsAdjacent[1].X) / 2, (points[1].Y + pointsAdjacent[1].Y) / 2);

                                        // Save the points so we can draw them all at once later
                                        allPoints.Add(centerOne);
                                        allPoints.Add(centerTwo);
                                    }
                                }
                            }
                        }

                        // Sort the points left to right so we don't have a line jumping randomly all of the board
                        allPoints.Sort((c, n) => c.X.CompareTo(n.X));

                        var pen = new Pen(GraphicsSettings.EquatorColor, GraphicsSettings.TileSpacing * 0.75f);
                        pen.EndCap   = LineCap.Round;
                        pen.StartCap = LineCap.Round;

                        g.DrawLines(pen, allPoints.ToArray());

                        //var width = GraphicsSettings.TileSpacing;
                        //for (int t = width; t >= 1; t--)
                        //{
                        //    var color = Color.FromArgb(255 - 255 * t / width, GraphicsSettings.EquatorColor.R, GraphicsSettings.EquatorColor.G, GraphicsSettings.EquatorColor.B);
                        //    var pen = new Pen(color, t);
                        //    pen.EndCap = LineCap.Round;
                        //    pen.StartCap = LineCap.Round;

                        //    g.DrawLines(pen, allPoints.ToArray());
                        //}
                    }

                    // Draw rotation buttons
                    if (GraphicsSettings.ShowRotationButtons)
                    {
                        for (int i = 0; i < _rotations.Count; i++)
                        {
                            float opacity = 0.25f;
                            if (_rotations[i].IsWithinCircle(mouse))
                            {
                                opacity = 1f;
                            }

                            ColorMatrix matrix = new ColorMatrix();
                            matrix.Matrix33 = opacity;
                            ImageAttributes attributes = new ImageAttributes();
                            attributes.SetColorMatrix(matrix, ColorMatrixFlag.Default, ColorAdjustType.Bitmap);
                            g.DrawImage(_rotations[i].Image, _rotations[i].BoundingBoxFull, 0, 0, _rotations[i].Image.Width, _rotations[i].Image.Height, GraphicsUnit.Pixel, attributes);
                        }
                    }

                    // Draw tiles
                    for (int i = 0; i < 80; i++)
                    {
                        DrawTile(g, gameState, i, hoverTile, lastPlayIndex, highlightLastMove);

                        if (displayHeatmap)
                        {
                            var details = analysisStatus?.Details?.FirstOrDefault(x => x.MoveIndex == boardIndexFromTileIndex[i]);
                            if (details != null)
                            {
                                var min   = analysisStatus.Details.Min(x => x.Evaluation);
                                var max   = analysisStatus.Details.Max(x => x.Evaluation);
                                var scale = 1.0;
                                if (max - min > 0)
                                {
                                    scale = (details.Evaluation - min) / (max - min);
                                }
                                var isBest = details.Evaluation == max;
                                FillRoundedRectangle(g, i, scale, isBest);
                                DrawTileText(g, i, details.Evaluation.ToString(), 3, GraphicsSettings.SubTextFontSize, false, Color.Black);
                            }
                        }
                        else if (GraphicsSettings.ShowTileNames)
                        {
                            DrawTileSubText(g, i, Constants.TileNames[boardIndexFromTileIndex[i]]);
                        }

                        if (gameState.Tiles[boardIndexFromTileIndex[i]] == 0)
                        {
                            if (GraphicsSettings.ShowTileIndexes)
                            {
                                DrawTileMainText(g, i, boardIndexFromTileIndex[i].ToString());
                            }

                            //DrawTileMainText(g, i, Constants.FastestPaths[i].Length.ToString());
                        }
                        else
                        {
                            int value = Math.Abs(gameState.Tiles[boardIndexFromTileIndex[i]]);

                            if (!GraphicsSettings.ShowTileNames)
                            {
                                if (Math.Abs(gameState.Tiles[boardIndexFromTileIndex[i]]) <= VolcanoGame.Settings.MaxMagmaChamberLevel)
                                {
                                    DrawTileSubText(g, i, "Chamber");
                                }
                                else
                                {
                                    value -= VolcanoGame.Settings.MaxMagmaChamberLevel;
                                    DrawTileSubText(g, i, "Volcano");
                                }
                            }

                            DrawTileMainText(g, i, value.ToString());
                        }
                    }

                    // Draw turn clock
                    if (_clock.Width > 0)
                    {
                        var lastToMove = moveNumber % 6;

                        var centerCover = new RectangleF(_clock.X + _clock.Width / 3, _clock.Y + _clock.Width / 3, _clock.Width / 3, _clock.Width / 3);
                        var angle       = 360f / 6;
                        var start       = -90f - angle / 2;

                        var moveColor = GraphicsSettings.EmptyTileColor;
                        switch (lastToMove)
                        {
                        case 0:
                        case 4:
                            moveColor = GraphicsSettings.PlayerOneVolcanoTileColor;
                            break;

                        case 1:
                        case 3:
                            moveColor = GraphicsSettings.PlayerTwoVolcanoTileColor;
                            break;
                        }

                        var shadeColor = Color.FromArgb(128, 255, 255, 255);

                        var player1brush      = new SolidBrush(GraphicsSettings.PlayerOneVolcanoTileColor);
                        var player2brush      = new SolidBrush(GraphicsSettings.PlayerTwoVolcanoTileColor);
                        var growthBrush       = new SolidBrush(GraphicsSettings.EmptyTileColor);
                        var playerToMoveBrush = new SolidBrush(moveColor);
                        var playerToMovePen   = new Pen(moveColor, 8f * _fontScale);
                        var shadeBrush        = new SolidBrush(shadeColor);

                        g.FillPie(player1brush, _clock, start, angle);
                        g.FillPie(player2brush, _clock, start + angle, angle);
                        g.FillPie(growthBrush, _clock, start + angle * 2, angle);
                        g.FillPie(player2brush, _clock, start + angle * 3, angle);
                        g.FillPie(player1brush, _clock, start + angle * 4, angle);
                        g.FillPie(growthBrush, _clock, start + angle * 5, angle);

                        g.FillPie(shadeBrush, _clock, start + angle * lastToMove + angle, angle * 5);
                        g.DrawPie(playerToMovePen, _clock, start + angle * lastToMove, angle);

                        g.FillEllipse(playerToMoveBrush, centerCover);
                    }

                    using (Bitmap b2 = new Bitmap(_panel.Width, _panel.Height))
                        using (Graphics g2 = Graphics.FromImage(b2))
                            using (Graphics g3 = _panel.CreateGraphics())
                            {
                                g2.Clear(background);
                                g2.DrawImage(b, (_panel.Width - GraphicsSettings.IdealPanelWidth) / 2, (_panel.Height - GraphicsSettings.IdealPanelHeight) / 2, GraphicsSettings.IdealPanelWidth, GraphicsSettings.IdealPanelHeight);

                                Color playerColor = gameState.Player == Player.One ? GraphicsSettings.PlayerOneVolcanoTileColor : GraphicsSettings.PlayerTwoVolcanoTileColor;
                                g2.DrawString("Turn " + gameState.Turn, new Font("Tahoma", 12f * _fontScale, FontStyle.Bold), new SolidBrush(playerColor), new Point(5, 5));
                                if (gameState.State == GameState.GameOver)
                                {
                                    playerColor = gameState.Winner == Player.One ? GraphicsSettings.PlayerOneVolcanoTileColor : GraphicsSettings.PlayerTwoVolcanoTileColor;
                                    string gameOver = "Game Over!";
                                    Font   f        = new Font("Tahoma", 12f * _fontScale, FontStyle.Bold);
                                    SizeF  size     = g.MeasureString(gameOver, f);
                                    g2.DrawString(gameOver, f, new SolidBrush(playerColor), new Point(_panel.Width - (int)size.Width - 5, 5));
                                }
                                g2.DrawString(game.NodesPerSecond.ToString() + " NPS", new Font("Tahoma", 12f, FontStyle.Bold), Brushes.Gray, new Point(5, _panel.Height - 25));

                                // Double buffering
                                g3.DrawImage(b2, 0, 0, _panel.Width, _panel.Height);
                            }
                }
        }