1
0
Fork 0
mirror of https://github.com/luanti-org/luanti.git synced 2025-09-30 19:22:14 +00:00

Make mapgen edges a vector too

This commit is contained in:
sfan5 2025-08-22 19:41:15 +02:00
parent 630ca5daa0
commit 2847f3e805
4 changed files with 47 additions and 25 deletions

View file

@ -1127,25 +1127,13 @@ void MapgenParams::writeParams(Settings *settings) const
s32 MapgenParams::getSpawnRangeMax() s32 MapgenParams::getSpawnRangeMax()
{ {
auto [emin, emax] = get_mapgen_edges(mapgen_limit, chunksize); auto [emin, emax] = get_mapgen_edges(mapgen_limit, chunksize);
return std::min(-emin, emax); s32 min_xz = std::max(emin.X, emin.Z), max_xz = std::min(emax.X, emax.Z);
return std::min(-min_xz, max_xz);
} }
std::pair<s16, s16> get_mapgen_edges(s16 mapgen_limit, v3s16 chunksize) std::pair<v3s16, v3s16> get_mapgen_edges(s16 mapgen_limit, v3s16 chunksize)
{ {
// FIXME: this is no longer exact
const s16 cs = std::max(std::max(chunksize.X, chunksize.Y), chunksize.Z);
// Central chunk offset, in blocks
s16 ccoff_b = -cs / 2;
// Chunksize, in nodes
s32 csize_n = cs * MAP_BLOCKSIZE;
// Minp/maxp of central chunk, in nodes
s16 ccmin = ccoff_b * MAP_BLOCKSIZE;
s16 ccmax = ccmin + csize_n - 1;
// Fullminp/fullmaxp of central chunk, in nodes
s16 ccfmin = ccmin - MAP_BLOCKSIZE;
s16 ccfmax = ccmax + MAP_BLOCKSIZE;
// Effective mapgen limit, in blocks // Effective mapgen limit, in blocks
// Uses same calculation as ServerMap::blockpos_over_mapgen_limit(v3s16 p) // Uses same calculation as ServerMap::blockpos_over_mapgen_limit(v3s16 p)
s16 mapgen_limit_b = rangelim(mapgen_limit, s16 mapgen_limit_b = rangelim(mapgen_limit,
@ -1153,10 +1141,29 @@ std::pair<s16, s16> get_mapgen_edges(s16 mapgen_limit, v3s16 chunksize)
// Effective mapgen limits, in nodes // Effective mapgen limits, in nodes
s16 mapgen_limit_min = -mapgen_limit_b * MAP_BLOCKSIZE; s16 mapgen_limit_min = -mapgen_limit_b * MAP_BLOCKSIZE;
s16 mapgen_limit_max = (mapgen_limit_b + 1) * MAP_BLOCKSIZE - 1; s16 mapgen_limit_max = (mapgen_limit_b + 1) * MAP_BLOCKSIZE - 1;
// Number of complete chunks from central chunk fullminp/fullmaxp
// to effective mapgen limits. const auto &calculate = [&] (s16 cs) -> std::pair<s16, s16> {
s16 numcmin = std::max((ccfmin - mapgen_limit_min) / csize_n, 0); // Central chunk offset, in blocks
s16 numcmax = std::max((mapgen_limit_max - ccfmax) / csize_n, 0); s16 ccoff_b = -cs / 2;
// Chunksize, in nodes
s32 csize_n = cs * MAP_BLOCKSIZE;
// Minp/maxp of central chunk, in nodes
s16 ccmin = ccoff_b * MAP_BLOCKSIZE;
s16 ccmax = ccmin + csize_n - 1;
// Fullminp/fullmaxp of central chunk, in nodes
s16 ccfmin = ccmin - MAP_BLOCKSIZE;
s16 ccfmax = ccmax + MAP_BLOCKSIZE;
// Number of complete chunks from central chunk fullminp/fullmaxp
// to effective mapgen limits.
s16 numcmin = std::max((ccfmin - mapgen_limit_min) / csize_n, 0);
s16 numcmax = std::max((mapgen_limit_max - ccfmax) / csize_n, 0);
return {ccmin - numcmin * csize_n, ccmax + numcmax * csize_n};
};
// Mapgen edges, in nodes // Mapgen edges, in nodes
return {ccmin - numcmin * csize_n, ccmax + numcmax * csize_n}; v3s16 emin, emax;
std::tie(emin.X, emax.X) = calculate(chunksize.X);
std::tie(emin.Y, emax.Y) = calculate(chunksize.Y);
std::tie(emin.Z, emax.Z) = calculate(chunksize.Z);
return {emin, emax};
} }

View file

@ -325,4 +325,4 @@ protected:
// Calculate exact edges of the outermost mapchunks that are within the set // Calculate exact edges of the outermost mapchunks that are within the set
// mapgen_limit. Returns the minimum and maximum edges in nodes in that order. // mapgen_limit. Returns the minimum and maximum edges in nodes in that order.
std::pair<s16, s16> get_mapgen_edges(s16 mapgen_limit, v3s16 chunksize); std::pair<v3s16, v3s16> get_mapgen_edges(s16 mapgen_limit, v3s16 chunksize);

View file

@ -867,9 +867,9 @@ int ModApiMapgen::l_get_mapgen_edges(lua_State *L)
chunksize = params->chunksize; chunksize = params->chunksize;
} }
std::pair<s16, s16> edges = get_mapgen_edges(mapgen_limit, chunksize); auto edges = get_mapgen_edges(mapgen_limit, chunksize);
push_v3s16(L, v3s16(1, 1, 1) * edges.first); push_v3s16(L, edges.first);
push_v3s16(L, v3s16(1, 1, 1) * edges.second); push_v3s16(L, edges.second);
return 2; return 2;
} }

