fix line placement
This commit is contained in:
parent
116cbd61db
commit
5a89d97b75
@ -17,7 +17,7 @@ function place_structures(x, z, w, d, seed, hmap, chunk_height)
|
|||||||
local sz = z + math.random() * 20 - 10
|
local sz = z + math.random() * 20 - 10
|
||||||
local ez = z + math.random() * 20 - 10
|
local ez = z + math.random() * 20 - 10
|
||||||
table.insert(placements,
|
table.insert(placements,
|
||||||
{":line", 0, {sx - 10, sy, sz - 10}, {ex + 10, ey, ez + 10}, 2})
|
{":line", 0, {sx - 10, sy, sz - 10}, {ex + 10, ey, ez + 10}, 3})
|
||||||
end
|
end
|
||||||
return placements
|
return placements
|
||||||
end
|
end
|
||||||
|
|||||||
@ -178,20 +178,10 @@ void WorldGenerator::placeLine(const LinePlacement& line) {
|
|||||||
for (int cz = cza; cz <= czb; cz++) {
|
for (int cz = cza; cz <= czb; cz++) {
|
||||||
for (int cx = cxa; cx <= cxb; cx++) {
|
for (int cx = cxa; cx <= cxb; cx++) {
|
||||||
auto& otherPrototype = requirePrototype(cx, cz);
|
auto& otherPrototype = requirePrototype(cx, cz);
|
||||||
auto chunkAABB = gen_chunk_aabb(cx, cz);
|
|
||||||
chunkAABB.a -= line.radius;
|
|
||||||
chunkAABB.b += line.radius;
|
|
||||||
auto found = util::closest_point_on_segment(line.a, line.b, {
|
|
||||||
cx * CHUNK_W + CHUNK_W / 2,
|
|
||||||
0,
|
|
||||||
cz * CHUNK_D + CHUNK_D / 2
|
|
||||||
});
|
|
||||||
if (chunkAABB.contains(found)) {
|
|
||||||
otherPrototype.lines.push_back(line);
|
otherPrototype.lines.push_back(line);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
void WorldGenerator::generateStructures(
|
void WorldGenerator::generateStructures(
|
||||||
ChunkPrototype& prototype, int chunkX, int chunkZ
|
ChunkPrototype& prototype, int chunkX, int chunkZ
|
||||||
@ -315,6 +305,14 @@ void WorldGenerator::update(int centerX, int centerY, int loadDistance) {
|
|||||||
surroundMap.setCenter(centerX, centerY);
|
surroundMap.setCenter(centerX, centerY);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// @return integer square of distance between two points
|
||||||
|
/// @note glm::distance2 does not support integer vectors
|
||||||
|
static inline int distance2(const glm::ivec3& a, const glm::ivec3& b) {
|
||||||
|
return (b.x - a.x) * (b.x - a.x) +
|
||||||
|
(b.y - a.y) * (b.y - a.y) +
|
||||||
|
(b.z - a.z) * (b.z - a.z);
|
||||||
|
}
|
||||||
|
|
||||||
void WorldGenerator::generate(voxel* voxels, int chunkX, int chunkZ) {
|
void WorldGenerator::generate(voxel* voxels, int chunkX, int chunkZ) {
|
||||||
surroundMap.completeAt(chunkX, chunkZ);
|
surroundMap.completeAt(chunkX, chunkZ);
|
||||||
|
|
||||||
@ -391,15 +389,32 @@ void WorldGenerator::generate(voxel* voxels, int chunkX, int chunkZ) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (const auto& line : prototype.lines) {
|
for (const auto& line : prototype.lines) {
|
||||||
int minY = std::max(0, std::min(line.a.y-line.radius, line.b.y-line.radius));
|
int cgx = chunkX * CHUNK_W;
|
||||||
int maxY = std::min(CHUNK_H, std::max(line.a.y+line.radius, line.b.y+line.radius));
|
int cgz = chunkZ * CHUNK_D;
|
||||||
for (int y = minY; y < maxY; y++) {
|
|
||||||
for (int z = 0; z < CHUNK_D; z++) {
|
|
||||||
for (int x = 0; x < CHUNK_W; x++) {
|
|
||||||
int gx = x + chunkX * CHUNK_W;
|
|
||||||
int gz = z + chunkZ * CHUNK_D;
|
|
||||||
|
|
||||||
if (glm::distance2(util::closest_point_on_segment(line.a, line.b, {gx, y, gz}), {gx, y, gz}) <= line.radius*line.radius) {
|
int radius = line.radius;
|
||||||
|
|
||||||
|
int minX = std::max(0, std::min(line.a.x-radius-cgx, line.b.x-radius-cgx));
|
||||||
|
int maxX = std::min(CHUNK_W, std::max(line.a.x+radius-cgx, line.b.x+radius-cgx));
|
||||||
|
|
||||||
|
int minZ = std::max(0, std::min(line.a.z-radius-cgz, line.b.z-radius-cgz));
|
||||||
|
int maxZ = std::min(CHUNK_D, std::max(line.a.z+radius-cgz, line.b.z+radius-cgz));
|
||||||
|
|
||||||
|
int minY = std::max(0, std::min(line.a.y-radius, line.b.y-radius));
|
||||||
|
int maxY = std::min(CHUNK_H, std::max(line.a.y+radius, line.b.y+radius));
|
||||||
|
|
||||||
|
auto a = line.a;
|
||||||
|
auto b = line.b;
|
||||||
|
|
||||||
|
for (int y = minY; y < maxY; y++) {
|
||||||
|
for (int z = minZ; z < maxZ; z++) {
|
||||||
|
for (int x = minX; x < maxX; x++) {
|
||||||
|
int gx = x + cgx;
|
||||||
|
int gz = z + cgz;
|
||||||
|
glm::ivec3 point {gx, y, gz};
|
||||||
|
glm::ivec3 closest = util::closest_point_on_segment(
|
||||||
|
a, b, point);
|
||||||
|
if (distance2(closest, point) <= radius*radius) {
|
||||||
voxels[vox_index(x, y, z)] = {line.block, {}};
|
voxels[vox_index(x, y, z)] = {line.block, {}};
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user