aboutsummaryrefslogtreecommitdiff
path: root/src/mazerator.cpp
diff options
context:
space:
mode:
authorHampusM <hampus@hampusmat.com>2022-02-15 20:27:51 +0100
committerHampusM <hampus@hampusmat.com>2022-02-15 20:27:51 +0100
commit5dae8f8d10d506abc3c75a1f66c1dfe620c84fc1 (patch)
tree2bfb6efef0535a35bab1da811a5f69cb5203dff9 /src/mazerator.cpp
parent9147551cd21d565f9503e3ebbcd2121e284d88d5 (diff)
refactor: improve project design
Diffstat (limited to 'src/mazerator.cpp')
-rw-r--r--src/mazerator.cpp170
1 files changed, 94 insertions, 76 deletions
diff --git a/src/mazerator.cpp b/src/mazerator.cpp
index b30124f..81960af 100644
--- a/src/mazerator.cpp
+++ b/src/mazerator.cpp
@@ -1,35 +1,28 @@
-#include "engine/matrix.hpp"
+#include "conversion.hpp"
+
+#include "app/app.hpp"
#include "engine/vector2.hpp"
-#include "getopt.h"
-#include "maze.hpp"
#include "random_generator.hpp"
-#include "utils.hpp"
+
+#include <getopt.h>
#include <iostream>
#include <memory>
#include <string>
+#include <string_view>
+#include <vector>
+
+constexpr unsigned int DEFAULT_MAZE_WIDTH = 40U;
+constexpr unsigned int DEFAULT_MAZE_HEIGHT = 20U;
-void optarg_error(int arg, std::string error)
+constexpr std::string_view DEFAULT_MAZE_WALL = "█";
+
+void optarg_error(int arg, const std::string &error)
{
std::cout << "Error: Invalid option argument for -" << arg << ". " << error
<< std::endl;
exit(EXIT_FAILURE);
}
-void validate_start_coords(unsigned int start_x, unsigned int start_y, unsigned int width,
- unsigned int height)
-{
- if (start_x >= width)
- {
- throw "The x start coordinate cannot be higher than or equal to the maze's width";
- }
-
- if (start_y >= height)
- {
- throw "The y start coordinate cannot be higher than or equal to the maze's "
- "height";
- }
-}
-
/**
* Parses a unsigned integer command-line argument.
*
@@ -54,102 +47,135 @@ void parse_uint_arg(unsigned int *num_dst, int arg, bool check_zero = false)
}
}
-const struct option options[] = {{"width", required_argument, NULL, 'w'},
- {"height", required_argument, NULL, 'h'},
- {"wall", required_argument, NULL, 'W'},
- {"seed", required_argument, NULL, 's'},
- {"start-x", required_argument, NULL, 'x'},
- {"start-y", required_argument, NULL, 'y'},
- {"help", no_argument, NULL, 0},
- {NULL, 0, NULL, 0}};
+const std::array<option, 8> options = {
+ option({"width", required_argument, nullptr, 'w'}),
+ option({"height", required_argument, nullptr, 'h'}),
+ option({"wall", required_argument, nullptr, 'W'}),
+ option({"seed", required_argument, nullptr, 's'}),
+ option({"start-x", required_argument, nullptr, 'x'}),
+ option({"start-y", required_argument, nullptr, 'y'}),
+ option({"help", no_argument, nullptr, 0}),
+ option({nullptr, 0, nullptr, 0})};
int main(int argc, char *argv[])
{
- unsigned int maze_width = 40U;
- unsigned int maze_height = 20U;
+ auto args = std::vector<std::string>(argv, argv + argc);
- std::unique_ptr<unsigned int> start_x = nullptr;
- std::unique_ptr<unsigned int> start_y = nullptr;
+ AppOptions app_options;
- std::shared_ptr<RandomNumberGenerator> random_gen = nullptr;
+ BoundsOpts default_maze_bounds = {DEFAULT_MAZE_WIDTH, DEFAULT_MAZE_HEIGHT};
- std::string wall = "█";
+ app_options.maze_bounds(std::make_shared<Bounds>(default_maze_bounds));
- int arg;
- while ((arg = getopt_long(argc, argv, "w:h:W:s:x:y:", options, nullptr)) != -1)
+ app_options.wall(DEFAULT_MAZE_WALL);
+
+ std::unique_ptr<unsigned int> start_x = nullptr;
+ std::unique_ptr<unsigned int> start_y = nullptr;
+
+ int arg = 0;
+ while ((arg = getopt_long(argc, argv, "w:h:W:s:x:y:", options.data(), nullptr)) != -1)
{
switch (arg)
{
case 'w':
- parse_uint_arg(&maze_width, arg, true);
+ {
+ app_options.maze_bounds()->width(
+ static_cast<unsigned int>(std::stoul(optarg, nullptr, NUMBER_BASE)));
break;
+ }
case 'h':
- parse_uint_arg(&maze_height, arg, true);
+ {
+ app_options.maze_bounds()->height(
+ static_cast<unsigned int>(std::stoul(optarg, nullptr, NUMBER_BASE)));
break;
+ }
case 'x':
+ {
start_x = std::make_unique<unsigned int>();
+
parse_uint_arg(start_x.get(), arg);
break;
+ }
case 'y':
+ {
start_y = std::make_unique<unsigned int>();
+
parse_uint_arg(start_y.get(), arg);
break;
+ }
case 'W':
- wall = optarg;
+ {
+ app_options.wall(optarg);
break;
+ }
case 's':
- unsigned int seed;
+ {
+ unsigned int seed = 0;
parse_uint_arg(&seed, arg, true);
- random_gen = std::make_shared<RandomNumberGenerator>(seed);
+ app_options.random_gen(std::make_shared<RandomNumberGenerator>(seed));
break;
+ }
case 0:
- std::cout
- << "Usage: " << argv[0]
- << " [OPTION]...\n\n"
- "Options:\n"
- " -w, --width WIDTH The width of the maze (Default: 40)\n"
- " -h, --height HEIGHT The height of the maze (Default: 20)\n"
- " -x, --start-x X The x coordinate for the start "
- "position "
- "(Default: random)\n"
- " -y, --start-y Y The y coordinate for the start "
- "position "
- "(Default: random)\n"
- " -W, --wall WALL Single character used as maze walls "
- "(Default: '█')\n"
- " -s, --seed SEED The randomization seed used for maze "
- "generation\n"
- " --help Displays usage information"
- << std::endl;
+ {
+ std::cout << "Usage: " << args[0]
+ << " [OPTION]...\n\n"
+ "Options:\n"
+ " -w, --width WIDTH The width of the maze (Default: "
+ << DEFAULT_MAZE_WIDTH
+ << ")\n"
+ " -h, --height HEIGHT The height of the maze (Default: "
+ << DEFAULT_MAZE_HEIGHT
+ << ")\n"
+ " -x, --start-x X The x coordinate for the start "
+ "position "
+ "(Default: random)\n"
+ " -y, --start-y Y The y coordinate for the start "
+ "position "
+ "(Default: random)\n"
+ " -W, --wall WALL Single character used as maze walls "
+ "(Default: '"
+ << DEFAULT_MAZE_WALL
+ << "')\n"
+ " -s, --seed SEED The randomization seed used for maze "
+ "generation\n"
+ " --help Displays usage information"
+ << std::endl;
return EXIT_SUCCESS;
+ }
case '?':
- std::cout << "\nTry '" << argv[0] << " --help' for more information"
+ {
+ std::cout << "\nTry '" << args[0] << " --help' for more information"
<< std::endl;
return EXIT_FAILURE;
}
+ }
}
- if (random_gen == nullptr)
+ if (app_options.random_gen() == nullptr)
{
- random_gen = std::make_shared<RandomNumberGenerator>();
+ app_options.random_gen(std::make_shared<RandomNumberGenerator>());
}
if (start_x == nullptr)
{
- start_x =
- std::make_unique<unsigned int>(random_gen->in_range(0, maze_width - 1U));
+ start_x = std::make_unique<unsigned int>(app_options.random_gen()->in_range(
+ 0, app_options.maze_bounds()->width() - 1U));
}
if (start_y == nullptr)
{
- start_y =
- std::make_unique<unsigned int>(random_gen->in_range(0, maze_height - 1U));
+ start_y = std::make_unique<unsigned int>(app_options.random_gen()->in_range(
+ 0, app_options.maze_bounds()->height() - 1U));
}
+ Vector2Opts start_coords = {.x = *start_x, .y = *start_y};
+
+ app_options.start_coords(std::make_shared<Vector2>(start_coords));
+
try
{
- validate_start_coords(*start_x, *start_y, maze_width, maze_height);
+ app_options.maze_bounds()->verify_coords(*app_options.start_coords());
}
catch (const char *error)
{
@@ -157,13 +183,5 @@ int main(int argc, char *argv[])
return EXIT_FAILURE;
}
- Matrix<std::string> matrix(maze_height * 2U + 1U, maze_width * 2U + 1U);
-
- matrix.fill(wall);
-
- auto start_pos = std::make_shared<Vector2>(*start_x * 2U + 1U, *start_y * 2U + 1U);
-
- matrix_to_maze<std::string>(&matrix, start_pos, " ", random_gen);
-
- matrix.print();
+ app_start(app_options);
}