From 521398771934963adbb491faa077ade5161fd557 Mon Sep 17 00:00:00 2001 From: sebastian Date: Sun, 8 Feb 2026 14:22:13 +0100 Subject: [PATCH] UPD: Refactor Forest Tile Generation to seperate method --- CMakeLists.txt | 6 ++ src/engine/toolbox/Random.cpp | 5 ++ src/engine/toolbox/Random.h | 38 ++++++++++++ src/game/hexWorld/MapGenerator.h | 60 ++++--------------- .../tileGenerator/ForestTileGenerator.cpp | 48 +++++++++++++++ .../tileGenerator/ForestTileGenerator.h | 24 ++++++++ .../HexTileGeneratorStrategy.cpp | 5 ++ .../tileGenerator/HexTileGeneratorStrategy.h | 23 +++++++ 8 files changed, 159 insertions(+), 50 deletions(-) create mode 100644 src/engine/toolbox/Random.cpp create mode 100644 src/engine/toolbox/Random.h create mode 100644 src/game/hexWorld/tileGenerator/ForestTileGenerator.cpp create mode 100644 src/game/hexWorld/tileGenerator/ForestTileGenerator.h create mode 100644 src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.cpp create mode 100644 src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.h diff --git a/CMakeLists.txt b/CMakeLists.txt index 17b0f91..f7b167f 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -73,6 +73,12 @@ add_executable(Dicewars_Siedler src/main.cpp src/engine/renderer/shaders/TerrainShader.h src/engine/renderer/model/AssetManager.cpp src/engine/renderer/model/AssetManager.h + src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.cpp + src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.h + src/game/hexWorld/tileGenerator/ForestTileGenerator.cpp + src/game/hexWorld/tileGenerator/ForestTileGenerator.h + src/engine/toolbox/Random.cpp + src/engine/toolbox/Random.h ) target_include_directories(Dicewars_Siedler PRIVATE diff --git a/src/engine/toolbox/Random.cpp b/src/engine/toolbox/Random.cpp new file mode 100644 index 0000000..f46e530 --- /dev/null +++ b/src/engine/toolbox/Random.cpp @@ -0,0 +1,5 @@ +// +// Created by sebastian on 08.02.26. +// + +#include "Random.h" diff --git a/src/engine/toolbox/Random.h b/src/engine/toolbox/Random.h new file mode 100644 index 0000000..51355fa --- /dev/null +++ b/src/engine/toolbox/Random.h @@ -0,0 +1,38 @@ +// +// Created by sebastian on 08.02.26. +// + +#ifndef RANDOM_H +#define RANDOM_H +#include + + +class Random { +public: + Random() : gen(std::random_device{}()) {}; + + // Float zwischen min und max + float randomFloat(float min, float max) { + std::uniform_real_distribution dist(min, max); + return dist(gen); + } + + // Int zwischen min und max (inklusive) + int randomInt(int min, int max) { + std::uniform_int_distribution dist(min, max); + return dist(gen); + } + + // Bool mit Wahrscheinlichkeit p + bool randomBool(float probability = 0.5f) { + std::bernoulli_distribution dist(probability); + return dist(gen); + } + +private: + std::mt19937 gen; +}; + + + +#endif //RANDOM_H diff --git a/src/game/hexWorld/MapGenerator.h b/src/game/hexWorld/MapGenerator.h index 2a248eb..2afc880 100644 --- a/src/game/hexWorld/MapGenerator.h +++ b/src/game/hexWorld/MapGenerator.h @@ -10,27 +10,20 @@ #include "HexTile.h" #include "Map.h" #include "../../engine/renderer/model/AssetManager.h" +#include "../../engine/toolbox/Random.h" +#include "tileGenerator/ForestTileGenerator.h" class MapGenerator { public: static void generateHexMap(Map& map, int width, int height, float hexRadius, std::vector>& mapEntities) { // Zufallsgenerator initialisieren (einmal) - std::random_device rd; // Zufälliger Seed - std::mt19937 gen(rd()); // Mersenne Twister Generator + Random random; - // Verteilung definieren: hier z.B. 0 bis 9 - std::uniform_real_distribution dis(0.0f, 1.0f); map.tiles.clear(); float xOffset = hexRadius * std::sqrt(3.0f); float zOffset = hexRadius * 1.5f; - std::shared_ptr treeModel = AssetManager::getModel("lowPolyTree"); - std::shared_ptr treeModel2 = AssetManager::getModel("lowPolyTree2"); - std::vector> treeModels = {treeModel, treeModel2}; - - std::uniform_int_distribution treeModelDistribution(0, treeModels.size() - 1); - for (int r = 0; r < height; ++r) { for (int q = 0; q < width; ++q) { HexTile tile; @@ -43,53 +36,20 @@ public: tile.worldPos = glm::vec3(x, 0.0f, z); tile.radius = hexRadius; - float randomValue = dis(gen); + float randomValue = random.randomFloat(0.0f, 1.0f); if (randomValue < 0.5f) { tile.resourceType = RessourceType::WOOD; - - int treeCount = 3 + (int) (dis(gen) * 3); - std::uniform_real_distribution offsetDis(-hexRadius * 0.5f, hexRadius * 0.5f); - - float minDistance = 3.0f; // Minimaler Abstand zwischen Bäumen - - for (int i = 0; i < treeCount; ++i) { - glm::vec3 treePos; - bool validPos = false; - - // versuche zufällige Position, bis Abstand stimmt oder max Versuche erreicht - int attempts = 0; - const int maxAttempts = 10; - - while (!validPos && attempts < maxAttempts) { - treePos = tile.worldPos; - treePos.x += offsetDis(gen); - treePos.z += offsetDis(gen); - - validPos = true; - for (const auto& otherTree : tile.entitiesOnTile) { - if (glm::distance(treePos, otherTree->getPosition()) < minDistance) { - validPos = false; - break; - } - } - attempts++; - } - - if (!validPos) continue; // zu viele Versuche, überspringen - - int treeModelIndex = treeModelDistribution(gen); - auto treeEntity = std::make_shared(treeModels[treeModelIndex], treePos, 0, 0, 0, 1.f); - mapEntities.push_back(treeEntity); - tile.entitiesOnTile.push_back(treeEntity); - } - - + ForestTileGenerator forestTileGenerator; + const std::vector> forestEntities = forestTileGenerator.generateHexTile(random, tile.worldPos, mapEntities); + tile.entitiesOnTile = forestEntities; } - map.tiles.push_back(tile); } } } + +private: + }; diff --git a/src/game/hexWorld/tileGenerator/ForestTileGenerator.cpp b/src/game/hexWorld/tileGenerator/ForestTileGenerator.cpp new file mode 100644 index 0000000..86d85a2 --- /dev/null +++ b/src/game/hexWorld/tileGenerator/ForestTileGenerator.cpp @@ -0,0 +1,48 @@ +// +// Created by sebastian on 08.02.26. +// + +#include "ForestTileGenerator.h" + +#include "../../../engine/renderer/model/AssetManager.h" +#include "glm/detail/func_geometric.inl" + + +std::vector> ForestTileGenerator::generateHexTile(Random& random, glm::vec3 tilePos, std::vector> &mapEntities) const { + int treeCount = random.randomInt(minTreeCount, maxTreeCount); + + std::vector> entitiesOnTile; + std::shared_ptr treeModel = AssetManager::getModel("lowPolyTree"); + std::shared_ptr treeModel2 = AssetManager::getModel("lowPolyTree2"); + std::vector> treeModels = {treeModel, treeModel2}; + for (int i = 0; i < treeCount; ++i) { + glm::vec3 treePos; + bool validPos = false; + + // versuche zufällige Position, bis Abstand stimmt oder max Versuche erreicht + int attempts = 0; + + while (!validPos && attempts < maxAttempts) { + treePos = tilePos; + treePos.x += random.randomFloat(-hexRadius * 0.5f, hexRadius * 0.5f); + treePos.z += random.randomFloat(-hexRadius * 0.5f, hexRadius * 0.5f); + + validPos = true; + for (const auto& otherTree : entitiesOnTile) { + if (glm::distance(treePos, otherTree->getPosition()) < minDistance) { + validPos = false; + break; + } + } + attempts++; + } + + if (!validPos) continue; // zu viele Versuche, überspringen + + int treeModelIndex = random.randomInt(0, static_cast(treeModels.size()-1)); + auto treeEntity = std::make_shared(treeModels[treeModelIndex], treePos, 0, 0, 0, 1.f); + mapEntities.push_back(treeEntity); + entitiesOnTile.push_back(treeEntity); + } + return entitiesOnTile; +} diff --git a/src/game/hexWorld/tileGenerator/ForestTileGenerator.h b/src/game/hexWorld/tileGenerator/ForestTileGenerator.h new file mode 100644 index 0000000..618117d --- /dev/null +++ b/src/game/hexWorld/tileGenerator/ForestTileGenerator.h @@ -0,0 +1,24 @@ +// +// Created by sebastian on 08.02.26. +// + +#ifndef FORESTTILEGENERATOR_H +#define FORESTTILEGENERATOR_H +#include "HexTileGeneratorStrategy.h" + + +class ForestTileGenerator : public HexTileGeneratorStrategy { +public: + std::vector> generateHexTile(Random& random, glm::vec3 tilePos, std::vector>& mapEntities) const override; +private: + const int minTreeCount = 3; + const int maxTreeCount = 5; + const float minDistance = 3.0f; + const int maxAttempts = 10; + + const float hexRadius = 10.f; +}; + + + +#endif //FORESTTILEGENERATOR_H diff --git a/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.cpp b/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.cpp new file mode 100644 index 0000000..66676ef --- /dev/null +++ b/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.cpp @@ -0,0 +1,5 @@ +// +// Created by sebastian on 08.02.26. +// + +#include "HexTileGeneratorStrategy.h" diff --git a/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.h b/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.h new file mode 100644 index 0000000..9c7661b --- /dev/null +++ b/src/game/hexWorld/tileGenerator/HexTileGeneratorStrategy.h @@ -0,0 +1,23 @@ +// +// Created by sebastian on 08.02.26. +// + +#ifndef HEXTILEGENERATORSTRATEGY_H +#define HEXTILEGENERATORSTRATEGY_H +#include +#include + +#include "../../../engine/layer/entities/Entity.h" +#include "../../../engine/toolbox/Random.h" + + +class HexTileGeneratorStrategy { +public: + virtual ~HexTileGeneratorStrategy() = default; + + virtual std::vector> generateHexTile(Random& random, glm::vec3 tilePos, std::vector>& mapEntities) const = 0; +}; + + + +#endif //HEXTILEGENERATORSTRATEGY_H