Пример #1
0
        public Maze(int height, int width)
        {
            this.Height = height;
            this.Width = width;

            MazeCells = new MazeCell[height][];
            for (int h = 0; h < height; h++)
            {
                MazeCells[h] = new MazeCell[width];
                for (int w = 0; w < width; w++)
                {
                    MazeCell mc = new MazeCell(w, h);

                    if (h == 0)
                    {
                        ((List<MazeDirection>)mc.BuildDirections).Remove(MazeDirection.Up);
                    }
                    if (h == this.Height - 1)
                    {
                        ((List<MazeDirection>)mc.BuildDirections).Remove(MazeDirection.Down);
                    }

                    if (w == 0)
                    {
                        ((List<MazeDirection>)mc.BuildDirections).Remove(MazeDirection.Left);
                    }
                    if (w == this.Width - 1)
                    {
                       ((List<MazeDirection>)mc.BuildDirections).Remove(MazeDirection.Right);
                    }

                    MazeCells[h][w] = mc;
                }
            }
        }
Пример #2
0
 private void buttonStepBuild_Click(object sender, EventArgs e)
 {
     if (this.buildCells < this.mazeHeight * this.mazeWidth)
     {
         doBuildStep(checkBoxFastBacktrackBuild.Checked, checkBoxDebugBuildBacktrack.Checked);
         this.progressBarBuildCells.Value = this.buildCells;
         this.progressBarBuildBacktrack.Value = this.backtrakBuildCells;
         this.progressBarBuildBacktrack.Maximum = this.buildCells;
         if (this.buildCells == this.mazeWidth * this.mazeHeight)
         {
             this.timer.Stop();
             this.MazeDrawer.Draw(false, false);
             this.CurrentCell = null;
         }
     }
     else if (this.CurrentCell != this.Maze.VisitFinalCell)
     {
         doExploreStep(true, true);
     }
 }
Пример #3
0
        private void buttonNew_Click(object sender, EventArgs e)
        {
            timer.Stop();
            MazeDrawer.CalculateSize(this.panel1.CreateGraphics(), (int)numericUpDownPathSize.Value, (int)numericUpDownWallSize.Value, out this.mazeWidth, out this.mazeHeight);
            this.Maze = new Maze(this.mazeHeight, this.mazeWidth);
            this.MazeDrawer = new MazeDrawer(this.panel1.CreateGraphics(), this.Maze, (int)numericUpDownPathSize.Value, (int)numericUpDownWallSize.Value);
            this.MazeDrawer.BuildColor = this.buttonBuildColor.BackColor;
            this.MazeDrawer.BuildBackColor = this.buttonBuildBacktrackColor.BackColor;
            this.MazeDrawer.ExploreColor = Color.Red;
            this.MazeDrawer.ExploreBackColor = Color.Yellow;
            this.MazeDrawer.Draw(false, false);
            this.CurrentCell = null;

            this.panel1.BackColor = this.MazeDrawer.WallColor;
            this.labelSize.Text = string.Format("{0} x {1} maze", this.mazeHeight, this.mazeWidth);
            this.labelCells.Text = string.Format("{0} steps", this.mazeHeight * this.mazeWidth);
            this.buildCells = 0;
            this.backtrakBuildCells = 0;
            this.progressBarBuildCells.Maximum = this.mazeHeight * this.mazeWidth;
            this.progressBarBuildBacktrack.Maximum = this.buildCells;
            this.labelBuiltCells.Text = string.Format("{0} / {1} (0% / {2})", this.buildCells, this.mazeWidth * this.mazeHeight, this.buildCells - this.mazeWidth * this.mazeHeight);
            this.labelBacktrackBuiltCells.Text = string.Format("{0} / {1} (0% / {2})", this.backtrakBuildCells, this.buildCells, this.backtrakBuildCells - this.buildCells);
        }