View file

@ -7,6 +7,7 @@
#include "emerge.h" #include "emerge.h"
#include "mapgen/mapgen.h" #include "mapgen/mapgen.h"
#include "mapgen/mg_biome.h" #include "mapgen/mg_biome.h"
#include "irrlicht_changes/printing.h"
#include "mock_server.h" #include "mock_server.h"
class TestMapgen : public TestBase class TestMapgen : public TestBase
@ -18,6 +19,7 @@ public:
void runTests(IGameDef *gamedef); void runTests(IGameDef *gamedef);
void testBiomeGen(IGameDef *gamedef); void testBiomeGen(IGameDef *gamedef);
void testMapgenEdges();
}; };
static TestMapgen g_test_instance; static TestMapgen g_test_instance;
@ -37,6 +39,7 @@ namespace {
void TestMapgen::runTests(IGameDef *gamedef) void TestMapgen::runTests(IGameDef *gamedef)
{ {
TEST(testBiomeGen, gamedef); TEST(testBiomeGen, gamedef);
TEST(testMapgenEdges);
} }
void TestMapgen::testBiomeGen(IGameDef *gamedef) void TestMapgen::testBiomeGen(IGameDef *gamedef)
@ -98,7 +101,7 @@ void TestMapgen::testBiomeGen(IGameDef *gamedef)
{ 0, "deciduous_forest_shore", S16_MIN }, { 0, "deciduous_forest_shore", S16_MIN },
{ -100, "deciduous_forest_shore", S16_MIN }, { -100, "deciduous_forest_shore", S16_MIN },
}; };
for (const auto expected : expected_biomes) { for (const auto &expected : expected_biomes) {
Biome *biome = biomegen->getBiomeAtIndex( Biome *biome = biomegen->getBiomeAtIndex(
(1 * CSIZE.X) + 1, // index in CSIZE 2D noise map (1 * CSIZE.X) + 1, // index in CSIZE 2D noise map
v3s16(2000, expected.check_y, -1000) // absolute coordinates v3s16(2000, expected.check_y, -1000) // absolute coordinates
@ -123,3 +126,15 @@ void TestMapgen::testBiomeGen(IGameDef *gamedef)
} }
} }
void TestMapgen::testMapgenEdges()
{
v3s16 emin, emax;
std::tie(emin, emax) = get_mapgen_edges(31007, v3s16(5));
UASSERTEQ(auto, emin, v3s16(-30912));
UASSERTEQ(auto, emax, v3s16(30927));
std::tie(emin, emax) = get_mapgen_edges(502 * MAP_BLOCKSIZE, v3s16(1, 2, 1));
UASSERTEQ(auto, emin, v3s16(-8016));
UASSERTEQ(auto, emax, v3s16(8031, 8015, 8031));
}