flatten array along y coordinate

intervalmaps-array-y
EmaMaker 2022-12-17 18:10:59 +01:00
parent 69c44e3609
commit 9ed97b6161
7 changed files with 60 additions and 52 deletions

View File

@ -9,7 +9,7 @@ namespace utils
// https://stackoverflow.com/questions/20266201/3d-array-1d-flat-indexing // https://stackoverflow.com/questions/20266201/3d-array-1d-flat-indexing
// flatten 3d coords to 1d array cords // flatten 3d coords to 1d array cords
int coord3DTo1D(int x, int y, int z, int maxX, int maxY, int maxZ); int coord3DTo1D(int x, int y, int z, int maxX, int maxY, int maxZ);
std::array<int, 3> coord1DTo3D(int idx, int maxX, int maxY, int mazZ); void coord1DTo3D(int idx, int maxX, int maxY, int mazZ, int* x, int* y, int* z);
} }
#endif #endif

View File

@ -27,12 +27,14 @@ namespace Chunk
Block Chunk::getBlock(int x, int y, int z) Block Chunk::getBlock(int x, int y, int z)
{ {
return blocks.at(HILBERT_XYZ_ENCODE[x][y][z]); return blocks.at(coord3DTo1D(x, y, z));
// return blocks.at(HILBERT_XYZ_ENCODE[x][y][z]);
} }
void Chunk::setBlock(Block b, int x, int y, int z) void Chunk::setBlock(Block b, int x, int y, int z)
{ {
int coord = HILBERT_XYZ_ENCODE[x][y][z]; // return blocks.insert(HILBERT_XYZ_ENCODE[x][y][z], HILBERT_XYZ_ENCODE[x][y][z]+1, b);
int coord = coord3DTo1D(x, y, z);
blocks.insert(coord <= 0 ? 0 : coord, coord+1 >= CHUNK_VOLUME ? CHUNK_VOLUME : coord+1, b); blocks.insert(coord <= 0 ? 0 : coord, coord+1 >= CHUNK_VOLUME ? CHUNK_VOLUME : coord+1, b);
} }

View File

@ -4,7 +4,6 @@
#include "block.hpp" #include "block.hpp"
#include "chunkgenerator.hpp" #include "chunkgenerator.hpp"
#include "globals.hpp"
#include "OpenSimplexNoise.h" #include "OpenSimplexNoise.h"
#include "utils.hpp" #include "utils.hpp"
@ -44,14 +43,17 @@ void generateNoise(Chunk::Chunk *chunk)
Block block_prev{Block::AIR}; Block block_prev{Block::AIR};
int block_prev_start{0}; int block_prev_start{0};
// A space filling curve is continuous, so there is no particular order // The order of iteration MUST RESPECT the order in which the array is transformed from 3d to 1d
for (int s = 0; s < CHUNK_VOLUME; s++) for (int k = 0; k < CHUNK_SIZE; k++)
{ {
for (int i = 0; i < CHUNK_SIZE; i++)
int x = HILBERT_XYZ_DECODE[s][0] + CHUNK_SIZE * chunk->getPosition().x; {
int y = HILBERT_XYZ_DECODE[s][1] + CHUNK_SIZE * chunk->getPosition().y; for (int j = 0; j < CHUNK_SIZE; j++)
int z = HILBERT_XYZ_DECODE[s][2] + CHUNK_SIZE * chunk->getPosition().z; {
int d2 = HILBERT_XYZ_DECODE[s][0] * CHUNK_SIZE + HILBERT_XYZ_DECODE[s][2]; int x = i + CHUNK_SIZE * chunk->getPosition().x;
int y = j + CHUNK_SIZE * chunk->getPosition().y;
int z = k + CHUNK_SIZE * chunk->getPosition().z;
int d2 = k * CHUNK_SIZE + i;
if (grassNoiseLUT[d2] == -1) if (grassNoiseLUT[d2] == -1)
grassNoiseLUT[d2] = GRASS_OFFSET + (int)((0.5 + noiseGen1.eval(x * NOISE_GRASS_X_MULT, z * NOISE_GRASS_Z_MULT) * NOISE_GRASS_MULT)); grassNoiseLUT[d2] = GRASS_OFFSET + (int)((0.5 + noiseGen1.eval(x * NOISE_GRASS_X_MULT, z * NOISE_GRASS_Z_MULT) * NOISE_GRASS_MULT));
@ -71,14 +73,18 @@ void generateNoise(Chunk::Chunk *chunk)
else else
block = Block::AIR; block = Block::AIR;
int index = Chunk::coord3DTo1D(i, j, k);
int min = index > block_prev_start ? block_prev_start : index, max = index > block_prev_start ? index : block_prev_start;
if (block != block_prev) if (block != block_prev)
{ {
chunk->setBlocks(block_prev_start, s, block_prev); chunk->setBlocks(block_prev_start, index, block_prev);
block_prev_start = s; block_prev_start = index;
} }
block_prev = block; block_prev = block;
} }
}
}
chunk->setBlocks(block_prev_start, CHUNK_VOLUME, block_prev); chunk->setBlocks(block_prev_start, CHUNK_VOLUME, block_prev);
} }

View File

