diff --git a/CMakeLists.txt b/CMakeLists.txt index ce52906..156e8a6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -7,13 +7,18 @@ include_directories(.) add_executable(epr24pr3_ojanssen2 main.cpp + std_lib_inc.h Player.cpp Player.h PositionVector.cpp PositionVector.h - std_lib_inc.h Maze.h Maze.cpp MazeParser.h MazeParser.cpp + Game.h + Game.cpp + Exceptions/MovementNotPossible.h + Exceptions/MalformedMaze.h + Exceptions/UnkownAction.h ) diff --git a/Exceptions/MalformedMaze.h b/Exceptions/MalformedMaze.h new file mode 100644 index 0000000..2f0b0f0 --- /dev/null +++ b/Exceptions/MalformedMaze.h @@ -0,0 +1,26 @@ +// +// Created by moonleay on 12/17/24. +// + +#ifndef MALFORMEDMAZE_H +#define MALFORMEDMAZE_H + +namespace game_exceptions +{ + class MalformedMaze + { + string why; + + public: + MalformedMaze(string why): why(why) + { + } + + string what() + { + return this->why; + } + }; +} // game_exceptions + +#endif //MALFORMEDMAZE_H diff --git a/Exceptions/MovementNotPossible.h b/Exceptions/MovementNotPossible.h new file mode 100644 index 0000000..b6db2f0 --- /dev/null +++ b/Exceptions/MovementNotPossible.h @@ -0,0 +1,26 @@ +// +// Created by moonleay on 12/17/24. +// + +#ifndef MOVEMENTNOTPOSSIBLE_H +#define MOVEMENTNOTPOSSIBLE_H + +namespace game_exceptions +{ + class MovementNotPossible + { + string why; + + public: + MovementNotPossible(string why): why(why) + { + } + + string what() + { + return this->why; + } + }; +} // game_exceptions + +#endif //MOVEMENTNOTPOSSIBLE_H diff --git a/Exceptions/UnkownAction.h b/Exceptions/UnkownAction.h new file mode 100644 index 0000000..6be05b0 --- /dev/null +++ b/Exceptions/UnkownAction.h @@ -0,0 +1,26 @@ +// +// Created by moonleay on 12/17/24. +// + +#ifndef UNKOWNACTION_H +#define UNKOWNACTION_H + +namespace game_exceptions +{ + class UnkownAction + { + string why; + + public: + UnkownAction(string why): why(why) + { + } + + string what() + { + return this->why; + } + }; +} // game_exceptions + +#endif //UNKOWNACTION_H diff --git a/Game.cpp b/Game.cpp new file mode 100644 index 0000000..2c3de4b --- /dev/null +++ b/Game.cpp @@ -0,0 +1,122 @@ +// +// Created by moonleay on 12/17/24. +// + +#include "Game.h" +#include "MazeParser.h" +#include "Player.h" +#include "Maze.h" +#include "Exceptions/MovementNotPossible.h" +#include "Exceptions/UnkownAction.h" + +using game::Player; +using game::Maze; +using game_exceptions::UnkownAction; +using game_exceptions::MovementNotPossible; + +namespace game // Namespace = Scope with name and no features +{ + Game::Game(): maze({}, {}), player(0, 0) + { + // Lese das Labyrinth ein + maze = MazeParser::request_maze_from_user(); + + // Lese die Startpositon des Spielers aus dem eingelesenen Labyrinth aus + vector player_start_position = maze.get_player_start_position(); + + // Überschreibe den Spieler mit der gegebenen Startposition + this->player = Player(player_start_position[1], player_start_position[0]); + } + + PositionVector Game::handle_user_input(char input) + { + // Erstelle einen Vector mit einer Bewegung von 0 und 0 + PositionVector movement_vector = PositionVector(0, 0); + + // Kontrolliere, was der Spieler machen möchte. Speichere die erforderte Bewegung im Bewegungsvektor. + // Schreibe nachrichten in die Konsole, + // wenn nach Hilfe gefragt wird oder eine unbekannte Eingabe eingegeben wurde + switch (input) + { + case 'w': + movement_vector.update(0, -1); + break; + case 'a': + movement_vector.update(-1, 0); + break; + case 's': + movement_vector.update(0, 1); + break; + case 'd': + movement_vector.update(1, 0); + break; + case 'h': + // Schreibe hilfsreiche Tipps in die Konsole + cout << + "Du wurdest von einem Zauberer in ein Labyrinth gesperrt, nachdem du seine Künste beleidigt hast.\n" + << "Er laesst dich leben, wenn du es schaffst den Ausgang (Z) zu finden. Solltest du keinen Erfolg haben, laesst er dich verhungern.\n" + << "Auf deinem Abenteuer wirst du dabei boesen Geistern (A) begegnen und mit Schluesseln (K) Tueren (T) aufschliessen.\n" + << "Bewege dich mit 'w', 'a', 's' und 'd'.\n"; + break; + default: + // Die gewollte Aktion kenne ich nicht. Melde Fehler dem Nutzer + throw UnkownAction("Diese Eingabe kenne ich nicht. Gib 'h' ein, um eine Hilfe zu erhalten."); + } + + return movement_vector; + } + + void Game::run_game() + { + // Erstelle eine Variable für den Input + char game_input; + + // Durchlaufe die Hauptschleife des Spiels + while (true) + { + // Zeige dem Spieler das Spielfeld + maze.render(player); + + // Kontrolliere, ob der Spieler an einem Geist gestorben ist + if (maze.was_player_killed_by_ghost(player)) + { + cout << "Sie haben einen Geist getroffen! Game Over!\n"; + break; + } + + // Kontrolliere, ob der Spieler schon das Ziel erreicht hat + if (maze.is_player_at_goal(player)) + { + // Ziel erreicht! Herzlichen Glückwunsch! + cout << "Ziel erreicht! Herzlichen Glueckwunsch!\n"; + break; + } + + // Lese Eingabe des Spielers + cin >> game_input; + + PositionVector movement_vector = PositionVector(0, 0); + + try + { + movement_vector = handle_user_input(game_input); + } catch (UnkownAction& err) + { + cout << err.what() << "\n"; + } + + + // Kontrolliere gewollte Bewegung und setze sie um. + try + { + maze = player.move(maze, movement_vector); + } + catch (MovementNotPossible& err) + { + // Diese Bewegung ist nicht möglich! + // Gebe aus, warum. + cout << err.what() << "\n"; + } + } + } +} // game diff --git a/Game.h b/Game.h new file mode 100644 index 0000000..d43fdb8 --- /dev/null +++ b/Game.h @@ -0,0 +1,33 @@ +// +// Created by moonleay on 12/17/24. +// +#include "Maze.h" +#include "Player.h" + +#ifndef GAME_H +#define GAME_H + +namespace game +{ + /// Eine Instanz des Spiels + class Game + { + private: + Maze maze; + Player player; + + public: + Game(); + + /// Bearbeite die Eingabe des Spielers + /// @param input Die Eingabe des Nutzers + /// @return Der Bewegungsvektor, um den sich den Spieler bewegen möchte + /// @throws UnkownAction Wenn die Eingabe des Spielers unbekannt ist + static PositionVector handle_user_input(char input); + + /// Starte das Spiel + void run_game(); + }; +} // game + +#endif //GAME_H diff --git a/Maze.h b/Maze.h index 3fe70dc..48159ba 100644 --- a/Maze.h +++ b/Maze.h @@ -25,10 +25,6 @@ namespace game /// Das Spielfeld Maze(vector> play_field, vector player_start_position); - /// Ein Standard Konstruktor - /// Variablen innerhalb der Klasse bleiben leer - Maze() = default; - /// Kontrolliere, ob der Spieler stirbt /// @param player Der Spieler /// @return Ob der Spieler tot ist diff --git a/MazeParser.cpp b/MazeParser.cpp index 3eac229..37118f7 100644 --- a/MazeParser.cpp +++ b/MazeParser.cpp @@ -4,6 +4,10 @@ #include "MazeParser.h" +#include "Exceptions/MalformedMaze.h" + +using game_exceptions::MalformedMaze; + namespace game { vector MazeParser::request_numbers_from_user(const int amount_of_numbers) @@ -22,7 +26,7 @@ namespace game // Sollte etwas schiefgelaufen sein, dann wirf eine Exception if (!cin) - throw runtime_error("Cin failed while reading numbers!"); + throw MalformedMaze("Cin failed while reading numbers!"); // Schreibe die gelesene Zahl auf die Liste list.push_back(input); @@ -68,11 +72,11 @@ namespace game // Werfe eine Exception, wenn der Input nicht lesbar ist, d.h. Nutzer hat eine Falsch eingabe getätigt. if (!cin) - throw runtime_error("Cin failed while reading chars!"); + throw MalformedMaze("Cin failed while reading chars!"); // Kontrolliere, ob das Element in einem Labyrinth vorkommen darf if (!is_valid_maze_element(input)) - throw runtime_error("The given input is not a valid element of a maze!"); + throw MalformedMaze("The given input is not a valid element of a maze!"); // Schreibe den eingelesenen Wert in die aktuelle Reihe row.push_back(input); diff --git a/Player.cpp b/Player.cpp index 574f194..50c4994 100644 --- a/Player.cpp +++ b/Player.cpp @@ -5,6 +5,9 @@ #include "std_lib_inc.h" #include "Player.h" #include "Maze.h" +#include "Exceptions/MovementNotPossible.h" + +using game_exceptions::MovementNotPossible; namespace game { @@ -55,7 +58,7 @@ namespace game } } else - throw runtime_error("Bewegung nicht moeglich!"); + throw MovementNotPossible("Bewegung nicht moeglich!"); return maze; } diff --git a/main.cpp b/main.cpp index 099ee29..b7325b9 100644 --- a/main.cpp +++ b/main.cpp @@ -1,113 +1,42 @@ -#include "Maze.h" #include "std_lib_inc.h" -#include "Player.h" +#include "Maze.h" #include "PositionVector.h" #include "MazeParser.h" +#include "Game.h" +#include "Exceptions/MalformedMaze.h" +#include "Exceptions/MovementNotPossible.h" +#include "Exceptions/UnkownAction.h" using game::Player; using game::PositionVector; using game::Maze; using game::MazeParser; +using game::Game; + +using game_exceptions::MalformedMaze; +using game_exceptions::UnkownAction; +using game_exceptions::MovementNotPossible; // Ein Programm, welches dir erlaubt ein Labyrinth zu erkunden mit 'w', 'a', 's', und 'd'. -const vector player_start_position = {4, 0}; int main() { - // Erstelle eine Variable, in der wir das eingelesene Labyrinth speichern - Maze maze; - try { - // Lese das Labyrinth ein - maze = MazeParser::request_maze_from_user(); + // Erstelle eine Variable, in der wir das eingelesene Labyrinth speichern + Game game = Game(); + + // Starte das Spiel + game.run_game(); } - catch (...) + catch (MalformedMaze& _) { // Das Labyrinth einlesen hat nicht geklappt. Gebe Fehlermeldung aus und beende das Programm. cout << "Fehler beim Einlesen des Labyrinths.\n"; return 0; } - // Lese die Startpositon des Spielers aus dem eingelesenen Labyrinth aus - vector player_start_position = maze.get_player_start_position(); - // Erstelle einen Spieler mit der gegebenen start position - Player player = Player(player_start_position[1], player_start_position[0]); - - // Erstelle eine Variable für den Input - char game_input; - - // Durchlaufe die Hauptschleife des Spiels - while (true) - { - // Zeige dem Spieler das Spielfeld - maze.render(player); - - // Kontrolliere, ob der Spieler an einem Geist gestorben ist - if (maze.was_player_killed_by_ghost(player)) - { - cout << "Sie haben einen Geist getroffen! Game Over!\n"; - break; - } - - // Kontrolliere, ob der Spieler schon das Ziel erreicht hat - if (maze.is_player_at_goal(player)) - { - // Ziel erreicht! Herzlichen Glückwunsch! - cout << "Ziel erreicht! Herzlichen Glueckwunsch!\n"; - break; - } - - // Lese Eingabe des Spielers - cin >> game_input; - - // Erstelle einen Vector mit einer Bewegung von 0 und 0 - PositionVector movement_vector = PositionVector(0, 0); - - // Kontrolliere, was der Spieler machen möchte. Speichere die erforderte Bewegung im Bewegungsvektor. - // Schreibe nachrichten in die Konsole, - // wenn nach Hilfe gefragt wird oder eine unbekannte Eingabe eingegeben wurde - switch (game_input) - { - case 'w': - movement_vector.update(0, -1); - break; - case 'a': - movement_vector.update(-1, 0); - break; - case 's': - movement_vector.update(0, 1); - break; - case 'd': - movement_vector.update(1, 0); - break; - case 'h': - // Schreibe hilfsreiche Tipps in die Konsole - cout << - "Du wurdest von einem Zauberer in ein Labyrinth gesperrt, nachdem du seine Künste beleidigt hast.\n" - << "Er laesst dich leben, wenn du es schaffst den Ausgang (Z) zu finden. Solltest du keinen Erfolg haben, laesst er dich verhungern.\n" - << "Auf deinem Abenteuer wirst du dabei boesen Geistern (A) begegnen und mit Schluesseln (K) Tueren (T) aufschliessen.\n" - << "Bewege dich mit 'w', 'a', 's' und 'd'.\n"; - break; - default: - // Die gewollte Aktion kenne ich nicht. Schreibe eine Fehlernachricht in die Konsole - cout << "Diese Eingabe kenne ich nicht. Gib 'h' ein, um eine Hilfe zu erhalten.\n"; - break; - } - - // Kontrolliere gewollte Bewegung und setze sie um. - try - { - maze = player.move(maze, movement_vector); - } - catch (runtime_error& err) - { - // Diese Bewegung ist nicht möglich! - // Gebe aus, warum. - cout << err.what() << "\n"; - } - } // Beende das Programm return 0; }