binary_tree_generator.hxx
Go to the documentation of this file.
1 /*===========================================================================================================
2  *
3  * HUC - Hurna Core
4  *
5  * Copyright (c) Michael Jeulin-Lagarrigue
6  *
7  * Licensed under the MIT License, you may not use this file except in compliance with the License.
8  * You may obtain a copy of the License at
9  *
10  * https://github.com/Hurna/Hurna-Core/blob/master/LICENSE
11  *
12  * Unless required by applicable law or agreed to in writing, software distributed under the License is
13  * distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and limitations under the License.
15  *
16  * The above copyright notice and this permission notice shall be included in all copies or
17  * substantial portions of the Software.
18  *
19  *=========================================================================================================*/
20 #ifndef MODULE_MAZE_BTG_HXX
21 #define MODULE_MAZE_BTG_HXX
22 
23 #include <DataStructures/grid.hxx>
24 
25 // STD
26 #include <random>
27 
28 namespace huc
29 {
30  namespace maze
31  {
48  {
49  public:
51  typedef Maze::Cell Cell;
52 
53  std::unique_ptr<Maze> operator()(const uint32_t width, const uint32_t height, const uint32_t seed = 0)
54  {
55  if (width < 1 || height < 1)
56  return nullptr;
57 
58  auto maze(std::unique_ptr<Maze>(new Maze(width, height)));
59  std::mt19937 mt(seed); // Initialize random generator based on Mersenne Twister algorithm
60 
61  // For each existing cell in the grid, randomly carve a passage either east or south
62  for (uint32_t y = 0; y < height; ++y)
63  {
64  for (uint32_t x = 0; x < width; ++x)
65  {
66  // Get available neighbours
67  auto cell = (*maze)[x][y];
68  auto curNeighbours = GetNeighbours(*maze, *cell.get());
69 
70  if (curNeighbours.empty())
71  continue;
72 
73  // Randomly select a node to be processed
74  auto randIdx = mt() % curNeighbours.size();
75  maze->Connect(cell, curNeighbours[randIdx]);
76  }
77  }
78 
79  return maze;
80  }
81 
82  private:
89  static std::vector<std::shared_ptr<Cell>> GetNeighbours(const Maze& maze, const Cell& cell)
90  {
91  std::vector<std::shared_ptr<Cell>> neighbours;
92 
93  const auto x = cell.x;
94  const auto y = cell.y;
95 
96  if (x > 0) neighbours.push_back(maze[x-1][y]); // West Direction - Push left if available
97  if (y > 0) neighbours.push_back(maze[x][y-1]); // North Direction - Push top if available
98 
99  return neighbours;
100  }
101  };
102  }
103 }
104 
105 #endif // MODULE_MAZE_BTG_HXX
std::unique_ptr< Maze > operator()(const uint32_t width, const uint32_t height, const uint32_t seed=0)
const uint32_t y
Definition: grid.hxx:70
static std::vector< std::shared_ptr< Cell > > GetNeighbours(const Maze &maze, const Cell &cell)
const uint32_t x
Definition: grid.hxx:69