@ -99,10 +99,10 @@ void ChunkMesh::mesh()
{ {
for (x[u] = 0; x[u] < CHUNK_SIZE; x[u]++) for (x[u] = 0; x[u] < CHUNK_SIZE; x[u]++)
{ {
Block b1 = (x[dim] >= 0) ? blocks[HILBERT_XYZ_ENCODE[x[0]][x[1]][x[2]]] : Block::NULLBLK; Block b1 = (x[dim] >= 0) ? blocks[Chunk::coord3DTo1D(x[0], x[1], x[2])] : Block::NULLBLK; /*blocks[SpaceFilling::HILBERT_XYZ_ENCODE[x[0]][x[1]][x[2]]]*/
Block b2 = (x[dim] < CHUNK_SIZE - 1) Block b2 = (x[dim] < CHUNK_SIZE - 1)
? blocks[HILBERT_XYZ_ENCODE[x[0] + q[0]][x[1] + q[1]][x[2] + q[2]]] ? blocks[Chunk::coord3DTo1D(x[0] + q[0], x[1] + q[1], x[2] + q[2])]
: Block::NULLBLK; : Block::NULLBLK; /*blocks[SpaceFilling::HILBERT_XYZ_ENCODE[x[0] + q[0]][x[1] + q[1]][x[2] + q[2]]]*/
// This is the original line taken from rob's code, readapted (replace voxelFace // This is the original line taken from rob's code, readapted (replace voxelFace
// with b1 and b2). // with b1 and b2).

View File

@ -10,6 +10,7 @@
#include "chunkmanager.hpp" #include "chunkmanager.hpp"
#include "main.hpp" #include "main.hpp"
#include "spacefilling.hpp" #include "spacefilling.hpp"
#include "utils.hpp"
float deltaTime = 0.0f; // Time between current frame and last frame float deltaTime = 0.0f; // Time between current frame and last frame
float lastFrame = 0.0f; // Time of last frame float lastFrame = 0.0f; // Time of last frame
@ -52,7 +53,7 @@ int main()
glEnable(GL_DEPTH_TEST); glEnable(GL_DEPTH_TEST);
glEnable(GL_CULL_FACE); // GL_BACK GL_CCW by default glEnable(GL_CULL_FACE); // GL_BACK GL_CCW by default
SpaceFilling::initLUT(); // SpaceFilling::initLUT();
chunkmanager::init(); chunkmanager::init();
while (!glfwWindowShouldClose(window)) while (!glfwWindowShouldClose(window))
@ -64,7 +65,8 @@ int main()
// FPS Counter // FPS Counter
frames++; frames++;
if(currentFrame - lastFPSFrame >= 1.0f){ if (currentFrame - lastFPSFrame >= 1.0f)
{
std::cout << "FPS: " << frames << " Frametime: " << deltaTime << std::endl; std::cout << "FPS: " << frames << " Frametime: " << deltaTime << std::endl;
frames = 0; frames = 0;
lastFPSFrame = currentFrame; lastFPSFrame = currentFrame;

View File

@ -188,16 +188,15 @@ namespace SpaceFilling
void initLUT() void initLUT()
{ {
uint32_t morton, hilbert,j; uint32_t morton, hilbert;
for (uint32_t i = 0; i < CHUNK_SIZE; i++) for (uint32_t i = 0; i < CHUNK_SIZE; i++)
{ {
for (uint32_t y = 0; y < CHUNK_SIZE; y++) for (uint32_t j = 0; j < CHUNK_SIZE; j++)
{ {
for (uint32_t k = 0; k < CHUNK_SIZE; k++) for (uint32_t k = 0; k < CHUNK_SIZE; k++)
{ {
j = CHUNK_SIZE - 1 - y;
morton = Morton_3D_Encode_10bit(i, j, k); morton = Morton_3D_Encode_10bit(i, j, k);
hilbert = MortonToHilbert3D(morton, 2); // 4 hilbert bits hilbert = MortonToHilbert3D(morton, 4); // 4 hilbert bits
MORTON_XYZ_ENCODE[i][j][k] = morton; MORTON_XYZ_ENCODE[i][j][k] = morton;
MORTON_XYZ_DECODE[morton][0] = i; MORTON_XYZ_DECODE[morton][0] = i;

View File

@ -7,13 +7,12 @@ bool utils::withinDistance(int startx, int starty, int startz, int x, int y, int
// https://stackoverflow.com/questions/20266201/3d-array-1d-flat-indexing // https://stackoverflow.com/questions/20266201/3d-array-1d-flat-indexing
//flatten 3d coords to 1d array cords //flatten 3d coords to 1d array cords
int utils::coord3DTo1D (int x, int y, int z, int maxX, int maxY, int maxZ){ int utils::coord3DTo1D (int x, int y, int z, int maxX, int maxY, int maxZ){
return x + maxX * (y + z * maxY); return y + maxY * (x + z * maxX);
} }
std::array<int, 3> utils::coord1DTo3D(int idx, int maxX, int maxY, int mazZ){ void utils::coord1DTo3D(int idx, int maxX, int maxY, int mazZ, int* x, int* y, int* z){
int z = idx / (maxX * maxY); *z = idx / (maxX * maxY);
idx -= (z * maxX* maxY); idx -= (*z * maxX* maxY);
int y = idx / maxX; *x = idx / maxY;
int x = idx % maxX; *y = idx % maxY;
return std::array<int, 3> {x, y, z};
} }