Пример #4
0
        public MazeCell AdvanceBuild(MazeCell mazeCell, MazeDirection mazeDirection)
        {
            MazeCell newHead = null;

            if (mazeCell != null)
            {
                switch (mazeDirection)
                {
                    case MazeDirection.Up:
                        newHead = this.MazeCells[mazeCell.Y - 1][mazeCell.X];
                        break;
                    case MazeDirection.Right:
                        newHead = this.MazeCells[mazeCell.Y][mazeCell.X + 1];
                        break;
                    case MazeDirection.Down:
                        newHead = this.MazeCells[mazeCell.Y + 1][mazeCell.X];
                        break;
                    case MazeDirection.Left:
                        newHead = this.MazeCells[mazeCell.Y][mazeCell.X - 1];
                        break;
                }

                ((List<MazeDirection>)mazeCell.BuildDirections).Remove(mazeDirection);
                ((List<MazeDirection>)mazeCell.ExploreDirections).Add(mazeDirection);

                newHead.PreviousBuildCell = mazeCell;
                newHead.PreviousBuildDirection = this.oppositeDirection(mazeDirection);
                newHead.HasPath = true;
                ((List<MazeDirection>)newHead.BuildDirections).Remove(this.oppositeDirection(mazeDirection));
                ((List<MazeDirection>)newHead.ExploreDirections).Add(this.oppositeDirection(mazeDirection));

                if (newHead.Y > 0)
                {
                    MazeCell upCell = this.MazeCells[newHead.Y - 1][newHead.X];
                    if (upCell.HasPath)
                    {
                        ((List<MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Up);
                        ((List<MazeDirection>)upCell.BuildDirections).Remove(MazeDirection.Down);
                    }
                }

                if (newHead.X < this.Width - 1)
                {
                    MazeCell rightCell = this.MazeCells[newHead.Y][newHead.X + 1];
                    if (rightCell.HasPath)
                    {
                        ((List<MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Right);
                        ((List<MazeDirection>)rightCell.BuildDirections).Remove(MazeDirection.Left);
                    }
                }

                if (newHead.Y < this.Height - 1)
                {
                    MazeCell downCell = this.MazeCells[newHead.Y + 1][newHead.X];
                    if (downCell.HasPath)
                    {
                        ((List<MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Down);
                        ((List<MazeDirection>)downCell.BuildDirections).Remove(MazeDirection.Up);
                    }

                }

                if (newHead.X > 0)
                {
                    MazeCell leftCell = this.MazeCells[newHead.Y][newHead.X - 1];
                    if (leftCell.HasPath)
                    {
                        ((List<MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Left);
                        ((List<MazeDirection>)leftCell.BuildDirections).Remove(MazeDirection.Right);
                    }
                }
            }

            return newHead;
        }
Пример #5
0
        public MazeCell AdvanceExplore(MazeCell mazeCell, MazeDirection mazeDirection)
        {
            MazeCell newHead = null;

            if (mazeCell != null)
            {
                switch (mazeDirection)
                {
                    case MazeDirection.Up:
                        newHead = this.MazeCells[mazeCell.Y - 1][mazeCell.X];
                        break;
                    case MazeDirection.Right:
                        newHead = this.MazeCells[mazeCell.Y][mazeCell.X + 1];
                        break;
                    case MazeDirection.Down:
                        newHead = this.MazeCells[mazeCell.Y + 1][mazeCell.X];
                        break;
                    case MazeDirection.Left:
                        newHead = this.MazeCells[mazeCell.Y][mazeCell.X - 1];
                        break;
                }

                ((List<MazeDirection>)mazeCell.ExploreDirections).Remove(mazeDirection);
                ((List<MazeDirection>)newHead.ExploreDirections).Remove(this.oppositeDirection(mazeDirection));

                newHead.PreviousExploreCell = mazeCell;
                newHead.PreviousExploreDirection = this.oppositeDirection(mazeDirection);
                newHead.Visited = true;
            }

            return newHead;
        }
Пример #6
0
 public void PaintExploreBackwardCells(MazeCell fromCell, MazeCell toCell, MazeDirection mazeDirection)
 {
     PaintCell(fromCell.X, fromCell.Y, this.ExploreBackColor);
     PaintBorder(fromCell.X, fromCell.Y, mazeDirection, this.ExploreBackColor);
     PaintCell(toCell.X, toCell.Y, this.ExploreBackColor);
 }
Пример #7
0
 public void PaintBuildForwardCell(MazeCell mazeCell)
 {
     PaintCell(mazeCell.X, mazeCell.Y, this.BuildColor);
 }
Пример #8
0
 public void PaintBuildForwardCells(MazeCell fromCell, MazeCell toCell, MazeDirection mazeDirection)
 {
     PaintCell(fromCell.X, fromCell.Y, this.BuildColor);
     PaintBorder(fromCell.X, fromCell.Y, mazeDirection, this.BuildColor);
     PaintCell(toCell.X, toCell.Y, this.BuildColor);
 }
Пример #9
0
        private void doBuildStep(bool fastBacktrack, bool debugBacktrack)
        {
            if (!stepping && this.Maze != null && this.MazeDrawer != null && this.buildCells < this.mazeHeight * this.mazeWidth)
            {
                stepping = true;
                if (this.CurrentCell != null)
                {
                    if (this.CurrentCell.CanContinueBuild)
                    {
                        MazeDirection mazeDirection = this.Maze.GetRandomDirection(this.CurrentCell.BuildDirections);
                        MazeCell newCell = this.Maze.AdvanceBuild(this.CurrentCell, mazeDirection);
                        this.MazeDrawer.PaintBuildForwardCells(this.CurrentCell, newCell, mazeDirection);
                        this.CurrentCell = newCell;
                        this.buildCells++;
                        this.labelBuiltCells.Text = string.Format("{0} / {1} ({2}% / {3})", this.buildCells, this.mazeWidth * this.mazeHeight, (int)(100 * this.buildCells / (this.mazeWidth * this.mazeHeight)), this.buildCells - this.mazeWidth * this.mazeHeight);
                        this.labelBacktrackBuiltCells.Text = string.Format("{0} / {1} ({2}% / {3})", this.backtrakBuildCells, this.buildCells, (int)(100 * this.backtrakBuildCells / this.buildCells), this.backtrakBuildCells - this.buildCells);
                    }
                    else
                    {
                        Action stepBack = () =>
                        {
                            this.CurrentCell.HasBacktrackPath = true;
                            MazeDirection mazeDirection = this.CurrentCell.PreviousBuildDirection;
                            if (debugBacktrack)
                            {
                                this.MazeDrawer.PaintBuildBackwardCells(this.CurrentCell, this.CurrentCell.PreviousBuildCell, this.CurrentCell.PreviousBuildDirection);
                            }
                            this.CurrentCell = this.CurrentCell.PreviousBuildCell;
                            this.backtrakBuildCells++;
                            this.labelBacktrackBuiltCells.Text = string.Format("{0} / {1} ({2}% / {3})", this.backtrakBuildCells, this.buildCells, (int)(100 * this.backtrakBuildCells / this.buildCells), this.backtrakBuildCells - this.buildCells);
                        };

                        if (fastBacktrack)
                        {
                            while (!this.CurrentCell.CanContinueBuild && this.CurrentCell.PreviousBuildCell != null)
                            {
                                stepBack();
                            }
                        }
                        else
                        {
                            if (this.CurrentCell.PreviousBuildCell != null)
                            {
                                stepBack();
                            }
                        }
                    }
                }
                else
                {
                    this.CurrentCell = this.Maze.GetRandomCell();
                    this.CurrentCell.HasPath = true;
                    this.MazeDrawer.PaintCell(this.CurrentCell.X, this.CurrentCell.Y, this.MazeDrawer.BuildColor);
                    this.buildCells++;
                    this.labelBuiltCells.Text = string.Format("{0} / {1} ({2}% / {3})", this.buildCells, this.mazeWidth * this.mazeHeight, (int)(100 * this.buildCells / (this.mazeWidth * this.mazeHeight)), this.buildCells - this.mazeWidth * this.mazeHeight);
                    this.labelBacktrackBuiltCells.Text = string.Format("{0} / {1} ({2}% / {3})", this.backtrakBuildCells, this.buildCells, (int)(100 * this.backtrakBuildCells / this.buildCells), this.backtrakBuildCells - this.buildCells);
                }
                stepping = false;
            }
        }
Пример #10
0
        private void doExploreStep(bool fastBacktrack, bool debugBacktrack)
        {
            if (!stepping && this.CurrentCell != this.Maze.VisitFinalCell)
            {
                stepping = true;

                if (this.CurrentCell != null)
                {
                    if (this.CurrentCell.CanContinueExplore)
                    {
                        MazeDirection mazeDirection = this.Maze.GetRandomDirection(this.CurrentCell.ExploreDirections);
                        MazeCell newCell = this.Maze.AdvanceExplore(this.CurrentCell, mazeDirection);
                        this.MazeDrawer.PaintExploreForwardCells(this.CurrentCell, newCell, mazeDirection);
                        this.CurrentCell = newCell;
                    }
                    else
                    {
                        Action stepBack = () =>
                        {
                            this.CurrentCell.VisitedBack = true;
                            MazeDirection mazeDirection = this.CurrentCell.PreviousBuildDirection;
                            if (debugBacktrack)
                            {
                                this.MazeDrawer.PaintExploreBackwardCells(this.CurrentCell, this.CurrentCell.PreviousExploreCell, this.CurrentCell.PreviousExploreDirection);
                            }
                            this.CurrentCell = this.CurrentCell.PreviousExploreCell;
                        };

                        if (fastBacktrack)
                        {
                            while (!this.CurrentCell.CanContinueExplore)
                            {
                                stepBack();
                            }
                        }
                        else
                        {
                            stepBack();
                        }
                    }
                }
                else
                {
                    this.CurrentCell = this.Maze.VisitInitialCell;
                    this.CurrentCell.Visited = true;
                    this.MazeDrawer.PaintCell(this.CurrentCell.X, this.CurrentCell.Y, this.MazeDrawer.ExploreColor);
                }

                stepping = false;
            }
        }
Пример #11
0
 private void buttonSkip_Click(object sender, EventArgs e)
 {
     timer.Stop();
     while (this.buildCells < this.mazeHeight * this.mazeWidth)
     {
         doBuildStep(true, false);
         this.progressBarBuildCells.Value = this.buildCells;
         this.progressBarBuildBacktrack.Value = this.backtrakBuildCells;
         this.progressBarBuildBacktrack.Maximum = this.buildCells;
     }
     this.timer.Stop();
     this.MazeDrawer.Draw(false, false);
     this.CurrentCell = null;
 }
Пример #12
0
 public void PaintExploreBackwardCells(MazeCell fromCell, MazeCell toCell, MazeDirection mazeDirection)
 {
     PaintCell(fromCell.X, fromCell.Y, this.ExploreBackColor);
     PaintBorder(fromCell.X, fromCell.Y, mazeDirection, this.ExploreBackColor);
     PaintCell(toCell.X, toCell.Y, this.ExploreBackColor);
 }
Пример #13
0
 public void PaintBuildForwardCell(MazeCell mazeCell)
 {
     PaintCell(mazeCell.X, mazeCell.Y, this.BuildColor);
 }
Пример #14
0
 public void PaintBuildForwardCells(MazeCell fromCell, MazeCell toCell, MazeDirection mazeDirection)
 {
     PaintCell(fromCell.X, fromCell.Y, this.BuildColor);
     PaintBorder(fromCell.X, fromCell.Y, mazeDirection, this.BuildColor);
     PaintCell(toCell.X, toCell.Y, this.BuildColor);
 }
Пример #15
0
        public MazeCell AdvanceBuild(MazeCell mazeCell, MazeDirection mazeDirection)
        {
            MazeCell newHead = null;

            if (mazeCell != null)
            {
                switch (mazeDirection)
                {
                case MazeDirection.Up:
                    newHead = this.MazeCells[mazeCell.Y - 1][mazeCell.X];
                    break;

                case MazeDirection.Right:
                    newHead = this.MazeCells[mazeCell.Y][mazeCell.X + 1];
                    break;

                case MazeDirection.Down:
                    newHead = this.MazeCells[mazeCell.Y + 1][mazeCell.X];
                    break;

                case MazeDirection.Left:
                    newHead = this.MazeCells[mazeCell.Y][mazeCell.X - 1];
                    break;
                }

                ((List <MazeDirection>)mazeCell.BuildDirections).Remove(mazeDirection);
                ((List <MazeDirection>)mazeCell.ExploreDirections).Add(mazeDirection);

                newHead.PreviousBuildCell      = mazeCell;
                newHead.PreviousBuildDirection = this.oppositeDirection(mazeDirection);
                newHead.HasPath = true;
                ((List <MazeDirection>)newHead.BuildDirections).Remove(this.oppositeDirection(mazeDirection));
                ((List <MazeDirection>)newHead.ExploreDirections).Add(this.oppositeDirection(mazeDirection));

                if (newHead.Y > 0)
                {
                    MazeCell upCell = this.MazeCells[newHead.Y - 1][newHead.X];
                    if (upCell.HasPath)
                    {
                        ((List <MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Up);
                        ((List <MazeDirection>)upCell.BuildDirections).Remove(MazeDirection.Down);
                    }
                }

                if (newHead.X < this.Width - 1)
                {
                    MazeCell rightCell = this.MazeCells[newHead.Y][newHead.X + 1];
                    if (rightCell.HasPath)
                    {
                        ((List <MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Right);
                        ((List <MazeDirection>)rightCell.BuildDirections).Remove(MazeDirection.Left);
                    }
                }

                if (newHead.Y < this.Height - 1)
                {
                    MazeCell downCell = this.MazeCells[newHead.Y + 1][newHead.X];
                    if (downCell.HasPath)
                    {
                        ((List <MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Down);
                        ((List <MazeDirection>)downCell.BuildDirections).Remove(MazeDirection.Up);
                    }
                }

                if (newHead.X > 0)
                {
                    MazeCell leftCell = this.MazeCells[newHead.Y][newHead.X - 1];
                    if (leftCell.HasPath)
                    {
                        ((List <MazeDirection>)newHead.BuildDirections).Remove(MazeDirection.Left);
                        ((List <MazeDirection>)leftCell.BuildDirections).Remove(MazeDirection.Right);
                    }
                }
            }

            return(newHead);
        }