mirror of
https://github.com/Motschen/Adventura.git
synced 2025-12-13 10:25:09 +01:00
docs: add more comments
This commit is contained in:
4
TEST.txt
4
TEST.txt
@@ -1,7 +1,7 @@
|
|||||||
Für einen automatisierten Test, führe das Programm mit dem Argument --test aus
|
Für einen automatisierten Test, führe das Programm mit dem Argument --test aus. Zum Spielen einfach ohne Parameter.
|
||||||
|
|
||||||
asdddddddddddddddwwwwwwddddddwwwwdddd
|
asdddddddddddddddwwwwwwddddddwwwwdddd
|
||||||
aaaaaaassssssddddssssdddddddddddwwwwwddddddwwwwdddddddddddddddddddd
|
aaaaaaassssssddddssssdddddddddddwwwwwddddddwwwwdddddddddddddddddddd
|
||||||
ddddddddddddddddddddddddddddddddddwwwwwdddddddddd
|
ddddddddddddddddddddddddddddddddddwwwwwdddddddddd
|
||||||
aaddddddddddwwwwwwddddddddddddddddddddddd
|
aaddddddddddwwwwwwddddddddddddddddddddddd
|
||||||
ddddwwwwwwddddddddddddddddddddddddddddddddddddaaaaaaaaaaaaaaaaaaaaassssdddddddddddddddddddddddddddddddddddddddddddddddddwwwwwwddddddddddddddd
|
ddddwwwwwwddddddddddddddddddddddddddddddddddddaaaaaaaaaaaaaaaaaaaaasssssdddddddddddddddddddddddddddddddddddddddddddddddddwwwwwwddddddddddddddd
|
||||||
@@ -32,6 +32,14 @@ public:
|
|||||||
registerBlock(SAND);
|
registerBlock(SAND);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets a block by its encoding.
|
||||||
|
*
|
||||||
|
* If the block is not registered, a non-solid decoration block is created for it.
|
||||||
|
*
|
||||||
|
* @param encoding The encoding of the block to get.
|
||||||
|
* @return The block with the given encoding.
|
||||||
|
*/
|
||||||
const Block getByEncoding(char encoding) {
|
const Block getByEncoding(char encoding) {
|
||||||
for (Block block : registeredBlocks) {
|
for (Block block : registeredBlocks) {
|
||||||
if (block.getEncoding() == encoding) return block;
|
if (block.getEncoding() == encoding) return block;
|
||||||
|
|||||||
@@ -2,27 +2,78 @@
|
|||||||
class BlockSettings {
|
class BlockSettings {
|
||||||
public:
|
public:
|
||||||
BlockSettings() {}
|
BlockSettings() {}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is solid ground, meaning players and objects will
|
||||||
|
* not fall through.
|
||||||
|
*
|
||||||
|
* @return true if the block is solid, false otherwise.
|
||||||
|
*/
|
||||||
bool isSolid() {
|
bool isSolid() {
|
||||||
return isSolid_;
|
return isSolid_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block has collision, disallowing players to pass through it.
|
||||||
|
*
|
||||||
|
* @return true if the block has collision, false otherwise.
|
||||||
|
*/
|
||||||
bool hasCollision() {
|
bool hasCollision() {
|
||||||
return hasCollision_;
|
return hasCollision_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is affected by gravity, meaning it will fall down
|
||||||
|
* until it reaches stable ground.
|
||||||
|
*
|
||||||
|
* @return true if the block is affected by gravity, false otherwise.
|
||||||
|
*/
|
||||||
bool hasGravity() {
|
bool hasGravity() {
|
||||||
return hasGravity_;
|
return hasGravity_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block can be pushed by players.
|
||||||
|
*
|
||||||
|
* @return true if the block can be pushed, false otherwise.
|
||||||
|
*/
|
||||||
bool isPushable() {
|
bool isPushable() {
|
||||||
return isPushable_;
|
return isPushable_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is lethal to players, causing them to be killed instantly upon contact.
|
||||||
|
*
|
||||||
|
* @return true if the block is lethal, false otherwise.
|
||||||
|
*/
|
||||||
bool isLethal() {
|
bool isLethal() {
|
||||||
return isLethal_;
|
return isLethal_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is brittle, meaning it will fall or break
|
||||||
|
* when a player passes over it.
|
||||||
|
*
|
||||||
|
* @return true if the block is brittle, false otherwise.
|
||||||
|
*/
|
||||||
bool isBrittle() {
|
bool isBrittle() {
|
||||||
return isBrittle_;
|
return isBrittle_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is climbable from the top, allowing players above to climb down.
|
||||||
|
*
|
||||||
|
* @return true if the block is climbable from the top, false otherwise.
|
||||||
|
*/
|
||||||
bool isClimbableFromTop() {
|
bool isClimbableFromTop() {
|
||||||
return isClimbableFromTop_;
|
return isClimbableFromTop_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if the block is climbable from the bottom, allowing players to climb up.
|
||||||
|
*
|
||||||
|
* @return true if the block is climbable from the bottom, false otherwise.
|
||||||
|
*/
|
||||||
bool isClimbableFromBottom() {
|
bool isClimbableFromBottom() {
|
||||||
return isClimbableFromBottom_;
|
return isClimbableFromBottom_;
|
||||||
}
|
}
|
||||||
@@ -41,38 +92,83 @@ class BlockSettings {
|
|||||||
};
|
};
|
||||||
class BlockSettingsBuilder {
|
class BlockSettingsBuilder {
|
||||||
public:
|
public:
|
||||||
|
/**
|
||||||
|
* Marks the block non-solid, letting players and objects fall through.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder nonSolid() {
|
BlockSettingsBuilder nonSolid() {
|
||||||
blockSettings.isSolid_ = false;
|
blockSettings.isSolid_ = false;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Makes the block pushable by players.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder pushable() {
|
BlockSettingsBuilder pushable() {
|
||||||
blockSettings.isPushable_ = true;
|
blockSettings.isPushable_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Marks the block as collidable, disallowing players to pass through it.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder collidable() {
|
BlockSettingsBuilder collidable() {
|
||||||
blockSettings.hasCollision_ = true;
|
blockSettings.hasCollision_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Marks the block as affected by gravity, making it fall down until it reaches stable ground.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder gravity() {
|
BlockSettingsBuilder gravity() {
|
||||||
blockSettings.hasGravity_ = true;
|
blockSettings.hasGravity_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Makes the block lethal to players, killing them instantly if they touch it.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder lethal() {
|
BlockSettingsBuilder lethal() {
|
||||||
blockSettings.isLethal_ = true;
|
blockSettings.isLethal_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Makes the block brittle, making it fall down when a player passes over it.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder brittle() {
|
BlockSettingsBuilder brittle() {
|
||||||
blockSettings.isBrittle_ = true;
|
blockSettings.isBrittle_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Marks the block as climbable from the top, allowing players above to climb down.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder climbableFromTop() {
|
BlockSettingsBuilder climbableFromTop() {
|
||||||
blockSettings.isClimbableFromTop_ = true;
|
blockSettings.isClimbableFromTop_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Marks the block as climbable from the bottom, allowing players below to climb up.
|
||||||
|
*
|
||||||
|
* @return BlockSettingsBuilder with changed settings
|
||||||
|
*/
|
||||||
BlockSettingsBuilder climbableFromBottom() {
|
BlockSettingsBuilder climbableFromBottom() {
|
||||||
blockSettings.isClimbableFromBottom_ = true;
|
blockSettings.isClimbableFromBottom_ = true;
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
/**
|
||||||
|
* Returns the built BlockSettings object.
|
||||||
|
*
|
||||||
|
* @return BlockSettings object with the set properties
|
||||||
|
*/
|
||||||
BlockSettings build() {
|
BlockSettings build() {
|
||||||
return blockSettings;
|
return blockSettings;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,10 +1,8 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <iostream>
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <streambuf>
|
|
||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
@@ -16,21 +14,6 @@ using std::endl;
|
|||||||
using std::string;
|
using std::string;
|
||||||
using std::vector;
|
using std::vector;
|
||||||
|
|
||||||
string readInput(string feedback);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Reads a string from the user. The string is expected to be the first
|
|
||||||
* argument before a comma.
|
|
||||||
*
|
|
||||||
* @return The string read from the user.
|
|
||||||
*/
|
|
||||||
string readInput(string feedback) {
|
|
||||||
string name;
|
|
||||||
cout << feedback << endl;
|
|
||||||
getline(std::cin, name);
|
|
||||||
return name;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a list of all files in the specified directory, sorted alphabetically.
|
* Get a list of all files in the specified directory, sorted alphabetically.
|
||||||
*
|
*
|
||||||
@@ -38,11 +21,11 @@ string readInput(string feedback) {
|
|||||||
*
|
*
|
||||||
* @param dir The directory to get the file names from
|
* @param dir The directory to get the file names from
|
||||||
* @param extension The file extension to filter by
|
* @param extension The file extension to filter by
|
||||||
* @return A list of all file names in the specified directory, sorted alphabetically.
|
* @return A list of all filtered file names in the specified directory, sorted alphabetically.
|
||||||
*/
|
*/
|
||||||
vector<string> getOrderedFileNames(string dir, string extension) {
|
vector<string> getOrderedFileNames(string dir, string extension) {
|
||||||
vector<string> worlds;
|
vector<string> worlds;
|
||||||
// This used to be so elegant and iterate over all files in the worlds directory,
|
// This used to be elegant and iterate over all files in the worlds directory,
|
||||||
// but because of the weird restriction with no folders being allowed, we just filter the files based on their extension.
|
// but because of the weird restriction with no folders being allowed, we just filter the files based on their extension.
|
||||||
for (auto & entry : std::filesystem::directory_iterator(dir)) {
|
for (auto & entry : std::filesystem::directory_iterator(dir)) {
|
||||||
if (static_cast<string>(entry.path()).ends_with(extension)) worlds.push_back(entry.path());
|
if (static_cast<string>(entry.path()).ends_with(extension)) worlds.push_back(entry.path());
|
||||||
@@ -62,22 +45,10 @@ vector<string> getOrderedFileNames(string dir, string extension) {
|
|||||||
* @return The content of the file as a vector of strings.
|
* @return The content of the file as a vector of strings.
|
||||||
*/
|
*/
|
||||||
vector<string> readFileAsVector(const string& fileLocation) {
|
vector<string> readFileAsVector(const string& fileLocation) {
|
||||||
|
vector<string> lines;
|
||||||
vector<string> lines;
|
|
||||||
// string currentLine = "";
|
|
||||||
// for (char c : readFile(fileLocation)) {
|
|
||||||
// if (c == '\n' || c == '\r') {
|
|
||||||
// file.push_back(currentLine);
|
|
||||||
// currentLine = "";
|
|
||||||
// }
|
|
||||||
// else {
|
|
||||||
// currentLine += c;
|
|
||||||
// }
|
|
||||||
// }
|
|
||||||
// file.push_back(currentLine);
|
|
||||||
|
|
||||||
std::ifstream file(fileLocation);
|
std::ifstream file(fileLocation);
|
||||||
// Read the file line by line into a string
|
// Read the file line by line
|
||||||
string line;
|
string line;
|
||||||
while (std::getline(file, line)) {
|
while (std::getline(file, line)) {
|
||||||
lines.push_back(line);
|
lines.push_back(line);
|
||||||
@@ -87,7 +58,8 @@ vector<string> readFileAsVector(const string& fileLocation) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Prints the content of a file line by line into the console (in the specified color).
|
* Prints the content of a file into the console line by line.
|
||||||
|
*
|
||||||
* We use this to print our death and victory screens.
|
* We use this to print our death and victory screens.
|
||||||
*
|
*
|
||||||
* @param fileLocation Path to the file to be printed.
|
* @param fileLocation Path to the file to be printed.
|
||||||
|
|||||||
@@ -2,4 +2,5 @@ Welcome to Adventura v1.0 by Martin Prokoph!
|
|||||||
|
|
||||||
No Arguments: Play through all levels inside the world folder (in alphabetical order)
|
No Arguments: Play through all levels inside the world folder (in alphabetical order)
|
||||||
--level, -l <levelName>: Load (only) the specified level
|
--level, -l <levelName>: Load (only) the specified level
|
||||||
|
--test, -t: Automatically play through all levels
|
||||||
--help, -h: Show this screen
|
--help, -h: Show this screen
|
||||||
64
main.cpp
64
main.cpp
@@ -15,6 +15,7 @@ using std::cout;
|
|||||||
using std::endl;
|
using std::endl;
|
||||||
|
|
||||||
bool startWorld(string worldFile);
|
bool startWorld(string worldFile);
|
||||||
|
bool parseArgs(int argc, char *argv[]);
|
||||||
|
|
||||||
bool testMode = false;
|
bool testMode = false;
|
||||||
unsigned int worldIndex = 2;
|
unsigned int worldIndex = 2;
|
||||||
@@ -27,27 +28,8 @@ unsigned int worldIndex = 2;
|
|||||||
* If the player reaches the goal of the final level, print the victory screen and exit.
|
* If the player reaches the goal of the final level, print the victory screen and exit.
|
||||||
*/
|
*/
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
if (argc > 1) {
|
if (parseArgs(argc, argv)) return 0;
|
||||||
for (int i = 1; i < argc; i++) {
|
|
||||||
string arg = string(argv[i]);
|
|
||||||
if (arg == "-h" || arg == "--help")
|
|
||||||
break;
|
|
||||||
else if (arg == "-t" || arg == "--test")
|
|
||||||
testMode = true;
|
|
||||||
|
|
||||||
else if ((arg == "-l" || arg == "--level") && argc > i + 1) {
|
|
||||||
if (!startWorld("./worlds/" + string(argv[i+1])))
|
|
||||||
return 0; // Load only the specified world
|
|
||||||
else
|
|
||||||
printFile("./completed_single_level.screen.txt", Color::BRIGHT_GREEN);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!testMode) {
|
|
||||||
printFile("./help.screen.txt", Color::BRIGHT_BLUE); // Print help screen
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!testMode) {
|
if (!testMode) {
|
||||||
printFile("./start.screen.txt", Color::BRIGHT_YELLOW);
|
printFile("./start.screen.txt", Color::BRIGHT_YELLOW);
|
||||||
waitForInput();
|
waitForInput();
|
||||||
@@ -83,4 +65,44 @@ bool startWorld(string worldFile) {
|
|||||||
worldIndex++;
|
worldIndex++;
|
||||||
if (!player.isAlive()) printFile("./death.screen.txt", Color::BRIGHT_RED);
|
if (!player.isAlive()) printFile("./death.screen.txt", Color::BRIGHT_RED);
|
||||||
return player.hasReachedGoal();
|
return player.hasReachedGoal();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Parses command-line arguments to set the game's configuration.
|
||||||
|
*
|
||||||
|
* Recognizes the following arguments:
|
||||||
|
* - "-h" or "--help": Displays the help screen and exits.
|
||||||
|
* - "-t" or "--test": Enables test mode, starting an automated playthrough.
|
||||||
|
* - "-l" or "--level <levelName>": Loads and plays only the specified level.
|
||||||
|
*
|
||||||
|
* If a custom action is specified, the function returns true to indicate
|
||||||
|
* immediate termination after executing the requested action.
|
||||||
|
*
|
||||||
|
* @param argc The number of command-line arguments.
|
||||||
|
* @param argv The array containing the command-line arguments.
|
||||||
|
* @return true if the program should exit after handling the arguments, false otherwise.
|
||||||
|
*/
|
||||||
|
bool parseArgs(int argc, char *argv[]) {
|
||||||
|
if (argc > 1) {
|
||||||
|
for (int i = 1; i < argc; i++) {
|
||||||
|
string arg = string(argv[i]);
|
||||||
|
if (arg == "-h" || arg == "--help")
|
||||||
|
break;
|
||||||
|
else if (arg == "-t" || arg == "--test")
|
||||||
|
testMode = true;
|
||||||
|
|
||||||
|
else if ((arg == "-l" || arg == "--level") && argc > i + 1) {
|
||||||
|
if (!startWorld("./" + string(argv[i+1])))
|
||||||
|
return true; // Load only the specified world
|
||||||
|
else
|
||||||
|
printFile("./completed_single_level.screen.txt", Color::BRIGHT_GREEN);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!testMode) {
|
||||||
|
printFile("./help.screen.txt", Color::BRIGHT_BLUE); // Print help screen
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
@@ -27,7 +27,7 @@ bool is_in(First &&first, T && ... t) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Waits until the user enters a key.
|
* Waits until the user enters a valid key.
|
||||||
* Used to prompt the user to press any key to continue.
|
* Used to prompt the user to press any key to continue.
|
||||||
*/
|
*/
|
||||||
void waitForInput() {
|
void waitForInput() {
|
||||||
|
|||||||
@@ -80,4 +80,5 @@ void printGuide() {
|
|||||||
for (std::pair<string, Color> p : guide) {
|
for (std::pair<string, Color> p : guide) {
|
||||||
cout << p.second << p.first << endl;
|
cout << p.second << p.first << endl;
|
||||||
}
|
}
|
||||||
|
cout << endl << Color::RESET << "WASD + Enter -> Spiel starten" << endl;
|
||||||
}
|
}
|
||||||
Reference in New Issue
Block a user