summaryrefslogtreecommitdiff
path: root/src/tools
diff options
context:
space:
mode:
Diffstat (limited to 'src/tools')
-rw-r--r--src/tools/CMakeLists.txt7
-rw-r--r--src/tools/dbimport/Main.cpp17
-rw-r--r--src/tools/map_extractor/System.cpp10
-rw-r--r--src/tools/map_extractor/adt.cpp10
-rw-r--r--src/tools/map_extractor/adt.h10
-rw-r--r--src/tools/map_extractor/dbcfile.cpp10
-rw-r--r--src/tools/map_extractor/dbcfile.h10
-rw-r--r--src/tools/map_extractor/loadlib.cpp10
-rw-r--r--src/tools/map_extractor/loadlib/loadlib.h10
-rw-r--r--src/tools/map_extractor/mpq_libmpq.cpp10
-rw-r--r--src/tools/map_extractor/mpq_libmpq04.h10
-rw-r--r--src/tools/map_extractor/wdt.cpp10
-rw-r--r--src/tools/map_extractor/wdt.h10
-rw-r--r--src/tools/mmaps_generator/Config.cpp276
-rw-r--r--src/tools/mmaps_generator/Config.h159
-rw-r--r--src/tools/mmaps_generator/Info/readme.txt39
-rw-r--r--src/tools/mmaps_generator/IntermediateValues.cpp52
-rw-r--r--src/tools/mmaps_generator/IntermediateValues.h14
-rw-r--r--src/tools/mmaps_generator/MapBuilder.cpp166
-rw-r--r--src/tools/mmaps_generator/MapBuilder.h49
-rw-r--r--src/tools/mmaps_generator/PathCommon.h16
-rw-r--r--src/tools/mmaps_generator/PathGenerator.cpp171
-rw-r--r--src/tools/mmaps_generator/TerrainBuilder.cpp34
-rw-r--r--src/tools/mmaps_generator/TerrainBuilder.h15
-rw-r--r--src/tools/mmaps_generator/mmaps-config.yaml145
-rw-r--r--src/tools/vmap4_assembler/VMapAssembler.cpp10
-rw-r--r--src/tools/vmap4_extractor/adtfile.cpp10
-rw-r--r--src/tools/vmap4_extractor/adtfile.h10
-rw-r--r--src/tools/vmap4_extractor/dbcfile.cpp10
-rw-r--r--src/tools/vmap4_extractor/dbcfile.h10
-rw-r--r--src/tools/vmap4_extractor/gameobject_extract.cpp10
-rw-r--r--src/tools/vmap4_extractor/loadlib/loadlib.h10
-rw-r--r--src/tools/vmap4_extractor/model.cpp10
-rw-r--r--src/tools/vmap4_extractor/model.h10
-rw-r--r--src/tools/vmap4_extractor/modelheaders.h10
-rw-r--r--src/tools/vmap4_extractor/mpq_libmpq.cpp10
-rw-r--r--src/tools/vmap4_extractor/mpq_libmpq04.h10
-rw-r--r--src/tools/vmap4_extractor/vec3d.h10
-rw-r--r--src/tools/vmap4_extractor/vmapexport.cpp10
-rw-r--r--src/tools/vmap4_extractor/vmapexport.h10
-rw-r--r--src/tools/vmap4_extractor/wdtfile.cpp10
-rw-r--r--src/tools/vmap4_extractor/wdtfile.h10
-rw-r--r--src/tools/vmap4_extractor/wmo.cpp10
-rw-r--r--src/tools/vmap4_extractor/wmo.h10
44 files changed, 968 insertions, 492 deletions
diff --git a/src/tools/CMakeLists.txt b/src/tools/CMakeLists.txt
index 9efea7aaec..03fa926fd4 100644
--- a/src/tools/CMakeLists.txt
+++ b/src/tools/CMakeLists.txt
@@ -140,7 +140,8 @@ foreach(TOOL_NAME ${TOOLS_BUILD_LIST})
mpq
zlib
Recast
- g3dlib)
+ g3dlib
+ fkYAML)
endif()
unset(TOOL_PUBLIC_INCLUDES)
@@ -170,4 +171,8 @@ foreach(TOOL_NAME ${TOOLS_BUILD_LIST})
elseif (WIN32)
install(TARGETS ${TOOL_PROJECT_NAME} DESTINATION "${CMAKE_INSTALL_PREFIX}")
endif()
+
+ if (${TOOL_PROJECT_NAME} STREQUAL "mmaps_generator")
+ install(FILES ${SOURCE_TOOL_PATH}/mmaps-config.yaml DESTINATION bin)
+ endif()
endforeach()
diff --git a/src/tools/dbimport/Main.cpp b/src/tools/dbimport/Main.cpp
index 87371f62a3..06b3ce6658 100644
--- a/src/tools/dbimport/Main.cpp
+++ b/src/tools/dbimport/Main.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -109,8 +109,8 @@ bool StartDB()
DatabaseLoader loader =
modules.empty() ? DatabaseLoader("dbimport") :
- (modules == "all") ? DatabaseLoader("dbimport", DatabaseLoader::DATABASE_NONE, AC_MODULES_LIST) :
- DatabaseLoader("dbimport", DatabaseLoader::DATABASE_NONE, modules);
+ (modules == "all") ? DatabaseLoader("dbimport", DatabaseLoader::DATABASE_MASK_ALL, AC_MODULES_LIST) :
+ DatabaseLoader("dbimport", DatabaseLoader::DATABASE_MASK_ALL, modules);
loader
.AddDatabase(LoginDatabase, "Login")
@@ -140,7 +140,8 @@ variables_map GetConsoleArguments(int argc, char** argv, fs::path& configFile)
("help,h", "print usage message")
("version,v", "print version build info")
("dry-run,d", "Dry run")
- ("config,c", value<fs::path>(&configFile)->default_value(fs::path(sConfigMgr->GetConfigPath() + std::string(_ACORE_DB_IMPORT_CONFIG))), "use <arg> as configuration file");
+ ("config,c", value<fs::path>(&configFile)->default_value(fs::path(sConfigMgr->GetConfigPath() + std::string(_ACORE_DB_IMPORT_CONFIG))), "use <arg> as configuration file")
+ ("config-policy", value<std::string>()->value_name("policy"), "override config severity policy (e.g. default=skip,critical_option=fatal)");
variables_map variablesMap;
diff --git a/src/tools/map_extractor/System.cpp b/src/tools/map_extractor/System.cpp
index 4396ed47f7..4fef9164e7 100644
--- a/src/tools/map_extractor/System.cpp
+++ b/src/tools/map_extractor/System.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/adt.cpp b/src/tools/map_extractor/adt.cpp
index 7717080c82..7a3c524182 100644
--- a/src/tools/map_extractor/adt.cpp
+++ b/src/tools/map_extractor/adt.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/adt.h b/src/tools/map_extractor/adt.h
index 01917e66f9..4cbbb20a07 100644
--- a/src/tools/map_extractor/adt.h
+++ b/src/tools/map_extractor/adt.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/dbcfile.cpp b/src/tools/map_extractor/dbcfile.cpp
index 589511666d..ecec134aea 100644
--- a/src/tools/map_extractor/dbcfile.cpp
+++ b/src/tools/map_extractor/dbcfile.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/dbcfile.h b/src/tools/map_extractor/dbcfile.h
index 5fd5365938..0fb6298fc1 100644
--- a/src/tools/map_extractor/dbcfile.h
+++ b/src/tools/map_extractor/dbcfile.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/loadlib.cpp b/src/tools/map_extractor/loadlib.cpp
index 8434fa641c..67cf659142 100644
--- a/src/tools/map_extractor/loadlib.cpp
+++ b/src/tools/map_extractor/loadlib.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/loadlib/loadlib.h b/src/tools/map_extractor/loadlib/loadlib.h
index 68fd5ea00b..6a34ea62f8 100644
--- a/src/tools/map_extractor/loadlib/loadlib.h
+++ b/src/tools/map_extractor/loadlib/loadlib.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/mpq_libmpq.cpp b/src/tools/map_extractor/mpq_libmpq.cpp
index 5b70a933ad..f9101027ea 100644
--- a/src/tools/map_extractor/mpq_libmpq.cpp
+++ b/src/tools/map_extractor/mpq_libmpq.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/mpq_libmpq04.h b/src/tools/map_extractor/mpq_libmpq04.h
index dece851e9e..6576111390 100644
--- a/src/tools/map_extractor/mpq_libmpq04.h
+++ b/src/tools/map_extractor/mpq_libmpq04.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/wdt.cpp b/src/tools/map_extractor/wdt.cpp
index 5ff0ddc299..ef10704a3d 100644
--- a/src/tools/map_extractor/wdt.cpp
+++ b/src/tools/map_extractor/wdt.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/map_extractor/wdt.h b/src/tools/map_extractor/wdt.h
index 3272959207..8ce1003646 100644
--- a/src/tools/map_extractor/wdt.h
+++ b/src/tools/map_extractor/wdt.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/mmaps_generator/Config.cpp b/src/tools/mmaps_generator/Config.cpp
new file mode 100644
index 0000000000..dabdb0f0d3
--- /dev/null
+++ b/src/tools/mmaps_generator/Config.cpp
@@ -0,0 +1,276 @@
+/*
+ * This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#include "Config.h"
+#include <filesystem>
+#include <fkYAML/node.hpp>
+#include "PathCommon.h"
+#include "TerrainBuilder.h"
+
+namespace MMAP
+{
+ float ComputeBaseUnitDim(int vertexPerMapEdge)
+ {
+ return GRID_SIZE / static_cast<float>(vertexPerMapEdge);
+ }
+
+ std::pair<uint32, uint32> MakeTileKey(uint32 x, uint32 y)
+ {
+ return {x, y};
+ }
+
+ bool isCurrentDirectory(const std::string& pathStr) {
+ try {
+ const std::filesystem::path givenPath = std::filesystem::canonical(std::filesystem::absolute(pathStr));
+ const std::filesystem::path currentPath = std::filesystem::canonical(std::filesystem::current_path());
+ return givenPath == currentPath;
+ } catch (const std::filesystem::filesystem_error& e) {
+ std::cerr << "Filesystem error: " << e.what() << "\n";
+ return false;
+ }
+ }
+
+ MmapTileRecastConfig ResolvedMeshConfig::toMMAPTileRecastConfig() const {
+ MmapTileRecastConfig config;
+ config.walkableSlopeAngle = walkableSlopeAngle;
+ config.walkableHeight = walkableHeight;
+ config.walkableClimb = walkableClimb;
+ config.walkableRadius = walkableRadius;
+ config.maxSimplificationError = maxSimplificationError;
+ config.cellSizeHorizontal = cellSizeHorizontal;
+ config.cellSizeVertical = cellSizeVertical;
+ config.baseUnitDim = baseUnitDim;
+ config.vertexPerMapEdge = vertexPerMapEdge;
+ config.vertexPerTileEdge = vertexPerTileEdge;
+ config.tilesPerMapEdge = tilesPerMapEdge;
+ return config;
+ }
+
+ std::optional<Config> Config::FromFile(std::string_view configFile) {
+ Config config;
+ if (!config.LoadConfig(configFile))
+ return std::nullopt;
+
+ return config;
+ }
+
+ Config::Config()
+ {
+ }
+
+ ResolvedMeshConfig Config::GetConfigForTile(uint32 mapID, uint32 tileX, uint32 tileY) const
+ {
+ const MapOverride* mapOverride = nullptr;
+ const TileOverride* tileOverride = nullptr;
+
+ // Lookup map and tile overrides
+ if (auto mapIt = _maps.find(mapID); mapIt != _maps.end())
+ {
+ mapOverride = &mapIt->second;
+
+ auto tileIt = mapOverride->tileOverrides.find(MakeTileKey(tileY, tileX));
+ if (tileIt != mapOverride->tileOverrides.end())
+ tileOverride = &tileIt->second;
+ }
+
+ // Helper lambdas to resolve values in order: tile -> map -> global
+ auto resolveFloat = [&](auto TileField, auto MapField, float GlobalValue) -> float {
+ if (tileOverride && TileField(tileOverride)) return *TileField(tileOverride);
+ if (mapOverride && MapField(mapOverride)) return *MapField(mapOverride);
+ return GlobalValue;
+ };
+
+ auto resolveInt = [&](auto TileField, auto MapField, int GlobalValue) -> int {
+ if (tileOverride && TileField(tileOverride)) return *TileField(tileOverride);
+ if (mapOverride && MapField(mapOverride)) return *MapField(mapOverride);
+ return GlobalValue;
+ };
+
+ // Resolve vertex settings
+ int vertexPerMap = resolveInt(
+ [](const TileOverride*) { return std::optional<int>{}; },
+ [](const MapOverride* m) { return m->vertexPerMapEdge; },
+ _global.vertexPerMapEdge
+ );
+
+ int vertexPerTile = resolveInt(
+ [](const TileOverride*) { return std::optional<int>{}; },
+ [](const MapOverride* m) { return m->vertexPerTileEdge; },
+ _global.vertexPerTileEdge
+ );
+
+ ResolvedMeshConfig config;
+ config.walkableSlopeAngle = resolveFloat(
+ [](const TileOverride* t) { return t->walkableSlopeAngle; },
+ [](const MapOverride* m) { return m->walkableSlopeAngle; },
+ _global.walkableSlopeAngle
+ );
+
+ config.walkableRadius = resolveInt(
+ [](const TileOverride* t) { return t->walkableRadius; },
+ [](const MapOverride* m) { return m->walkableRadius; },
+ _global.walkableRadius
+ );
+
+ config.walkableHeight = resolveInt(
+ [](const TileOverride* t) { return t->walkableHeight; },
+ [](const MapOverride* m) { return m->walkableHeight; },
+ _global.walkableHeight
+ );
+
+ config.walkableClimb = resolveInt(
+ [](const TileOverride* t) { return t->walkableClimb; },
+ [](const MapOverride* m) { return m->walkableClimb; },
+ _global.walkableClimb
+ );
+
+ config.vertexPerMapEdge = vertexPerMap;
+ config.vertexPerTileEdge = vertexPerTile;
+ config.baseUnitDim = ComputeBaseUnitDim(vertexPerMap);
+ config.tilesPerMapEdge = vertexPerMap / vertexPerTile;
+ config.maxSimplificationError = _global.maxSimplificationError;
+ config.cellSizeHorizontal = config.baseUnitDim;
+ config.cellSizeVertical = config.baseUnitDim;
+
+ if (mapOverride && mapOverride->cellSizeHorizontal.has_value())
+ config.cellSizeHorizontal = *mapOverride->cellSizeHorizontal;
+
+ if (mapOverride && mapOverride->cellSizeVertical.has_value())
+ config.cellSizeVertical = *mapOverride->cellSizeVertical;
+
+ return config;
+ }
+
+ bool Config::LoadConfig(std::string_view configFile) {
+ FILE* f = std::fopen(configFile.data(), "r");
+ if (!f)
+ return false;
+
+ fkyaml::node root = fkyaml::node::deserialize(f);
+ std::fclose(f);
+
+ if (!root.contains("mmapsConfig"))
+ return false;
+
+ fkyaml::node mmapsNode = root["mmapsConfig"];
+
+ auto tryFloat = [](const fkyaml::node& n, const char* key, float& out)
+ {
+ if (n.contains(key)) out = n[key].get_value<float>();
+ };
+ auto tryInt = [](const fkyaml::node& n, const char* key, int& out)
+ {
+ if (n.contains(key)) out = n[key].get_value<int>();
+ };
+ auto tryBoolean = [](const fkyaml::node& n, const char* key, bool& out)
+ {
+ if (n.contains(key)) out = n[key].get_value<bool>();
+ };
+ auto tryString = [](const fkyaml::node& n, const char* key, std::string& out)
+ {
+ if (n.contains(key)) out = n[key].get_value<std::string>();
+ };
+
+ tryBoolean(mmapsNode, "skipLiquid", _skipLiquid);
+ tryBoolean(mmapsNode, "skipContinents", _skipContinents);
+ tryBoolean(mmapsNode, "skipJunkMaps", _skipJunkMaps);
+ tryBoolean(mmapsNode, "skipBattlegrounds", _skipBattlegrounds);
+ tryBoolean(mmapsNode, "debugOutput", _debugOutput);
+
+ std::string dataDirPath;
+ tryString(mmapsNode, "dataDir", dataDirPath);
+ _dataDir = dataDirPath;
+
+ mmapsNode = mmapsNode["meshSettings"];
+
+ // Global config
+ tryFloat(mmapsNode, "walkableSlopeAngle", _global.walkableSlopeAngle);
+ tryInt(mmapsNode, "walkableHeight", _global.walkableHeight);
+ tryInt(mmapsNode, "walkableClimb", _global.walkableClimb);
+ tryInt(mmapsNode, "walkableRadius", _global.walkableRadius);
+ tryInt(mmapsNode, "vertexPerMapEdge", _global.vertexPerMapEdge);
+ tryInt(mmapsNode, "vertexPerTileEdge", _global.vertexPerTileEdge);
+ tryFloat(mmapsNode, "maxSimplificationError", _global.maxSimplificationError);
+
+ // Map overrides
+ if (mmapsNode.contains("mapsOverrides"))
+ {
+ fkyaml::node maps = mmapsNode["mapsOverrides"];
+ for (auto const& mapEntry : maps.as_map())
+ {
+ uint32 mapId = std::stoi(mapEntry.first.as_str());
+
+ MapOverride override;
+ fkyaml::node mapNode = mapEntry.second;
+
+ if (mapNode.contains("walkableSlopeAngle"))
+ override.walkableSlopeAngle = mapNode["walkableSlopeAngle"].get_value<float>();
+ if (mapNode.contains("walkableRadius"))
+ override.walkableRadius = mapNode["walkableRadius"].get_value<int>();
+ if (mapNode.contains("walkableHeight"))
+ override.walkableHeight = mapNode["walkableHeight"].get_value<int>();
+ if (mapNode.contains("walkableClimb"))
+ override.walkableClimb = mapNode["walkableClimb"].get_value<int>();
+ if (mapNode.contains("vertexPerMapEdge"))
+ override.vertexPerMapEdge = mapNode["vertexPerMapEdge"].get_value<int>();
+ if (mapNode.contains("cellSizeHorizontal"))
+ override.cellSizeHorizontal = mapNode["cellSizeHorizontal"].get_value<float>();
+ if (mapNode.contains("cellSizeVertical"))
+ override.cellSizeVertical = mapNode["cellSizeVertical"].get_value<float>();
+
+ // Tile overrides
+ if (mapNode.contains("tilesOverrides"))
+ {
+ fkyaml::node tiles = mapNode["tilesOverrides"];
+ for (auto const& tileEntry : tiles.as_map())
+ {
+ std::string key = tileEntry.first.as_str();
+ fkyaml::node tileNode = tileEntry.second;
+
+ size_t comma = key.find(',');
+ if (comma == std::string::npos)
+ continue;
+
+ uint32 tileX = static_cast<uint32>(std::stoi(key.substr(0, comma)));
+ uint32 tileY = static_cast<uint32>(std::stoi(key.substr(comma + 1)));
+
+ TileOverride tileOverride;
+ if (tileNode.contains("walkableSlopeAngle"))
+ tileOverride.walkableSlopeAngle = tileNode["walkableSlopeAngle"].get_value<float>();
+ if (tileNode.contains("walkableRadius"))
+ tileOverride.walkableRadius = tileNode["walkableRadius"].get_value<int>();
+ if (tileNode.contains("walkableHeight"))
+ tileOverride.walkableHeight = tileNode["walkableHeight"].get_value<int>();
+ if (tileNode.contains("walkableClimb"))
+ tileOverride.walkableClimb = tileNode["walkableClimb"].get_value<int>();
+
+ override.tileOverrides[{tileX, tileY}] = std::move(tileOverride);
+ }
+ }
+
+ _maps[mapId] = std::move(override);
+ }
+ }
+
+ // Resolve data dir path. Maybe we need to use an executable path instead of the current dir.
+ if (isCurrentDirectory(_dataDir.string()) && !std::filesystem::exists(MapsPath()))
+ if (auto execPath = std::filesystem::path(executableDirectoryPath()); std::filesystem::exists(execPath/ "maps"))
+ _dataDir = execPath;
+
+ return true;
+ }
+}
diff --git a/src/tools/mmaps_generator/Config.h b/src/tools/mmaps_generator/Config.h
new file mode 100644
index 0000000000..c97fa79998
--- /dev/null
+++ b/src/tools/mmaps_generator/Config.h
@@ -0,0 +1,159 @@
+/*
+ * This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
+ * more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+#include <filesystem>
+#include <optional>
+#include <string>
+#include <string_view>
+#include <unordered_map>
+#include <boost/program_options/options_description.hpp>
+#include "Define.h"
+#include "MapDefines.h"
+
+namespace std
+{
+ template <>
+ struct hash<std::pair<uint32_t, uint32_t>>
+ {
+ std::size_t operator()(const std::pair<uint32_t, uint32_t>& p) const noexcept
+ {
+ return std::hash<uint64_t>()((static_cast<uint64_t>(p.first) << 32) | p.second);
+ }
+ };
+}
+
+namespace MMAP
+{
+ struct ResolvedMeshConfig {
+ float walkableSlopeAngle;
+ int walkableRadius;
+ int walkableHeight;
+ int walkableClimb;
+ int vertexPerMapEdge;
+ int vertexPerTileEdge;
+ int tilesPerMapEdge;
+ float baseUnitDim;
+ float cellSizeHorizontal;
+ float cellSizeVertical;
+ float maxSimplificationError;
+
+ MmapTileRecastConfig toMMAPTileRecastConfig() const;
+ };
+
+ class Config {
+ public:
+ static std::optional<Config> FromFile(std::string_view configFile);
+
+ ~Config() = default;
+
+ ResolvedMeshConfig GetConfigForTile(uint32 mapID, uint32 tileX, uint32 tileY) const;
+
+ bool ShouldSkipLiquid() const { return _skipLiquid; }
+ bool ShouldSkipContinents() const { return _skipContinents; }
+ bool ShouldSkipJunkMaps() const { return _skipJunkMaps; }
+ bool ShouldSkipBattlegrounds() const { return _skipBattlegrounds; }
+ bool IsDebugOutputEnabled() const { return _debugOutput; }
+
+ std::string VMapsPath() const { return (_dataDir / "vmaps").string(); }
+ std::string MapsPath() const { return (_dataDir / "maps").string(); }
+ std::string MMapsPath() const { return (_dataDir / "mmaps").string(); }
+ std::string DataDirPath() const { return _dataDir.string(); }
+
+ private:
+ explicit Config();
+
+ bool LoadConfig(std::string_view configFile);
+
+ struct TileOverride {
+ std::optional<float> walkableSlopeAngle;
+ std::optional<int> walkableRadius;
+ std::optional<int> walkableHeight;
+ std::optional<int> walkableClimb;
+ };
+
+ struct MapOverride {
+ std::optional<float> walkableSlopeAngle;
+ std::optional<int> walkableRadius;
+ std::optional<int> walkableHeight;
+ std::optional<int> walkableClimb;
+ std::optional<int> vertexPerMapEdge;
+ std::optional<int> vertexPerTileEdge;
+
+ // The width/depth of each cell in the XZ-plane grid used for voxelization. [Units: world units]
+ // A smaller value increases navmesh resolution but also memory and CPU usage.
+ // Default is equal to calculated baseUnitDim.
+ // Recast reference: https://github.com/recastnavigation/recastnavigation/blob/bd98d84c274ee06842bf51a4088ca82ac71f8c2d/Recast/Include/Recast.h#L231
+ std::optional<float> cellSizeHorizontal;
+
+ // The height of each cell in the Y-axis used for voxelization. [Units: world units]
+ // Controls how vertical features are represented. Lower values improve accuracy for uneven terrain.
+ // Default is equal to calculated baseUnitDim.
+ // Recast reference: https://github.com/recastnavigation/recastnavigation/blob/bd98d84c274ee06842bf51a4088ca82ac71f8c2d/Recast/Include/Recast.h#L234
+ std::optional<float> cellSizeVertical;
+
+ std::unordered_map<std::pair<uint32, uint32>, TileOverride> tileOverrides;
+ };
+
+ struct GlobalConfig {
+ // Maximum slope angle (in degrees) NPCs can walk on.
+ // Surfaces steeper than this will be considered unwalkable.
+ float walkableSlopeAngle = 60.0f;
+
+ // Minimum distance (in cell units) around walkable surfaces.
+ // Helps prevent NPCs from clipping into walls and narrow gaps.
+ int walkableRadius = 2;
+
+ // Minimum ceiling height (in cell units) NPCs need to pass under an obstacle.
+ // Controls how much vertical clearance is required.
+ int walkableHeight = 6;
+
+ // Maximum height difference (in cell units) NPCs can step up or down.
+ // Higher values allow walking over fences, ledges, or steps.
+ int walkableClimb = 6;
+
+ // Number of vertices along one edge of the entire map's navmesh grid.
+ // Higher values increase mesh resolution but also CPU/memory usage.
+ int vertexPerMapEdge = 2000;
+
+ // Number of vertices along one edge of each tile chunk.
+ // Must divide (vertexPerMapEdge - 1) evenly for seamless tiles.
+ // A higher vertex count per tile means fewer total tiles,
+ // reducing runtime work to load, unload, and manage tiles.
+ int vertexPerTileEdge = 80;
+
+ // Tolerance for how much a polygon can deviate from the original geometry when simplified.
+ // Higher values produce simpler (faster) meshes but can reduce accuracy.
+ float maxSimplificationError = 1.8f;
+ };
+
+ GlobalConfig _global;
+ std::unordered_map<uint32, MapOverride> _maps;
+
+ bool _skipLiquid;
+ bool _skipContinents;
+ bool _skipJunkMaps;
+ bool _skipBattlegrounds;
+ bool _debugOutput;
+
+ std::filesystem::path _dataDir;
+ };
+}
+
+#endif //CONFIG_H
diff --git a/src/tools/mmaps_generator/Info/readme.txt b/src/tools/mmaps_generator/Info/readme.txt
index 7e1a1ece6f..c0702d50c4 100644
--- a/src/tools/mmaps_generator/Info/readme.txt
+++ b/src/tools/mmaps_generator/Info/readme.txt
@@ -1,5 +1,8 @@
Generator command line args
+--config [file.*] The path the yaml config file
+ Default: "mmaps-config.yaml"
+
--threads [#] Max number of threads used by the generator
Default: 3
@@ -11,39 +14,6 @@ Generator command line args
--silent [] Make us script friendly. Do not wait for user input
on error or completion.
---bigBaseUnit [true|false] Generate tile/map using bigger basic unit.
- Use this option only if you have unexpected gaps.
-
- false: use normal metrics (default)
-
---maxAngle [#] Max walkable inclination angle
-
- float between 45 and 90 degrees (default 60)
-
---skipLiquid [true|false] extract liquid data for maps
-
- false: include liquid data (default)
-
---skipContinents [true|false] continents are maps 0 (Eastern Kingdoms),
- 1 (Kalimdor), 530 (Outlands), 571 (Northrend)
-
- false: build continents (default)
-
---skipJunkMaps [true|false] junk maps include some unused
- maps, transport maps, and some other
-
- true: skip junk maps (default)
-
---skipBattlegrounds [true|false] does not include PVP arenas
-
- false: skip battlegrounds (default)
-
---debugOutput [true|false] create debugging files for use with RecastDemo
- if you are only creating mmaps for use with Moongose,
- you don't want debugging files
-
- false: don't create debugging files (default)
-
--tile [#,#] Build the specified tile
seperate number with a comma ','
must specify a map number (see below)
@@ -58,9 +28,6 @@ examples:
movement_extractor
builds maps using the default settings (see above for defaults)
-movement_extractor --skipContinents true
-builds the default maps, except continents
-
movement_extractor 0
builds all tiles of map 0
diff --git a/src/tools/mmaps_generator/IntermediateValues.cpp b/src/tools/mmaps_generator/IntermediateValues.cpp
index 12b478979e..584d14c021 100644
--- a/src/tools/mmaps_generator/IntermediateValues.cpp
+++ b/src/tools/mmaps_generator/IntermediateValues.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -16,6 +16,8 @@
*/
#include "IntermediateValues.h"
+#include <string>
+#include "StringFormat.h"
namespace MMAP
{
@@ -28,15 +30,15 @@ namespace MMAP
rcFreePolyMeshDetail(polyMeshDetail);
}
- void IntermediateValues::writeIV(uint32 mapID, uint32 tileX, uint32 tileY)
+ void IntermediateValues::writeIV(const std::string& dataPath, uint32 mapID, uint32 tileX, uint32 tileY)
{
- char fileName[255];
+ char fileName[512];
char tileString[25];
sprintf(tileString, "[%02u,%02u]: ", tileX, tileY);
printf("%sWriting debug output... \r", tileString);
- std::string name("meshes/%03u%02i%02i.");
+ std::string name(dataPath+"/meshes/%03u%02i%02i.");
#define DEBUG_WRITE(fileExtension,data) \
do { \
@@ -198,16 +200,19 @@ namespace MMAP
fwrite(mesh->meshes, sizeof(int), mesh->nmeshes * 4, file);
}
- void IntermediateValues::generateObjFile(uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData)
+ void IntermediateValues::generateObjFile(const std::string& dataPath, uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData)
{
- char objFileName[255];
- sprintf(objFileName, "meshes/map%03u%02u%02u.obj", mapID, tileY, tileX);
+ std::string objFileName = Acore::StringFormat(
+ "{}/meshes/map{:03}{:02}{:02}.obj",
+ dataPath,
+ mapID, tileY, tileX
+ );
- FILE* objFile = fopen(objFileName, "wb");
+ FILE* objFile = fopen(objFileName.c_str(), "wb");
if (!objFile)
{
char message[1024];
- sprintf(message, "Failed to open %s for writing!\n", objFileName);
+ sprintf(message, "Failed to open %s for writing!\n", objFileName.c_str());
perror(message);
return;
}
@@ -237,13 +242,17 @@ namespace MMAP
sprintf(tileString, "[%02u,%02u]: ", tileY, tileX);
printf("%sWriting debug output... \r", tileString);
- sprintf(objFileName, "meshes/%03u.map", mapID);
+ objFileName = Acore::StringFormat(
+ "{}/meshes/{:03}.map",
+ dataPath,
+ mapID
+ );
- objFile = fopen(objFileName, "wb");
+ objFile = fopen(objFileName.c_str(), "wb");
if (!objFile)
{
char message[1024];
- sprintf(message, "Failed to open %s for writing!\n", objFileName);
+ sprintf(message, "Failed to open %s for writing!\n", objFileName.c_str());
perror(message);
return;
}
@@ -252,12 +261,17 @@ namespace MMAP
fwrite(&b, sizeof(char), 1, objFile);
fclose(objFile);
- sprintf(objFileName, "meshes/%03u%02u%02u.mesh", mapID, tileY, tileX);
- objFile = fopen(objFileName, "wb");
+ objFileName = Acore::StringFormat(
+ "{}/meshes/{:03}{:02}{:02}.mesh",
+ dataPath,
+ mapID, tileY, tileX
+ );
+
+ objFile = fopen(objFileName.c_str(), "wb");
if (!objFile)
{
char message[1024];
- sprintf(message, "Failed to open %s for writing!\n", objFileName);
+ sprintf(message, "Failed to open %s for writing!\n", objFileName.c_str());
perror(message);
return;
}
diff --git a/src/tools/mmaps_generator/IntermediateValues.h b/src/tools/mmaps_generator/IntermediateValues.h
index 971cf9000a..2894e5b58e 100644
--- a/src/tools/mmaps_generator/IntermediateValues.h
+++ b/src/tools/mmaps_generator/IntermediateValues.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -35,7 +35,7 @@ namespace MMAP
IntermediateValues() {}
~IntermediateValues();
- void writeIV(uint32 mapID, uint32 tileX, uint32 tileY);
+ void writeIV(const std::string& dataPath, uint32 mapID, uint32 tileX, uint32 tileY);
void debugWrite(FILE* file, const rcHeightfield* mesh);
void debugWrite(FILE* file, const rcCompactHeightfield* chf);
@@ -43,7 +43,7 @@ namespace MMAP
void debugWrite(FILE* file, const rcPolyMesh* mesh);
void debugWrite(FILE* file, const rcPolyMeshDetail* mesh);
- void generateObjFile(uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData);
+ void generateObjFile(const std::string& dataPath, uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData);
};
}
#endif
diff --git a/src/tools/mmaps_generator/MapBuilder.cpp b/src/tools/mmaps_generator/MapBuilder.cpp
index 407cdb103c..45c71367b7 100644
--- a/src/tools/mmaps_generator/MapBuilder.cpp
+++ b/src/tools/mmaps_generator/MapBuilder.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -16,28 +16,28 @@
*/
#include "MapBuilder.h"
+#include <DetourCommon.h>
+#include <DetourNavMesh.h>
+#include <DetourNavMeshBuilder.h>
#include "IntermediateValues.h"
#include "MapDefines.h"
#include "MapTree.h"
+#include "MMapMgr.h"
#include "ModelInstance.h"
#include "PathCommon.h"
#include "StringFormat.h"
#include "VMapMgr2.h"
-#include <DetourCommon.h>
-#include <DetourNavMesh.h>
-#include <DetourNavMeshBuilder.h>
namespace MMAP
{
- TileBuilder::TileBuilder(MapBuilder* mapBuilder, bool skipLiquid, bool bigBaseUnit, bool debugOutput) :
- m_bigBaseUnit(bigBaseUnit),
+ TileBuilder::TileBuilder(MapBuilder* mapBuilder, bool skipLiquid, bool debugOutput) :
m_debugOutput(debugOutput),
m_mapBuilder(mapBuilder),
m_terrainBuilder(nullptr),
m_workerThread(&TileBuilder::WorkerThread, this),
m_rcContext(nullptr)
{
- m_terrainBuilder = new TerrainBuilder(skipLiquid);
+ m_terrainBuilder = new TerrainBuilder(m_mapBuilder->getConfig().DataDirPath(), skipLiquid);
m_rcContext = new rcContext(false);
}
@@ -55,26 +55,22 @@ namespace MMAP
m_workerThread.join();
}
- MapBuilder::MapBuilder(float maxWalkableAngle, bool skipLiquid,
- bool skipContinents, bool skipJunkMaps, bool skipBattlegrounds,
- bool debugOutput, bool bigBaseUnit, int mapid, const char* offMeshFilePath, unsigned int threads) :
-
- m_debugOutput (debugOutput),
+ MapBuilder::MapBuilder(Config* config, int mapid, const char* offMeshFilePath, unsigned int threads) :
+ m_config (config),
+ m_debugOutput (config->IsDebugOutputEnabled()),
m_offMeshFilePath (offMeshFilePath),
m_threads (threads),
- m_skipContinents (skipContinents),
- m_skipJunkMaps (skipJunkMaps),
- m_skipBattlegrounds (skipBattlegrounds),
- m_skipLiquid (skipLiquid),
- m_maxWalkableAngle (maxWalkableAngle),
- m_bigBaseUnit (bigBaseUnit),
+ m_skipContinents (config->ShouldSkipContinents()),
+ m_skipJunkMaps (config->ShouldSkipJunkMaps()),
+ m_skipBattlegrounds (config->ShouldSkipBattlegrounds()),
+ m_skipLiquid (config->ShouldSkipLiquid()),
m_mapid (mapid),
m_totalTiles (0u),
m_totalTilesProcessed(0u),
_cancelationToken (false)
{
- m_terrainBuilder = new TerrainBuilder(skipLiquid);
+ m_terrainBuilder = new TerrainBuilder(config->DataDirPath(), config->ShouldSkipLiquid());
m_rcContext = new rcContext(false);
@@ -105,7 +101,7 @@ namespace MMAP
char filter[12];
printf("Discovering maps... ");
- getDirContents(files, "maps");
+ getDirContents(files, m_config->MapsPath());
for (auto & file : files)
{
mapID = uint32(atoi(file.substr(0, file.size() - 8).c_str()));
@@ -117,7 +113,7 @@ namespace MMAP
}
files.clear();
- getDirContents(files, "vmaps", "*.vmtree");
+ getDirContents(files, m_config->VMapsPath(), "*.vmtree");
for (auto & file : files)
{
mapID = uint32(atoi(file.substr(0, file.size() - 7).c_str()));
@@ -138,7 +134,7 @@ namespace MMAP
sprintf(filter, "%03u*.vmtile", mapID);
files.clear();
- getDirContents(files, "vmaps", filter);
+ getDirContents(files, m_config->VMapsPath(), filter);
for (auto & file : files)
{
fsize = file.size();
@@ -153,7 +149,7 @@ namespace MMAP
sprintf(filter, "%03u*", mapID);
files.clear();
- getDirContents(files, "maps", filter);
+ getDirContents(files, m_config->MapsPath(), filter);
for (auto & file : files)
{
fsize = file.size();
@@ -209,7 +205,7 @@ namespace MMAP
for (unsigned int i = 0; i < m_threads; ++i)
{
- m_tileBuilders.push_back(new TileBuilder(this, m_skipLiquid, m_bigBaseUnit, m_debugOutput));
+ m_tileBuilders.push_back(new TileBuilder(this, m_skipLiquid, m_debugOutput));
}
if (mapID)
@@ -367,7 +363,7 @@ namespace MMAP
getTileBounds(tileX, tileY, data.solidVerts.getCArray(), data.solidVerts.size() / 3, bmin, bmax);
// build navmesh tile
- TileBuilder tileBuilder = TileBuilder(this, m_skipLiquid, m_bigBaseUnit, m_debugOutput);
+ TileBuilder tileBuilder = TileBuilder(this, m_skipLiquid, m_debugOutput);
tileBuilder.buildMoveMapTile(mapId, tileX, tileY, data, bmin, bmax, navMesh);
fclose(file);
}
@@ -385,7 +381,7 @@ namespace MMAP
/// @todo: delete the old tile as the user clearly wants to rebuild it
- TileBuilder tileBuilder = TileBuilder(this, m_skipLiquid, m_bigBaseUnit, m_debugOutput);
+ TileBuilder tileBuilder = TileBuilder(this, m_skipLiquid, m_debugOutput);
tileBuilder.buildTile(mapID, tileX, tileY, navMesh);
dtFreeNavMesh(navMesh);
@@ -567,15 +563,18 @@ namespace MMAP
return;
}
- char fileName[25];
- sprintf(fileName, "mmaps/%03u.mmap", mapID);
+ const std::string fileName = Acore::StringFormat(
+ MAP_FILE_NAME_FORMAT,
+ m_config->DataDirPath(),
+ mapID
+ );
- FILE* file = fopen(fileName, "wb");
+ FILE* file = fopen(fileName.c_str(), "wb");
if (!file)
{
dtFreeNavMesh(navMesh);
char message[1024];
- sprintf(message, "[Map %03i] Failed to open %s for writing!\n", mapID, fileName);
+ sprintf(message, "[Map %03i] Failed to open %s for writing!\n", mapID, fileName.c_str());
perror(message);
return;
}
@@ -608,16 +607,17 @@ namespace MMAP
int lTriCount = meshData.liquidTris.size() / 3;
uint8* lTriFlags = meshData.liquidType.getCArray();
- const TileConfig tileConfig = TileConfig(m_bigBaseUnit);
- int TILES_PER_MAP = tileConfig.TILES_PER_MAP;
- float BASE_UNIT_DIM = tileConfig.BASE_UNIT_DIM;
- rcConfig config = m_mapBuilder->GetMapSpecificConfig(mapID, bmin, bmax, tileConfig);
+ ResolvedMeshConfig cfg = m_mapBuilder->getConfig().GetConfigForTile(mapID, tileX, tileY);
+ int tilesPerMap = cfg.tilesPerMapEdge;
+ float baseUnitDim = cfg.baseUnitDim;
+
+ rcConfig config = m_mapBuilder->getRecastConfig(cfg, bmin, bmax);
// this sets the dimensions of the heightfield - should maybe happen before border padding
rcCalcGridSize(config.bmin, config.bmax, config.cs, &config.width, &config.height);
// allocate subregions : tiles
- Tile* tiles = new Tile[TILES_PER_MAP * TILES_PER_MAP];
+ Tile* tiles = new Tile[tilesPerMap * tilesPerMap];
// Initialize per tile config.
rcConfig tileCfg = config;
@@ -625,15 +625,16 @@ namespace MMAP
tileCfg.height = config.tileSize + config.borderSize * 2;
// merge per tile poly and detail meshes
- rcPolyMesh** pmmerge = new rcPolyMesh*[TILES_PER_MAP * TILES_PER_MAP];
- rcPolyMeshDetail** dmmerge = new rcPolyMeshDetail*[TILES_PER_MAP * TILES_PER_MAP];
+ rcPolyMesh** pmmerge = new rcPolyMesh*[tilesPerMap * tilesPerMap];
+ rcPolyMeshDetail** dmmerge = new rcPolyMeshDetail*[tilesPerMap * tilesPerMap];
int nmerge = 0;
+
// build all tiles
- for (int y = 0; y < TILES_PER_MAP; ++y)
+ for (int y = 0; y < tilesPerMap; ++y)
{
- for (int x = 0; x < TILES_PER_MAP; ++x)
+ for (int x = 0; x < tilesPerMap; ++x)
{
- Tile& tile = tiles[x + y * TILES_PER_MAP];
+ Tile& tile = tiles[x + y * tilesPerMap];
// Calculate the per tile bounding box.
tileCfg.bmin[0] = config.bmin[0] + x * float(config.tileSize * config.cs);
@@ -790,9 +791,9 @@ namespace MMAP
params.offMeshConAreas = meshData.offMeshConnectionsAreas.getCArray();
params.offMeshConFlags = meshData.offMeshConnectionsFlags.getCArray();
- params.walkableHeight = BASE_UNIT_DIM * config.walkableHeight; // agent height
- params.walkableRadius = BASE_UNIT_DIM * config.walkableRadius; // agent radius
- params.walkableClimb = BASE_UNIT_DIM * config.walkableClimb; // keep less that walkableHeight (aka agent height)!
+ params.walkableHeight = baseUnitDim * config.walkableHeight; // agent height
+ params.walkableRadius = baseUnitDim * config.walkableRadius; // agent radius
+ params.walkableClimb = baseUnitDim * config.walkableClimb; // keep less that walkableHeight (aka agent height)!
params.tileX = (((bmin[0] + bmax[0]) / 2) - navMesh->getParams()->orig[0]) / GRID_SIZE;
params.tileY = (((bmin[2] + bmax[2]) / 2) - navMesh->getParams()->orig[2]) / GRID_SIZE;
rcVcopy(params.bmin, bmin);
@@ -861,13 +862,17 @@ namespace MMAP
}
// file output
- char fileName[255];
- sprintf(fileName, "mmaps/%03u%02i%02i.mmtile", mapID, tileY, tileX);
- FILE* file = fopen(fileName, "wb");
+ const std::string fileName = Acore::StringFormat(
+ TILE_FILE_NAME_FORMAT,
+ m_mapBuilder->getConfig().DataDirPath(),
+ mapID, tileY, tileX
+ );
+
+ FILE* file = fopen(fileName.c_str(), "wb");
if (!file)
{
char message[1024];
- sprintf(message, "[Map %03i] Failed to open %s for writing!\n", mapID, fileName);
+ sprintf(message, "[Map %03i] Failed to open %s for writing!\n", mapID, fileName.c_str());
perror(message);
navMesh->removeTile(tileRef, nullptr, nullptr);
break;
@@ -879,6 +884,7 @@ namespace MMAP
MmapTileHeader header;
header.usesLiquids = m_terrainBuilder->usesLiquids();
header.size = uint32(navDataSize);
+ header.recastConfig = cfg.toMMAPTileRecastConfig();
fwrite(&header, sizeof(MmapTileHeader), 1, file);
// write data
@@ -899,8 +905,8 @@ namespace MMAP
v[2] += (unsigned short)config.borderSize;
}
- iv.generateObjFile(mapID, tileX, tileY, meshData);
- iv.writeIV(mapID, tileX, tileY);
+ iv.generateObjFile(m_mapBuilder->getConfig().DataDirPath(), mapID, tileX, tileY, meshData);
+ iv.writeIV(m_mapBuilder->getConfig().DataDirPath(), mapID, tileX, tileY);
}
}
@@ -1028,9 +1034,13 @@ namespace MMAP
/**************************************************************************/
bool TileBuilder::shouldSkipTile(uint32 mapID, uint32 tileX, uint32 tileY) const
{
- char fileName[255];
- sprintf(fileName, "mmaps/%03u%02i%02i.mmtile", mapID, tileY, tileX);
- FILE* file = fopen(fileName, "rb");
+ const std::string fileName = Acore::StringFormat(
+ TILE_FILE_NAME_FORMAT,
+ m_mapBuilder->getConfig().DataDirPath(),
+ mapID, tileY, tileX
+ );
+
+ FILE* file = fopen(fileName.c_str(), "rb");
if (!file)
return false;
@@ -1046,10 +1056,11 @@ namespace MMAP
if (header.mmapVersion != MMAP_VERSION)
return false;
- return true;
+ const auto desiredRecastConfig = m_mapBuilder->getConfig().GetConfigForTile(mapID, tileX, tileY).toMMAPTileRecastConfig();
+ return header.recastConfig == desiredRecastConfig;
}
- rcConfig MapBuilder::GetMapSpecificConfig(uint32 mapID, float bmin[3], float bmax[3], const TileConfig &tileConfig) const
+ rcConfig MapBuilder::getRecastConfig(const ResolvedMeshConfig &cfg, float bmin[3], float bmax[3]) const
{
rcConfig config;
memset(&config, 0, sizeof(rcConfig));
@@ -1058,39 +1069,20 @@ namespace MMAP
rcVcopy(config.bmax, bmax);
config.maxVertsPerPoly = DT_VERTS_PER_POLYGON;
- config.cs = tileConfig.BASE_UNIT_DIM;
- config.ch = tileConfig.BASE_UNIT_DIM;
- config.walkableSlopeAngle = m_maxWalkableAngle;
- config.tileSize = tileConfig.VERTEX_PER_TILE;
- config.walkableRadius = m_bigBaseUnit ? 1 : 2;
- config.borderSize = config.walkableRadius + 3;
- config.maxEdgeLen = tileConfig.VERTEX_PER_TILE + 1; // anything bigger than tileSize
- config.walkableHeight = m_bigBaseUnit ? 3 : 6;
- // a value >= 3|6 allows npcs to walk over some fences
- // a value >= 4|8 allows npcs to walk over all fences
- config.walkableClimb = m_bigBaseUnit ? 3 : 6;
+ config.cs = cfg.cellSizeHorizontal;
+ config.ch = cfg.cellSizeVertical;
+ config.walkableSlopeAngle = cfg.walkableSlopeAngle;
+ config.tileSize = cfg.vertexPerTileEdge;
+ config.walkableRadius = cfg.walkableRadius;
+ config.borderSize = cfg.walkableRadius + 3;
+ config.maxEdgeLen = cfg.vertexPerTileEdge + 1; // anything bigger than tileSize
+ config.walkableHeight = cfg.walkableHeight;
+ config.walkableClimb = cfg.walkableClimb;
config.minRegionArea = rcSqr(60);
config.mergeRegionArea = rcSqr(50);
- config.maxSimplificationError = 1.8f; // eliminates most jagged edges (tiny polygons)
+ config.maxSimplificationError = cfg.maxSimplificationError; // eliminates most jagged edges (tiny polygons)
config.detailSampleDist = config.cs * 16;
config.detailSampleMaxError = config.ch * 1;
-
- switch (mapID)
- {
- // Blade's Edge Arena
- case 562:
- // This allows to walk on the ropes to the pillars
- config.walkableRadius = 0;
- break;
- // Blackfathom Deeps
- case 48:
- // Reduce the chance to have underground levels
- config.ch *= 2;
- break;
- default:
- break;
- }
-
return config;
}
diff --git a/src/tools/mmaps_generator/MapBuilder.h b/src/tools/mmaps_generator/MapBuilder.h
index 19ef1ef59f..313c88c525 100644
--- a/src/tools/mmaps_generator/MapBuilder.h
+++ b/src/tools/mmaps_generator/MapBuilder.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -24,6 +24,7 @@
#include <thread>
#include <vector>
+#include "Config.h"
#include "Optional.h"
#include "TerrainBuilder.h"
@@ -71,27 +72,6 @@ namespace MMAP
rcPolyMeshDetail* dmesh{nullptr};
};
- struct TileConfig
- {
- TileConfig(bool bigBaseUnit)
- {
- // these are WORLD UNIT based metrics
- // this are basic unit dimentions
- // value have to divide GRID_SIZE(533.3333f) ( aka: 0.5333, 0.2666, 0.3333, 0.1333, etc )
- BASE_UNIT_DIM = bigBaseUnit ? 0.5333333f : 0.2666666f;
-
- // All are in UNIT metrics!
- VERTEX_PER_MAP = int(GRID_SIZE / BASE_UNIT_DIM + 0.5f);
- VERTEX_PER_TILE = bigBaseUnit ? 40 : 80; // must divide VERTEX_PER_MAP
- TILES_PER_MAP = VERTEX_PER_MAP / VERTEX_PER_TILE;
- }
-
- float BASE_UNIT_DIM;
- int VERTEX_PER_MAP;
- int VERTEX_PER_TILE;
- int TILES_PER_MAP;
- };
-
struct TileInfo
{
TileInfo() : m_mapId(uint32(-1)), m_tileX(), m_tileY(), m_navMeshParams() {}
@@ -109,7 +89,6 @@ namespace MMAP
public:
TileBuilder(MapBuilder* mapBuilder,
bool skipLiquid,
- bool bigBaseUnit,
bool debugOutput);
TileBuilder(TileBuilder&&) = default;
@@ -131,7 +110,6 @@ namespace MMAP
bool shouldSkipTile(uint32 mapID, uint32 tileX, uint32 tileY) const;
private:
- bool m_bigBaseUnit;
bool m_debugOutput;
MapBuilder* m_mapBuilder;
@@ -145,13 +123,7 @@ namespace MMAP
{
friend class TileBuilder;
public:
- MapBuilder(float maxWalkableAngle,
- bool skipLiquid,
- bool skipContinents,
- bool skipJunkMaps,
- bool skipBattlegrounds,
- bool debugOutput,
- bool bigBaseUnit,
+ MapBuilder(Config* config,
int mapid,
char const* offMeshFilePath,
unsigned int threads);
@@ -166,6 +138,7 @@ namespace MMAP
// builds list of maps, then builds all of mmap tiles (based on the skip settings)
void buildMaps(Optional<uint32> mapID);
+ const Config& getConfig() const { return *m_config; }
private:
// builds all mmap tiles for the specified map id (ignores skip settings)
void buildMap(uint32 mapID);
@@ -184,7 +157,7 @@ namespace MMAP
bool isTransportMap(uint32 mapID) const;
bool isContinentMap(uint32 mapID) const;
- rcConfig GetMapSpecificConfig(uint32 mapID, float bmin[3], float bmax[3], const TileConfig &tileConfig) const;
+ rcConfig getRecastConfig(const ResolvedMeshConfig &cfg, float bmin[3], float bmax[3]) const;
uint32 percentageDone(uint32 totalTiles, uint32 totalTilesDone) const;
uint32 currentPercentageDone() const;
@@ -201,10 +174,10 @@ namespace MMAP
bool m_skipBattlegrounds;
bool m_skipLiquid;
- float m_maxWalkableAngle;
- bool m_bigBaseUnit;
int32 m_mapid;
+ Config* m_config;
+
std::atomic<uint32> m_totalTiles;
std::atomic<uint32> m_totalTilesProcessed;
diff --git a/src/tools/mmaps_generator/PathCommon.h b/src/tools/mmaps_generator/PathCommon.h
index 866dffb688..6dc6dd608e 100644
--- a/src/tools/mmaps_generator/PathCommon.h
+++ b/src/tools/mmaps_generator/PathCommon.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -20,6 +20,7 @@
#include <string>
#include <vector>
+#include <boost/dll/runtime_symbol_info.hpp>
#ifndef _WIN32
#include <cstddef>
@@ -35,6 +36,11 @@
namespace MMAP
{
+ inline std::string executableDirectoryPath()
+ {
+ return boost::dll::program_location().parent_path().string();
+ }
+
inline bool matchWildcardFilter(const char* filter, const char* str)
{
if (!filter || !str)
diff --git a/src/tools/mmaps_generator/PathGenerator.cpp b/src/tools/mmaps_generator/PathGenerator.cpp
index 03fece6462..b7fa572c16 100644
--- a/src/tools/mmaps_generator/PathGenerator.cpp
+++ b/src/tools/mmaps_generator/PathGenerator.cpp
@@ -1,20 +1,21 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
* with this program. If not, see <http://www.gnu.org/licenses/>.
*/
+#include "Config.h"
#include "MapBuilder.h"
#include "PathCommon.h"
#include "Timer.h"
@@ -23,37 +24,34 @@
using namespace MMAP;
-bool checkDirectories(bool debugOutput)
+bool checkDirectories(const std::string &dataDirPath, bool debugOutput)
{
std::vector<std::string> dirFiles;
- if (getDirContents(dirFiles, "maps") == LISTFILE_DIRECTORY_NOT_FOUND || dirFiles.empty())
+ if (getDirContents(dirFiles, (std::filesystem::path(dataDirPath) / "maps").string()) == LISTFILE_DIRECTORY_NOT_FOUND || dirFiles.empty())
{
printf("'maps' directory is empty or does not exist\n");
return false;
}
dirFiles.clear();
- if (getDirContents(dirFiles, "vmaps", "*.vmtree") == LISTFILE_DIRECTORY_NOT_FOUND || dirFiles.empty())
+ if (getDirContents(dirFiles, (std::filesystem::path(dataDirPath) / "vmaps").string(), "*.vmtree") == LISTFILE_DIRECTORY_NOT_FOUND || dirFiles.empty())
{
printf("'vmaps' directory is empty or does not exist\n");
return false;
}
dirFiles.clear();
- if (getDirContents(dirFiles, "mmaps") == LISTFILE_DIRECTORY_NOT_FOUND)
+ if (getDirContents(dirFiles, (std::filesystem::path(dataDirPath) / "mmaps").string()) == LISTFILE_DIRECTORY_NOT_FOUND)
{
- return boost::filesystem::create_directory("mmaps");
+ return boost::filesystem::create_directory((std::filesystem::path(dataDirPath) / "mmaps").string());
}
dirFiles.clear();
- if (debugOutput)
+ if (debugOutput && getDirContents(dirFiles, (std::filesystem::path(dataDirPath) / "meshes").string()) == LISTFILE_DIRECTORY_NOT_FOUND)
{
- if (getDirContents(dirFiles, "meshes") == LISTFILE_DIRECTORY_NOT_FOUND)
- {
- printf("'meshes' directory does not exist (no place to put debugOutput files)\n");
- return false;
- }
+ printf("'meshes' directory does not exist creating...\n");
+ return boost::filesystem::create_directory((std::filesystem::path(dataDirPath) / "meshes").string());
}
return true;
@@ -63,32 +61,24 @@ bool handleArgs(int argc, char** argv,
int& mapnum,
int& tileX,
int& tileY,
- float& maxAngle,
- bool& skipLiquid,
- bool& skipContinents,
- bool& skipJunkMaps,
- bool& skipBattlegrounds,
- bool& debugOutput,
+ std::string& configFilePath,
bool& silent,
- bool& bigBaseUnit,
char*& offMeshInputPath,
char*& file,
unsigned int& threads)
{
+ bool hasCustomConfigPath = false;
char* param = nullptr;
for (int i = 1; i < argc; ++i)
{
- if (strcmp(argv[i], "--maxAngle") == 0)
+ if (strcmp(argv[i], "--config") == 0)
{
param = argv[++i];
if (!param)
return false;
- float maxangle = atof(param);
- if (maxangle <= 90.f && maxangle >= 45.f)
- maxAngle = maxangle;
- else
- printf("invalid option for '--maxAngle', using default\n");
+ hasCustomConfigPath = true;
+ configFilePath = param;
}
else if (strcmp(argv[i], "--threads") == 0)
{
@@ -126,88 +116,10 @@ bool handleArgs(int argc, char** argv,
return false;
}
}
- else if (strcmp(argv[i], "--skipLiquid") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- skipLiquid = true;
- else if (strcmp(param, "false") == 0)
- skipLiquid = false;
- else
- printf("invalid option for '--skipLiquid', using default\n");
- }
- else if (strcmp(argv[i], "--skipContinents") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- skipContinents = true;
- else if (strcmp(param, "false") == 0)
- skipContinents = false;
- else
- printf("invalid option for '--skipContinents', using default\n");
- }
- else if (strcmp(argv[i], "--skipJunkMaps") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- skipJunkMaps = true;
- else if (strcmp(param, "false") == 0)
- skipJunkMaps = false;
- else
- printf("invalid option for '--skipJunkMaps', using default\n");
- }
- else if (strcmp(argv[i], "--skipBattlegrounds") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- skipBattlegrounds = true;
- else if (strcmp(param, "false") == 0)
- skipBattlegrounds = false;
- else
- printf("invalid option for '--skipBattlegrounds', using default\n");
- }
- else if (strcmp(argv[i], "--debugOutput") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- debugOutput = true;
- else if (strcmp(param, "false") == 0)
- debugOutput = false;
- else
- printf("invalid option for '--debugOutput', using default true\n");
- }
else if (strcmp(argv[i], "--silent") == 0)
{
silent = true;
}
- else if (strcmp(argv[i], "--bigBaseUnit") == 0)
- {
- param = argv[++i];
- if (!param)
- return false;
-
- if (strcmp(param, "true") == 0)
- bigBaseUnit = true;
- else if (strcmp(param, "false") == 0)
- bigBaseUnit = false;
- else
- printf("invalid option for '--bigBaseUnit', using default false\n");
- }
else if (strcmp(argv[i], "--offMeshInput") == 0)
{
param = argv[++i];
@@ -229,6 +141,23 @@ bool handleArgs(int argc, char** argv,
}
}
+ if (!hasCustomConfigPath)
+ {
+ FILE* f = fopen(configFilePath.c_str(), "r");
+ if (!f)
+ {
+ auto execRelPath = std::filesystem::path(executableDirectoryPath())/configFilePath;
+ f = fopen(execRelPath.string().c_str(), "r");
+ if (!f)
+ {
+ printf("Failed to load configuration. Ensure that 'mmaps-config.yaml' exists in the current directory or specify its path using the --config option.'\n");
+ return false;
+ }
+ configFilePath = execRelPath.string();
+ }
+ fclose(f);
+ }
+
return true;
}
@@ -244,42 +173,36 @@ int main(int argc, char** argv)
unsigned int threads = std::thread::hardware_concurrency();
int mapnum = -1;
int tileX = -1, tileY = -1;
- float maxAngle = 60.0f;
- bool skipLiquid = false,
- skipContinents = false,
- skipJunkMaps = true,
- skipBattlegrounds = false,
- debugOutput = false,
- silent = false,
- bigBaseUnit = false;
+ bool silent = false;
char* offMeshInputPath = nullptr;
char* file = nullptr;
-
+ std::string configFilePath = "mmaps-config.yaml";
bool validParam = handleArgs(argc, argv, mapnum,
- tileX, tileY, maxAngle,
- skipLiquid, skipContinents, skipJunkMaps, skipBattlegrounds,
- debugOutput, silent, bigBaseUnit, offMeshInputPath, file, threads);
+ tileX, tileY, configFilePath, silent, offMeshInputPath, file, threads);
if (!validParam)
return silent ? -1 : finish("You have specified invalid parameters", -1);
- if (mapnum == -1 && debugOutput)
+ auto config = Config::FromFile(configFilePath);
+ if (!config)
+ return silent ? -1 : finish("Failed to load configuration. Ensure that 'mmaps-config.yaml' exists in the current directory or specify its path using the --config option.", -1);
+
+ if (mapnum == -1 && config->IsDebugOutputEnabled())
{
if (silent)
return -2;
- printf("You have specifed debug output, but didn't specify a map to generate.\n");
+ printf("You have specified debug output, but didn't specify a map to generate.\n");
printf("This will generate debug output for ALL maps.\n");
printf("Are you sure you want to continue? (y/n) ");
if (getchar() != 'y')
return 0;
}
- if (!checkDirectories(debugOutput))
+ if (!checkDirectories(config->DataDirPath(), config->IsDebugOutputEnabled()))
return silent ? -3 : finish("Press ENTER to close...", -3);
- MapBuilder builder(maxAngle, skipLiquid, skipContinents, skipJunkMaps,
- skipBattlegrounds, debugOutput, bigBaseUnit, mapnum, offMeshInputPath, threads);
+ MapBuilder builder(&config.value(), mapnum, offMeshInputPath, threads);
uint32 start = getMSTime();
if (file)
diff --git a/src/tools/mmaps_generator/TerrainBuilder.cpp b/src/tools/mmaps_generator/TerrainBuilder.cpp
index 2faee49d94..6fb539b0fc 100644
--- a/src/tools/mmaps_generator/TerrainBuilder.cpp
+++ b/src/tools/mmaps_generator/TerrainBuilder.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -25,6 +25,8 @@
#include <vector>
#include <map>
+#include "StringFormat.h"
+
// ******************************************
// Map file format defines
// ******************************************
@@ -80,10 +82,17 @@ struct map_liquidHeader
namespace MMAP
{
+ static char const* const MAP_FILE_NAME_FORMAT = "{}/{:03}{:02}{:02}.map";
uint32 const MAP_VERSION_MAGIC = 9;
- TerrainBuilder::TerrainBuilder(bool skipLiquid) : m_skipLiquid (skipLiquid) { }
+ TerrainBuilder::TerrainBuilder(const std::string &dataDirPath, bool skipLiquid) :
+ m_skipLiquid (skipLiquid),
+ m_mapsPath((std::filesystem::path(dataDirPath) / "maps").string()),
+ m_vmapsPath((std::filesystem::path(dataDirPath) / "vmaps").string())
+ {
+ }
+
TerrainBuilder::~TerrainBuilder() = default;
/**************************************************************************/
@@ -134,10 +143,13 @@ namespace MMAP
/**************************************************************************/
bool TerrainBuilder::loadMap(uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData, Spot portion)
{
- char mapFileName[255];
- sprintf(mapFileName, "maps/%03u%02u%02u.map", mapID, tileY, tileX);
+ const std::string mapFileName = Acore::StringFormat(
+ MAP_FILE_NAME_FORMAT,
+ m_mapsPath,
+ mapID, tileY, tileX
+ );
- FILE* mapFile = fopen(mapFileName, "rb");
+ FILE* mapFile = fopen(mapFileName.c_str(), "rb");
if (!mapFile)
return false;
@@ -146,7 +158,7 @@ namespace MMAP
fheader.versionMagic != MAP_VERSION_MAGIC)
{
fclose(mapFile);
- printf("%s is the wrong version, please extract new .map files\n", mapFileName);
+ printf("%s is the wrong version, please extract new .map files\n", mapFileName.c_str());
return false;
}
@@ -665,7 +677,7 @@ namespace MMAP
bool TerrainBuilder::loadVMap(uint32 mapID, uint32 tileX, uint32 tileY, MeshData& meshData)
{
IVMapMgr* vmapMgr = new VMapMgr2();
- int result = vmapMgr->loadMap("vmaps", mapID, tileX, tileY);
+ int result = vmapMgr->loadMap(m_vmapsPath.c_str(), mapID, tileX, tileY);
bool retval = false;
do
diff --git a/src/tools/mmaps_generator/TerrainBuilder.h b/src/tools/mmaps_generator/TerrainBuilder.h
index 23cdbc4710..63c21fe081 100644
--- a/src/tools/mmaps_generator/TerrainBuilder.h
+++ b/src/tools/mmaps_generator/TerrainBuilder.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
@@ -76,7 +76,7 @@ namespace MMAP
class TerrainBuilder
{
public:
- TerrainBuilder(bool skipLiquid);
+ TerrainBuilder(const std::string &mapsPath, bool skipLiquid);
~TerrainBuilder();
TerrainBuilder(const TerrainBuilder& tb) = delete;
@@ -121,6 +121,9 @@ namespace MMAP
/// Get the liquid type for a specific position
uint8 getLiquidType(int square, const uint8 liquid_type[16][16]);
+
+ std::string m_mapsPath;
+ std::string m_vmapsPath;
};
}
diff --git a/src/tools/mmaps_generator/mmaps-config.yaml b/src/tools/mmaps_generator/mmaps-config.yaml
new file mode 100644
index 0000000000..2a0aba1fc9
--- /dev/null
+++ b/src/tools/mmaps_generator/mmaps-config.yaml
@@ -0,0 +1,145 @@
+mmapsConfig:
+ skipLiquid: false
+ skipContinents: false
+ skipJunkMaps: true
+ skipBattlegrounds: false
+
+ # Path to the directory containing navigation data files.
+ # This directory should contain the "maps" and "vmaps" folders,
+ # and is also where the "mmaps" folder will be created or located.
+ dataDir: "./"
+
+ meshSettings:
+ # Here we have global config for recast navigation.
+ # It's possible to override these data on map or tile level (see mapsOverrides).
+
+ # Maximum slope angle (in degrees) NPCs can walk on.
+ # Surfaces steeper than this will be considered unwalkable.
+ walkableSlopeAngle: 60
+
+ # --- Cell Size Calculation ---
+ # Many parameters below are defined in "cell units".
+ # In RecastDemo, you often work with world units instead of cell units.
+ # By default, these cell units are converted to world units using the formula:
+ #
+ # cellSize = MMAP::GRID_SIZE / (verticesPerMapEdge - 1)
+ #
+ # Where:
+ # MMAP::GRID_SIZE = 533.3333f (the size of one map tile in world units)
+ # verticesPerMapEdge = number of vertices along one edge of the full map grid
+ #
+ # Example:
+ # If verticesPerMapEdge = 2000, then:
+ # cellSize ≈ 533.3333 / (2000 - 1) ≈ 0.2667 world units per cell
+ #
+ # To convert a value from cell units to world units (e.g., walkableClimb),
+ # multiply by cellSize. For example, a walkableClimb of 6 corresponds to:
+ # 6 * 0.2667 ≈ 1.6 world units
+
+ # Minimum ceiling height (in cell units) NPCs need to pass under an obstacle.
+ # Controls how much vertical clearance is required.
+ # To convert to world units, multiply by cellSize (see "Cell Size Calculation").
+ walkableHeight: 6
+
+ # Maximum height difference (in cell units) NPCs can step up or down.
+ # Higher values allow walking over fences, ledges, or steps.
+ # To convert to world units, multiply by cellSize (see "Cell Size Calculation").
+ #
+ # Vanilla WotLK uses 6, which allows creatures to "jump" over fences.
+ # Classic WotLK uses 4, which forces creatures to walk around fences.
+ walkableClimb: 6
+
+ # Minimum distance (in cell units) around walkable surfaces.
+ # Helps prevent NPCs from clipping into walls and narrow gaps.
+ # To convert to world units, multiply by cellSize (see "Cell Size Calculation").
+ walkableRadius: 2
+
+ # Number of vertices along one edge of the entire map's navmesh grid.
+ # Higher values increase mesh resolution but also CPU/memory usage.
+ verticesPerMapEdge: 2000
+
+ # Number of vertices along one edge of each tile chunk.
+ # Must divide (vertexPerMapEdge - 1) evenly for seamless tiles.
+ # A higher vertex count per tile means fewer total tiles,
+ # reducing runtime work to load, unload, and manage tiles.
+ verticesPerTileEdge: 80
+
+ # Tolerance for how much a polygon can deviate from the original geometry when simplified.
+ # Higher values produce simpler (faster) meshes but can reduce accuracy.
+ maxSimplificationError: 1.8
+
+ # You can override any global parameter for a specific map by specifying its map ID.
+ # Inside each map override, you can also override parameters per individual tile,
+ # identified by a string "tileX,tileY" (coordinates).
+ #
+ # Overrides cascade: global settings → map overrides → tile overrides.
+ # For example:
+ #
+ # mapsOverrides:
+ # "0": # Map ID 0 overrides
+ # walkableRadius: 5 # Override global climb height for entire map 0
+ #
+ # tilesOverrides:
+ # "50,70": # Tile at coordinates (50,70) on map 0
+ # walkableSlopeAngle: 70 # Override slope angle locally just here
+ # walkableClimb: 4 # Also override climb height for this tile only
+ #
+ # "51,71":
+ # walkableClimb: 3 # Override climb height for tile (51,71)
+ #
+ # "48,32":
+ # walkableClimb: 1 # Even smaller climb for tile (48,32)
+ #
+ # "1": # Map ID 1 overrides example
+ # walkableHeight: 8 # Increase clearance for whole map 1
+ #
+ # tilesOverrides:
+ # "100,100":
+ # maxSimplificationError: 2.5 # Looser mesh simplification for this tile only
+ #
+ # "101,101":
+ # walkableRadius: 1 # Smaller NPC radius here for tight corridors
+ #
+ # This approach allows very fine-grained control of navigation mesh parameters
+ # on a per-map and per-tile basis, optimizing pathfinding quality and performance.
+ #
+ # All parameters defined globally are eligible for override.
+ # Just specify the parameter name and new value in the override section.
+ mapsOverrides:
+ "562": # Blade's Edge Arena
+ walkableRadius: 0 # This allows walking on the ropes to the pillars
+
+ "48": # Blackfathom Deeps
+ cellSizeVertical: 0.5334 # ch*2 = 0.2667 * 2 ≈ 0.5334. Reduce the chance to have underground levels.
+
+ "529": # Arathi Basin
+ tilesOverrides:
+ "30,29": # Lumber Mill
+ # Make sure that Fear will not drop players rom cliff -
+ # https://github.com/azerothcore/azerothcore-wotlk/pull/22462#issuecomment-3067024680
+ walkableSlopeAngle: 45
+
+ # debugOutput generates debug files in the `meshes` directory for use with RecastDemo.
+ # This is useful for inspecting and debugging mmap generation visually.
+ #
+ # My workflow:
+ # 1. Install RecastDemo. I'm building it from the source of this fork: https://github.com/jackpoz/recastnavigation
+ # 2. In-game, move your character to the area you want to debug.
+ # 3. Type `.mmap loc` in chat. This will output:
+ # - The current tile file name (e.g., `04832.mmtile`)
+ # - The Recast config values used to generate that tile
+ # 4. Enable `debugOutput` and regenerate mmaps (preferably just the tile from step 3).
+ # - To regenerate only one tile, delete it from the `mmaps` folder.
+ # 5. After generation, you will find debug files in the `meshes` folder, including an OBJ file (e.g., `map0004832.obj`)
+ # 6. Copy these debug files to the `Meshes` folder used by RecastDemo.
+ # - RecastDemo expects this folder to be in the same directory as its executable.
+ # 7. In RecastDemo:
+ # - Click "Input Mesh" and select the `.obj` file
+ # - Choose "Solo Mesh" in the Sample selector
+ # 8. (Optional) Reuse the Recast config values from step 3:
+ # - `cellSizeHorizontal` → "Cell Size"
+ # - `walkableSlopeAngle` → "Max Slope"
+ # - `walkableClimb` → "Max Climb"
+ # - and so on
+ # 9. Scroll to the bottom of RecastDemo UI and press "Build" to generate the navigation mesh
+ debugOutput: false
diff --git a/src/tools/vmap4_assembler/VMapAssembler.cpp b/src/tools/vmap4_assembler/VMapAssembler.cpp
index fbe5fadb59..a0a6981ea6 100644
--- a/src/tools/vmap4_assembler/VMapAssembler.cpp
+++ b/src/tools/vmap4_assembler/VMapAssembler.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/adtfile.cpp b/src/tools/vmap4_extractor/adtfile.cpp
index 6db292bc86..98513c93dc 100644
--- a/src/tools/vmap4_extractor/adtfile.cpp
+++ b/src/tools/vmap4_extractor/adtfile.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/adtfile.h b/src/tools/vmap4_extractor/adtfile.h
index 201806f3a3..7ddd412d71 100644
--- a/src/tools/vmap4_extractor/adtfile.h
+++ b/src/tools/vmap4_extractor/adtfile.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/dbcfile.cpp b/src/tools/vmap4_extractor/dbcfile.cpp
index 3e6351b141..561d86265f 100644
--- a/src/tools/vmap4_extractor/dbcfile.cpp
+++ b/src/tools/vmap4_extractor/dbcfile.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/dbcfile.h b/src/tools/vmap4_extractor/dbcfile.h
index ad7a4bb703..49535cff9b 100644
--- a/src/tools/vmap4_extractor/dbcfile.h
+++ b/src/tools/vmap4_extractor/dbcfile.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/gameobject_extract.cpp b/src/tools/vmap4_extractor/gameobject_extract.cpp
index fd7160e783..b1470497e9 100644
--- a/src/tools/vmap4_extractor/gameobject_extract.cpp
+++ b/src/tools/vmap4_extractor/gameobject_extract.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/loadlib/loadlib.h b/src/tools/vmap4_extractor/loadlib/loadlib.h
index 83222d83af..037f15e633 100644
--- a/src/tools/vmap4_extractor/loadlib/loadlib.h
+++ b/src/tools/vmap4_extractor/loadlib/loadlib.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/model.cpp b/src/tools/vmap4_extractor/model.cpp
index d2912f0f37..ed006fbad2 100644
--- a/src/tools/vmap4_extractor/model.cpp
+++ b/src/tools/vmap4_extractor/model.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/model.h b/src/tools/vmap4_extractor/model.h
index 021d1dedba..6eb1c5ea94 100644
--- a/src/tools/vmap4_extractor/model.h
+++ b/src/tools/vmap4_extractor/model.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/modelheaders.h b/src/tools/vmap4_extractor/modelheaders.h
index b6230fee3f..8a46311628 100644
--- a/src/tools/vmap4_extractor/modelheaders.h
+++ b/src/tools/vmap4_extractor/modelheaders.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/mpq_libmpq.cpp b/src/tools/vmap4_extractor/mpq_libmpq.cpp
index 2e5e4eb2b7..d699c78294 100644
--- a/src/tools/vmap4_extractor/mpq_libmpq.cpp
+++ b/src/tools/vmap4_extractor/mpq_libmpq.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/mpq_libmpq04.h b/src/tools/vmap4_extractor/mpq_libmpq04.h
index 5b6c81ce3b..605ca54a8a 100644
--- a/src/tools/vmap4_extractor/mpq_libmpq04.h
+++ b/src/tools/vmap4_extractor/mpq_libmpq04.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/vec3d.h b/src/tools/vmap4_extractor/vec3d.h
index 25a042fc2e..fb07d0d473 100644
--- a/src/tools/vmap4_extractor/vec3d.h
+++ b/src/tools/vmap4_extractor/vec3d.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/vmapexport.cpp b/src/tools/vmap4_extractor/vmapexport.cpp
index 3acd698727..3b6e5a5be4 100644
--- a/src/tools/vmap4_extractor/vmapexport.cpp
+++ b/src/tools/vmap4_extractor/vmapexport.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/vmapexport.h b/src/tools/vmap4_extractor/vmapexport.h
index 4f51ae165f..bf0872bfa9 100644
--- a/src/tools/vmap4_extractor/vmapexport.h
+++ b/src/tools/vmap4_extractor/vmapexport.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/wdtfile.cpp b/src/tools/vmap4_extractor/wdtfile.cpp
index 1a52342408..59955d1571 100644
--- a/src/tools/vmap4_extractor/wdtfile.cpp
+++ b/src/tools/vmap4_extractor/wdtfile.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/wdtfile.h b/src/tools/vmap4_extractor/wdtfile.h
index e2a6a61dfe..f534a60c88 100644
--- a/src/tools/vmap4_extractor/wdtfile.h
+++ b/src/tools/vmap4_extractor/wdtfile.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/wmo.cpp b/src/tools/vmap4_extractor/wmo.cpp
index 70164930b7..0a25367949 100644
--- a/src/tools/vmap4_extractor/wmo.cpp
+++ b/src/tools/vmap4_extractor/wmo.cpp
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along
diff --git a/src/tools/vmap4_extractor/wmo.h b/src/tools/vmap4_extractor/wmo.h
index 8967a87a4a..dc44331e32 100644
--- a/src/tools/vmap4_extractor/wmo.h
+++ b/src/tools/vmap4_extractor/wmo.h
@@ -1,14 +1,14 @@
/*
* This file is part of the AzerothCore Project. See AUTHORS file for Copyright information
*
- * This program is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Affero General Public License as published by the
- * Free Software Foundation; either version 3 of the License, or (at your
- * option) any later version.
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
- * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for
+ * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along