diff --git a/.idea/.gitignore b/.idea/.gitignore new file mode 100644 index 0000000..13566b8 --- /dev/null +++ b/.idea/.gitignore @@ -0,0 +1,8 @@ +# Default ignored files +/shelf/ +/workspace.xml +# Editor-based HTTP Client requests +/httpRequests/ +# Datasource local storage ignored files +/dataSources/ +/dataSources.local.xml diff --git a/Maze.cpp b/Maze.cpp deleted file mode 100644 index 957c222..0000000 --- a/Maze.cpp +++ /dev/null @@ -1,162 +0,0 @@ -#include "Maze.h" -#include "Entity.h" -#include "Player.h" -#include "MalformedMaze.h" - -using game_exceptions::MalformedMaze; -namespace game { - /// Ist eine Konstante, darf also in global scope - static const vector valid_maze_elements = {'Z', '.', '#', 'A', 'K', 'T', 'B', 'C'}; - /// Welche Geistertypen es gibt - static const vector valid_enemies = {'A', 'B', 'C'}; - /// Die Maximale Labyrinthgröße - static constexpr int MAX_MAZE_SIZE = 20; - - Maze::Maze(const vector> &play_field, const vector &player_start_position, - const vector &enemies) : - field(play_field), player_start_position(Vector2d{player_start_position[1], player_start_position[0]}), - enemies(enemies) { - if (!this->is_pos_free(this->player_start_position, false)) - throw MalformedMaze("Player oob"); - } - - bool Maze::was_player_killed_by_ghost(const Player &player) const { - return this->field[player.get_pos().y][player.get_pos().x] == 'A'; - } - - bool Maze::is_player_at_goal(const Player &player) const { - return this->field[player.get_pos().y][player.get_pos().x] == 'Z'; - } - - bool Maze::is_pos_free(const Vector2d &pos, const bool &player_has_key) const { - if (pos.x < 0 || pos.y < 0 || pos.y > field.size() - 1 || pos.x > field[pos.y].size() - 1) - return false; - if (field[pos.y][pos.x] == '#') - return false; - if (field[pos.y][pos.x] == 'T') - return player_has_key; - return true; - } - - void Maze::render(const Player &player, const vector &entities, const bool &infomode_enabled) { - for (int y = 0; y < field.size(); ++y) { - for (int x = 0; x < field[y].size(); ++x) { - if (y == player.get_pos().y && x == player.get_pos().x) - cout << "S"; - else { - bool an_enemy_is_at_this_position = false; - for (Entity e: entities) - if (e.is_at_position({x, y})) { - an_enemy_is_at_this_position = true; - cout << e.get_display_character(); - } - if (!an_enemy_is_at_this_position) - cout << field[y][x]; - } - cout << " "; - } - if (y == 0 && infomode_enabled) { - const int steps = this->calculate_steps_until_win(player.get_pos(), 5); - if (steps < 999) - cout << steps << " Schritte bis zum Ziel"; - } - cout << "\n"; - } - } - - char Maze::get_field(const Vector2d &pos) const { return this->field[pos.y][pos.x]; } - - void Maze::update_field(const Vector2d &pos, const char &target) { this->field[pos.y][pos.x] = target; } - - Vector2d Maze::get_player_start_position() const { return this->player_start_position; } - - Vector2d Maze::get_delta_vector(const Vector2d &pos1, const Vector2d &pos2) const { - int x_diff = pos1.x - pos2.x; - int y_diff = pos1.y - pos2.y; - - return {x_diff, y_diff}; - } - - int Maze::calculate_steps_until_win(Vector2d position, const int &steps) { - if (!this->is_pos_free(position, false)) - return 999; - if (this->get_field(position) == 'Z') - return 0; - if (steps <= 0) - return 999; - - return 1 + std::min({this->calculate_steps_until_win(position.get_new_updated(0, -1), steps - 1), - this->calculate_steps_until_win(position.get_new_updated(0, 1), steps - 1), - this->calculate_steps_until_win(position.get_new_updated(1, 0), steps - 1), - this->calculate_steps_until_win(position.get_new_updated(-1, 0), steps - 1)}); - } - - vector Maze::get_entities() { return this->enemies; } - - vector Maze::request_numbers_from_user(const int &amount_of_numbers) { - int input; - vector list; - - for (int i = 0; i < amount_of_numbers; ++i) { - cin >> input; - if (!cin) - throw MalformedMaze("Cin failed while reading numbers!"); - - if (input > MAX_MAZE_SIZE) - throw MalformedMaze("This maze is too big"); - list.push_back(input); - } - - return list; - } - - bool Maze::validate_maze_element(const char &target) { - for (const char c: valid_maze_elements) - if (c == target) - return true; - return false; - } - - bool Maze::is_valid_enemy(const char &target) { - for (const char c: valid_enemies) - if (c == target) - return true; - return false; - } - - Maze Maze::request_maze_from_user() { - vector maze_size = request_numbers_from_user(2); - - char input; - vector> field; - vector enemies; - - for (int y = 0; y < maze_size[0]; ++y) { - vector row; - for (int x = 0; x < maze_size[1]; ++x) { - cin >> input; - if (!cin) - throw MalformedMaze("Cin failed while reading chars!"); - - // I don't think that this is needed. I doubt that they test the check for this one ~Eric - // if (input == 'q') - // throw ExitGame("Schoenen Tag noch!"); - - if (!validate_maze_element(input)) - throw MalformedMaze("The given input is not a valid element of a maze!"); - if (is_valid_enemy(input)) { - enemies.push_back(Entity({x, y}, input)); - row.push_back('.'); - } else { - row.push_back(input); - } - } - - field.push_back(row); - } - - vector player_start_pos = request_numbers_from_user(2); - - return {field, player_start_pos, enemies}; - } // Beispieleingabe: `4 3 #.# #.K #T# #Z# 0 1` -} // namespace game diff --git a/Maze.h b/Maze.h deleted file mode 100644 index e5c4151..0000000 --- a/Maze.h +++ /dev/null @@ -1,113 +0,0 @@ -#ifndef MAZE_H -#define MAZE_H - -#include "Vector2d.h" -#include "std_lib_inc.h" - -namespace game { - class Player; - class Entity; - /// Ist eine Konstante, darf also in global scope - - /// Ein Labyrinth. - /// Besitzt ein Feld - class Maze { - // class -> members private by default - - private: - /// Das Spielfeld - vector> field; - /// Die Startposition des Spielers - Vector2d player_start_position; - /// Eine Liste an Gegnern - vector enemies; - /// Erlaubte Zeichen in einem Labyrinth - /* Legende - * S - Spieler - * Z - Ziel - * . - Leerer Raum (begehbar) - * # - Wand - * A - Animaltronic - * K - Schlüssel - * T - Tür - * B - Bowie - * C - Connellys - */ - public: - /// Das Spielfeld - Maze(const Vector> &play_field, const Vector &player_start_position, - const Vector &enemies); - /// Kontrolliere, ob der Spieler stirbt - /// @param player Der Spieler - /// @return Ob der Spieler tot ist - bool was_player_killed_by_ghost(const Player &player) const; - - /// Kontrolliere, ob der Spieler am Ziel ist - /// @param player Der Spieler - /// @return Ob der Spieler am Ziel ist - bool is_player_at_goal(const Player &player) const; - - /// Kontrolliere, ob eine bestimmte Position begehbar ist - /// @param pos Die Position, die überprüft werden soll - /// @param player_has_key If the player has at least one key - /// @return Ob die Position begehbar ist - bool is_pos_free(const Vector2d &pos, const bool &player_has_key) const; - - /// Zeige das Spielfeld in der Konsole an - /// @param player Der Spieler - /// @param entities Die Entities auf dem Spielfeld - /// @param infomode_enabled Ob der Infomode aktiv ist - void render(const Player &player, const vector &entities, const bool &infomode_enabled); - - /// Kriege den Wert einer Position - /// @param pos Die gewollte Position - /// @return Der Wert der Position - char get_field(const Vector2d &pos) const; - - /// Ersetze den Wert von einer Position - /// @param pos Die Position die ersetzt werden soll - /// @param target Der Wert, auf den die Position gesetzt werden soll - void update_field(const Vector2d &pos, const char &target); - - /// Kriege die Startposition des Spielers - /// @return Die Startposition des Spielers - Vector2d get_player_start_position() const; - - /// Berrechne den Abstand zwischen zwei Vektoren - /// @return Der Abstand als Differenzvektor - Vector2d get_delta_vector(const Vector2d &pos1, const Vector2d &pos2) const; - - /// Berechne wie viele Schritte benötigt werden, um das Labyrinth zu schaffen - /// @warning Steps nicht zu groß setzen! Diese Funktion ist 4-fach rekursiv! - /// @param position Die Startposition - /// @param steps Wie viele Schritte maximal gegangen werden sollten - /// @returns Wie viele Schritte benötigt werden - int calculate_steps_until_win(Vector2d position, const int &steps); - - /// Kriege alle eingelesenen Entities - vector get_entities(); - - /// Lese ein Labyrinth aus der Konsole - /// @return Das Labyrinth - /// @throws runtime_exception Falls die Eingabe nicht korrekt verlaufen ist. - static Maze request_maze_from_user(); - - private: - /// Lese eine bestimmte Anzahl an Nummern aus der Konsole - /// @param amount_of_numbers Wie viele Nummern eingelesen werden sollen - /// @return Die eingelesenen Nummern - static vector request_numbers_from_user(const int &amount_of_numbers); - - /// Kontrolliere, ob ein Zeichen im Labyrinth vorkommen darf - /// @param target Das Zeichen, welches Kontrolliert werden soll - /// @return Ob das gegebene Zeichen in einem Labyrinth vorkommen darf - static bool validate_maze_element(const char &target); - - /// Ob der angegebene char in valider Geist ist - /// @param target Der zu kontrollierende Wert - /// @returns Ob der Wert ein Valider Geist ist - static bool is_valid_enemy(const char &target); - }; -} // namespace game - -#endif // MAZE_H diff --git a/Entity.cpp b/src/Entities/Entity.cpp similarity index 99% rename from Entity.cpp rename to src/Entities/Entity.cpp index 55d7f51..f9cb67a 100644 --- a/Entity.cpp +++ b/src/Entities/Entity.cpp @@ -1,5 +1,5 @@ #include "Entity.h" -#include "Maze.h" +#include "../Environment/Maze.h" namespace game { Entity::Entity(const Vector2d starting_position, const char display_character): pos(starting_position), display_character(display_character), move_left(true){} diff --git a/Entity.h b/src/Entities/Entity.h similarity index 98% rename from Entity.h rename to src/Entities/Entity.h index 04222e6..157fdcd 100644 --- a/Entity.h +++ b/src/Entities/Entity.h @@ -1,4 +1,4 @@ -#include "Vector2d.h" +#include "../Util/Vector2d.h" #ifndef ENTITY_H #define ENTITY_H diff --git a/Player.cpp b/src/Entities/Player.cpp similarity index 95% rename from Player.cpp rename to src/Entities/Player.cpp index f3b026b..c03b22a 100644 --- a/Player.cpp +++ b/src/Entities/Player.cpp @@ -1,8 +1,8 @@ #include "Player.h" -#include "Maze.h" -#include "MovementNotPossible.h" -#include "GameState.h" -#include "Game.h" +#include "../Environment/Maze.h" +#include "../Exceptions/MovementNotPossible.h" +#include "../Util/GameState.h" +#include "../Environment/Game.h" using game::GameState; using game::Game; diff --git a/Player.h b/src/Entities/Player.h similarity index 97% rename from Player.h rename to src/Entities/Player.h index e85460d..78f1fb9 100644 --- a/Player.h +++ b/src/Entities/Player.h @@ -1,5 +1,5 @@ -#include "Vector2d.h" -#include "GameState.h" +#include "../Util/Vector2d.h" +#include "../Util/GameState.h" #ifndef PLAYER_H #define PLAYER_H diff --git a/Game.cpp b/src/Environment/Game.cpp similarity index 96% rename from Game.cpp rename to src/Environment/Game.cpp index 869af38..bb61e71 100644 --- a/Game.cpp +++ b/src/Environment/Game.cpp @@ -1,8 +1,8 @@ #include "Game.h" #include "Maze.h" -#include "MovementNotPossible.h" -#include "UnkownAction.h" -#include "Vector2d.h" +#include "../Exceptions/MovementNotPossible.h" +#include "../Exceptions/UnkownAction.h" +#include "../Util/Vector2d.h" using game::Player; using game::Maze; diff --git a/Game.h b/src/Environment/Game.h similarity index 93% rename from Game.h rename to src/Environment/Game.h index cf8a102..b4cc407 100644 --- a/Game.h +++ b/src/Environment/Game.h @@ -1,7 +1,7 @@ #include "Maze.h" -#include "Player.h" -#include "GameState.h" -#include "Entity.h" +#include "../Entities/Player.h" +#include "../Util/GameState.h" +#include "../Entities/Entity.h" #ifndef GAME_H #define GAME_H @@ -11,7 +11,6 @@ namespace game /// Eine Instanz des Spiels class Game { - private: /// Das Labyrinth Maze maze; @@ -24,7 +23,6 @@ namespace game /// bool infomode_enabled; - public: explicit Game(Maze& maze); diff --git a/src/Environment/Maze.cpp b/src/Environment/Maze.cpp new file mode 100644 index 0000000..eac97e9 --- /dev/null +++ b/src/Environment/Maze.cpp @@ -0,0 +1,115 @@ +#include "Maze.h" +#include "../Entities/Player.h" +#include "../Exceptions/MalformedMaze.h" +#include "../Entities/Entity.h" +#include "../Util/MathUtil.h" + +using game_exceptions::MalformedMaze; + +namespace game +{ + class MathUtil; + + Maze::Maze(const vector>& play_field, const vector& player_start_position, const vector& enemies): + field(play_field), + player_start_position(Vector2d{player_start_position[1], player_start_position[0]}), + enemies(enemies) + { + if (!this->is_pos_free(this->player_start_position, false)) + throw MalformedMaze("Player oob"); + } + + bool Maze::was_player_killed_by_ghost(const Player& player) const + { + return this->field[player.get_pos().y][player.get_pos().x] == 'A'; + } + + bool Maze::is_player_at_goal(const Player& player) const + { + return this->field[player.get_pos().y][player.get_pos().x] == 'Z'; + } + + bool Maze::is_pos_free(const Vector2d& pos, const bool& player_has_key) const + { + if (pos.x < 0 || pos.y < 0 || pos.y > field.size() - 1 || pos.x > field[pos.y].size() - 1) + return false; + if (field[pos.y][pos.x] == '#') + return false; + if (field[pos.y][pos.x] == 'T') + return player_has_key; + return true; + } + + void Maze::render(const Player& player, const vector& entities, const bool& infomode_enabled) + { + for (int y = 0; y < field.size(); ++y) + { + for (int x = 0; x < field[y].size(); ++x) + { + if (y == player.get_pos().y && x == player.get_pos().x) + cout << "S"; + else { + bool an_enemy_is_at_this_position = false; + for (Entity e : entities) + if (e.is_at_position({x, y})) { + an_enemy_is_at_this_position = true; + cout << e.get_display_character(); + } + if (!an_enemy_is_at_this_position) + cout << field[y][x]; + } + cout << " "; + } + if (y == 0 && infomode_enabled) + { + const int steps = this->calculate_steps_until_win(player.get_pos(), 5); + if (steps < 999) + cout << steps << " Schritte bis zum Ziel"; + } + cout << "\n"; + } + } + + char Maze::get_field(const Vector2d& pos) const + { + return this->field[pos.y][pos.x]; + } + + void Maze::update_field(const Vector2d& pos, const char& target) + { + this->field[pos.y][pos.x] = target; + } + + Vector2d Maze::get_player_start_position() const + { + return this->player_start_position; + } + + Vector2d Maze::get_delta_vector(const Vector2d& pos1, const Vector2d& pos2) const { + int x_diff = pos1.x - pos2.x; + int y_diff = pos1.y - pos2.y; + + return {x_diff, y_diff}; + } + + int Maze::calculate_steps_until_win(Vector2d position, const int& steps) { + if (!this->is_pos_free(position, false)) + return 999; + if (this->get_field(position) == 'Z') + return 0; + if (steps <= 0) + return 999; + + vector i; + i.push_back(this->calculate_steps_until_win(position.get_new_updated(0, -1), steps - 1)); + i.push_back(this->calculate_steps_until_win(position.get_new_updated(0, 1), steps - 1)); + i.push_back(this->calculate_steps_until_win(position.get_new_updated(1, 0), steps - 1)); + i.push_back(this->calculate_steps_until_win(position.get_new_updated(-1, 0), steps - 1)); + + return MathUtil::get_min(i) + 1; + } + + vector Maze::get_entities() { + return this->enemies; + } +} // game diff --git a/src/Environment/Maze.h b/src/Environment/Maze.h new file mode 100644 index 0000000..81e551d --- /dev/null +++ b/src/Environment/Maze.h @@ -0,0 +1,80 @@ +#include "../std_lib_inc.h" +#include "../Util/Vector2d.h" + +#ifndef MAZE_H +#define MAZE_H + +namespace game +{ + class Player; + class Entity; + + /// Ein Labyrinth. + /// Besitzt ein Feld + class Maze + { + // class -> members private by default + private: + /// Das Spielfeld + vector> field; + /// Die Startposition des Spielers + Vector2d player_start_position; + /// Eine Liste an Gegnern + vector enemies; + + public: + /// Das Spielfeld + Maze(const Vector>& play_field, const Vector& player_start_position, const Vector& enemies); + /// Kontrolliere, ob der Spieler stirbt + /// @param player Der Spieler + /// @return Ob der Spieler tot ist + bool was_player_killed_by_ghost(const Player& player) const; + + /// Kontrolliere, ob der Spieler am Ziel ist + /// @param player Der Spieler + /// @return Ob der Spieler am Ziel ist + bool is_player_at_goal(const Player& player) const; + + /// Kontrolliere, ob eine bestimmte Position begehbar ist + /// @param pos Die Position, die überprüft werden soll + /// @param player_has_key If the player has at least one key + /// @return Ob die Position begehbar ist + bool is_pos_free(const Vector2d& pos, const bool& player_has_key) const; + + /// Zeige das Spielfeld in der Konsole an + /// @param player Der Spieler + /// @param entities Die Entities auf dem Spielfeld + /// @param infomode_enabled Ob der Infomode aktiv ist + void render(const Player& player, const vector& entities, const bool& infomode_enabled); + + /// Kriege den Wert einer Position + /// @param pos Die gewollte Position + /// @return Der Wert der Position + char get_field(const Vector2d& pos) const; + + /// Ersetze den Wert von einer Position + /// @param pos Die Position die ersetzt werden soll + /// @param target Der Wert, auf den die Position gesetzt werden soll + void update_field(const Vector2d& pos, const char& target); + + /// Kriege die Startposition des Spielers + /// @return Die Startposition des Spielers + Vector2d get_player_start_position() const; + + /// Berrechne den Abstand zwischen zwei Vektoren + /// @return Der Abstand als Differenzvektor + Vector2d get_delta_vector(const Vector2d& pos1, const Vector2d& pos2) const; + + /// Berechne wie viele Schritte benötigt werden, um das Labyrinth zu schaffen + /// @warning Steps nicht zu groß setzen! Diese Funktion ist 4-fach rekursiv! + /// @param position Die Startposition + /// @param steps Wie viele Schritte maximal gegangen werden sollten + /// @returns Wie viele Schritte benötigt werden + int calculate_steps_until_win(Vector2d position, const int& steps); + + /// Kriege alle eingelesenen Entities + vector get_entities(); + }; +} // game + +#endif //MAZE_H diff --git a/MalformedMaze.h b/src/Exceptions/MalformedMaze.h similarity index 92% rename from MalformedMaze.h rename to src/Exceptions/MalformedMaze.h index d75a2ac..c31c453 100644 --- a/MalformedMaze.h +++ b/src/Exceptions/MalformedMaze.h @@ -1,4 +1,4 @@ -#include "std_lib_inc.h" +#include "../std_lib_inc.h" #ifndef MALFORMEDMAZE_H #define MALFORMEDMAZE_H diff --git a/MovementNotPossible.h b/src/Exceptions/MovementNotPossible.h similarity index 92% rename from MovementNotPossible.h rename to src/Exceptions/MovementNotPossible.h index 3c7f34b..2eff7ff 100644 --- a/MovementNotPossible.h +++ b/src/Exceptions/MovementNotPossible.h @@ -1,4 +1,4 @@ -#include "std_lib_inc.h" +#include "../std_lib_inc.h" #ifndef MOVEMENTNOTPOSSIBLE_H #define MOVEMENTNOTPOSSIBLE_H diff --git a/UnkownAction.h b/src/Exceptions/UnkownAction.h similarity index 92% rename from UnkownAction.h rename to src/Exceptions/UnkownAction.h index d9ac740..216f9e7 100644 --- a/UnkownAction.h +++ b/src/Exceptions/UnkownAction.h @@ -1,4 +1,4 @@ -#include "std_lib_inc.h" +#include "../std_lib_inc.h" #ifndef UNKOWNACTION_H #define UNKOWNACTION_H diff --git a/GameState.h b/src/Util/GameState.h similarity index 100% rename from GameState.h rename to src/Util/GameState.h diff --git a/src/Util/MathUtil.cpp b/src/Util/MathUtil.cpp new file mode 100644 index 0000000..b9c6241 --- /dev/null +++ b/src/Util/MathUtil.cpp @@ -0,0 +1,11 @@ +#include "MathUtil.h" + +namespace game { + int MathUtil::get_min(const vector& numbers) { + int i = numbers[0]; + for (const int j : numbers) + if (j < i) + i = j; + return i; + } +} // game diff --git a/src/Util/MathUtil.h b/src/Util/MathUtil.h new file mode 100644 index 0000000..340a660 --- /dev/null +++ b/src/Util/MathUtil.h @@ -0,0 +1,16 @@ +#include "../std_lib_inc.h" +#ifndef UTIL_H +#define UTIL_H + +namespace game +{ + class MathUtil{ + public: + /// Gebe die minimale Nummer aus einer Liste zurück + /// @param numbers Eine liste an nummern + /// @returns Die kleinste Nummer + static int get_min(const vector& numbers); + }; +} // game + +#endif //UTIL_H diff --git a/src/Util/MazeParser.cpp b/src/Util/MazeParser.cpp new file mode 100644 index 0000000..9fb1876 --- /dev/null +++ b/src/Util/MazeParser.cpp @@ -0,0 +1,85 @@ +#include "MazeParser.h" +#include "../Environment/Maze.h" +#include "../Exceptions/MalformedMaze.h" +#include "../Entities/Entity.h" + +using game_exceptions::MalformedMaze; +using game::Entity; + +namespace game +{ + vector MazeParser::request_numbers_from_user(const int& amount_of_numbers) + { + int input; + vector list; + + for (int i = 0; i < amount_of_numbers; ++i) + { + cin >> input; + if (!cin) + throw MalformedMaze("Cin failed while reading numbers!"); + + if (input > MAX_MAZE_SIZE) + throw MalformedMaze("This maze is too big"); + list.push_back(input); + } + + return list; + } + + bool MazeParser::validate_maze_element(const char& target) + { + for (const char c : valid_maze_elements) + if (c == target) + return true; + return false; + } + + bool MazeParser::is_valid_enemy(const char& target) { + for (const char c : valid_enemies) + if (c == target) + return true; + return false; + } + + Maze MazeParser::request_maze_from_user() + { + vector maze_size = request_numbers_from_user(2); + + char input; + vector> field; + vector enemies; + + for (int y = 0; y < maze_size[0]; ++y) + { + vector row; + for (int x = 0; x < maze_size[1]; ++x) + { + cin >> input; + if (!cin) + throw MalformedMaze("Cin failed while reading chars!"); + + // I don't think that this is needed. I doubt that they test the check for this one ~Eric + // if (input == 'q') + // throw ExitGame("Schoenen Tag noch!"); + + if (!validate_maze_element(input)) + throw MalformedMaze("The given input is not a valid element of a maze!"); + if (is_valid_enemy(input)) + { + enemies.push_back(Entity({x, y}, input)); + row.push_back('.'); + } + else { + row.push_back(input); + } + } + + field.push_back(row); + } + + vector player_start_pos = request_numbers_from_user(2); + + return {field, player_start_pos, enemies}; + } // Beispieleingabe: `4 3 #.# #.K #T# #Z# 0 1` +} // game diff --git a/src/Util/MazeParser.h b/src/Util/MazeParser.h new file mode 100644 index 0000000..3de7fe0 --- /dev/null +++ b/src/Util/MazeParser.h @@ -0,0 +1,54 @@ +#include "../std_lib_inc.h" + +#ifndef MAZEPARSER_H +#define MAZEPARSER_H + +/* Legende + * S - Spieler + * Z - Ziel + * . - Leerer Raum (begehbar) + * # - Wand + * A - Animaltronic + * K - Schlüssel + * T - Tür + * B - Bowie + * C - Connellys + */ +namespace game +{ + /// Erlaubte Zeichen in einem Labyrinth + /// Ist eine Konstante, darf also in global scope + static const vector valid_maze_elements = {'Z', '.', '#', 'A', 'K', 'T', 'B', 'C'}; + /// Welche Geistertypen es gibt + static const vector valid_enemies = {'A', 'B', 'C'}; + /// Die Maximale Labyrinthgröße + static constexpr int MAX_MAZE_SIZE = 20; + + class Maze; + class MazeParser + { + private: + /// Lese eine bestimmte Anzahl an Nummern aus der Konsole + /// @param amount_of_numbers Wie viele Nummern eingelesen werden sollen + /// @return Die eingelesenen Nummern + static vector request_numbers_from_user(const int& amount_of_numbers); + + /// Kontrolliere, ob ein Zeichen im Labyrinth vorkommen darf + /// @param target Das Zeichen, welches Kontrolliert werden soll + /// @return Ob das gegebene Zeichen in einem Labyrinth vorkommen darf + static bool validate_maze_element(const char& target); + + /// Ob der angegebene char in valider Geist ist + /// @param target Der zu kontrollierende Wert + /// @returns Ob der Wert ein Valider Geist ist + static bool is_valid_enemy(const char& target); + + public: + /// Lese ein Labyrinth aus der Konsole + /// @return Das Labyrinth + /// @throws runtime_exception Falls die Eingabe nicht korrekt verlaufen ist. + static Maze request_maze_from_user(); + }; +} // game + +#endif //MAZEPARSER_H diff --git a/Vector2d.cpp b/src/Util/Vector2d.cpp similarity index 100% rename from Vector2d.cpp rename to src/Util/Vector2d.cpp diff --git a/Vector2d.h b/src/Util/Vector2d.h similarity index 100% rename from Vector2d.h rename to src/Util/Vector2d.h diff --git a/main.cpp b/src/main.cpp similarity index 82% rename from main.cpp rename to src/main.cpp index 8187159..aa72ad9 100644 --- a/main.cpp +++ b/src/main.cpp @@ -1,9 +1,11 @@ -#include "Maze.h" -#include "Game.h" -#include "MalformedMaze.h" -#include "GameState.h" +#include "Environment/Maze.h" +#include "Util/MazeParser.h" +#include "Environment/Game.h" +#include "Exceptions/MalformedMaze.h" +#include "Util/GameState.h" using game::Maze; +using game::MazeParser; using game::Game; using game::GameState; @@ -18,7 +20,7 @@ int main() GameState state = GameState::RUNNING; try { - Maze maze = Maze::request_maze_from_user(); + Maze maze = MazeParser::request_maze_from_user(); Game game = Game(maze); diff --git a/std_lib_inc.h b/src/std_lib_inc.h similarity index 100% rename from std_lib_inc.h rename to src/std_lib_inc.h