mirror of
https://github.com/ClassiCube/ClassiCube.git
synced 2025-09-13 01:26:50 -04:00
Move chunks dimensions code from MapRenderer to World
This commit is contained in:
parent
033560a773
commit
db97e790c3
@ -412,14 +412,14 @@ void Builder_MakeChunk(struct ChunkInfo* info) {
|
||||
hasMesh = BuildChunk(x, y, z, info);
|
||||
if (!hasMesh) return;
|
||||
|
||||
partsIndex = MapRenderer_Pack(x >> CHUNK_SHIFT, y >> CHUNK_SHIFT, z >> CHUNK_SHIFT);
|
||||
partsIndex = World_ChunkPack(x >> CHUNK_SHIFT, y >> CHUNK_SHIFT, z >> CHUNK_SHIFT);
|
||||
offset = 0;
|
||||
hasNorm = false;
|
||||
hasTran = false;
|
||||
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++) {
|
||||
j = i + ATLAS1D_MAX_ATLASES;
|
||||
curIdx = partsIndex + i * MapRenderer_ChunksCount;
|
||||
curIdx = partsIndex + i * World.ChunksCount;
|
||||
|
||||
SetPartInfo(&Builder_Parts[i], &offset, &MapRenderer_PartsNormal[curIdx], &hasNorm);
|
||||
SetPartInfo(&Builder_Parts[j], &offset, &MapRenderer_PartsTranslucent[curIdx], &hasTran);
|
||||
|
@ -218,13 +218,13 @@ static void ClassicLighting_RefreshAffected(int x, int y, int z, BlockID block,
|
||||
ClassicLighting_ResetNeighbour(x, y, z - 1, block, cx, cy, cz - 1, minCy, maxCy);
|
||||
}
|
||||
|
||||
if (bX == 15 && cx < MapRenderer_ChunksX - 1) {
|
||||
if (bX == 15 && cx < World.ChunksX - 1) {
|
||||
ClassicLighting_ResetNeighbour(x + 1, y, z, block, cx + 1, cy, cz, minCy, maxCy);
|
||||
}
|
||||
if (bY == 15 && cy < MapRenderer_ChunksY - 1 && ClassicLighting_Needs(block, World_GetBlock(x, y + 1, z))) {
|
||||
if (bY == 15 && cy < World.ChunksY - 1 && ClassicLighting_Needs(block, World_GetBlock(x, y + 1, z))) {
|
||||
MapRenderer_RefreshChunk(cx, cy + 1, cz);
|
||||
}
|
||||
if (bZ == 15 && cz < MapRenderer_ChunksZ - 1) {
|
||||
if (bZ == 15 && cz < World.ChunksZ - 1) {
|
||||
ClassicLighting_ResetNeighbour(x, y, z + 1, block, cx, cy, cz + 1, minCy, maxCy);
|
||||
}
|
||||
}
|
||||
|
@ -15,8 +15,7 @@
|
||||
#include "World.h"
|
||||
#include "Options.h"
|
||||
|
||||
int MapRenderer_ChunksX, MapRenderer_ChunksY, MapRenderer_ChunksZ;
|
||||
int MapRenderer_1DUsedCount, MapRenderer_ChunksCount;
|
||||
int MapRenderer_1DUsedCount;
|
||||
struct ChunkPartInfo* MapRenderer_PartsNormal;
|
||||
struct ChunkPartInfo* MapRenderer_PartsTranslucent;
|
||||
|
||||
@ -117,7 +116,7 @@ if (drawMin && drawMax) { \
|
||||
}
|
||||
|
||||
static void RenderNormalBatch(int batch) {
|
||||
int batchOffset = MapRenderer_ChunksCount * batch;
|
||||
int batchOffset = World.ChunksCount * batch;
|
||||
struct ChunkInfo* info;
|
||||
struct ChunkPartInfo part;
|
||||
cc_bool drawMin, drawMax;
|
||||
@ -221,7 +220,7 @@ if (drawMin && drawMax) { \
|
||||
}
|
||||
|
||||
static void RenderTranslucentBatch(int batch) {
|
||||
int batchOffset = MapRenderer_ChunksCount * batch;
|
||||
int batchOffset = World.ChunksCount * batch;
|
||||
struct ChunkInfo* info;
|
||||
struct ChunkPartInfo part;
|
||||
cc_bool drawMin, drawMax;
|
||||
@ -324,7 +323,7 @@ static void DeleteChunk(struct ChunkInfo* info) {
|
||||
|
||||
if (info->NormalParts) {
|
||||
ptr = info->NormalParts;
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += MapRenderer_ChunksCount) {
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += World.ChunksCount) {
|
||||
if (ptr->Offset < 0) continue;
|
||||
normPartsCount[i]--;
|
||||
#ifdef CC_BUILD_GL11
|
||||
@ -336,7 +335,7 @@ static void DeleteChunk(struct ChunkInfo* info) {
|
||||
|
||||
if (info->TranslucentParts) {
|
||||
ptr = info->TranslucentParts;
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += MapRenderer_ChunksCount) {
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += World.ChunksCount) {
|
||||
if (ptr->Offset < 0) continue;
|
||||
tranPartsCount[i]--;
|
||||
#ifdef CC_BUILD_GL11
|
||||
@ -363,14 +362,14 @@ static void BuildChunk(struct ChunkInfo* info, int* chunkUpdates) {
|
||||
|
||||
if (info->NormalParts) {
|
||||
ptr = info->NormalParts;
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += MapRenderer_ChunksCount) {
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += World.ChunksCount) {
|
||||
if (ptr->Offset >= 0) normPartsCount[i]++;
|
||||
}
|
||||
}
|
||||
|
||||
if (info->TranslucentParts) {
|
||||
ptr = info->TranslucentParts;
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += MapRenderer_ChunksCount) {
|
||||
for (i = 0; i < MapRenderer_1DUsedCount; i++, ptr += World.ChunksCount) {
|
||||
if (ptr->Offset >= 0) tranPartsCount[i]++;
|
||||
}
|
||||
}
|
||||
@ -400,7 +399,7 @@ static void FreeChunks(void) {
|
||||
|
||||
static void AllocateParts(void) {
|
||||
struct ChunkPartInfo* ptr;
|
||||
cc_uint32 count = MapRenderer_ChunksCount * MapRenderer_1DUsedCount;
|
||||
cc_uint32 count = World.ChunksCount * MapRenderer_1DUsedCount;
|
||||
|
||||
ptr = (struct ChunkPartInfo*)Mem_AllocCleared(count * 2, sizeof(struct ChunkPartInfo), "chunk parts");
|
||||
MapRenderer_PartsNormal = ptr;
|
||||
@ -408,10 +407,10 @@ static void AllocateParts(void) {
|
||||
}
|
||||
|
||||
static void AllocateChunks(void) {
|
||||
mapChunks = (struct ChunkInfo*) Mem_Alloc(MapRenderer_ChunksCount, sizeof(struct ChunkInfo), "chunk info");
|
||||
sortedChunks = (struct ChunkInfo**)Mem_Alloc(MapRenderer_ChunksCount, sizeof(struct ChunkInfo*), "sorted chunk info");
|
||||
renderChunks = (struct ChunkInfo**)Mem_Alloc(MapRenderer_ChunksCount, sizeof(struct ChunkInfo*), "render chunk info");
|
||||
distances = (cc_uint32*)Mem_Alloc(MapRenderer_ChunksCount, 4, "chunk distances");
|
||||
mapChunks = (struct ChunkInfo*) Mem_Alloc(World.ChunksCount, sizeof(struct ChunkInfo), "chunk info");
|
||||
sortedChunks = (struct ChunkInfo**)Mem_Alloc(World.ChunksCount, sizeof(struct ChunkInfo*), "sorted chunk info");
|
||||
renderChunks = (struct ChunkInfo**)Mem_Alloc(World.ChunksCount, sizeof(struct ChunkInfo*), "render chunk info");
|
||||
distances = (cc_uint32*)Mem_Alloc(World.ChunksCount, 4, "chunk distances");
|
||||
}
|
||||
|
||||
static void ResetPartFlags(void) {
|
||||
@ -463,7 +462,7 @@ static void DeleteChunks(void) {
|
||||
int i;
|
||||
if (!mapChunks) return;
|
||||
|
||||
for (i = 0; i < MapRenderer_ChunksCount; i++) {
|
||||
for (i = 0; i < World.ChunksCount; i++) {
|
||||
DeleteChunk(&mapChunks[i]);
|
||||
}
|
||||
ResetPartCounts();
|
||||
@ -496,10 +495,10 @@ static void RefreshBorderChunks(int maxHeight) {
|
||||
chunkPos = IVec3_MaxValue();
|
||||
if (!mapChunks || !World.Blocks) return;
|
||||
|
||||
for (cz = 0; cz < MapRenderer_ChunksZ; cz++) {
|
||||
for (cy = 0; cy < MapRenderer_ChunksY; cy++) {
|
||||
for (cx = 0; cx < MapRenderer_ChunksX; cx++) {
|
||||
onBorder = cx == 0 || cz == 0 || cx == (MapRenderer_ChunksX - 1) || cz == (MapRenderer_ChunksZ - 1);
|
||||
for (cz = 0; cz < World.ChunksZ; cz++) {
|
||||
for (cy = 0; cy < World.ChunksY; cy++) {
|
||||
for (cx = 0; cx < World.ChunksX; cx++) {
|
||||
onBorder = cx == 0 || cz == 0 || cx == (World.ChunksX - 1) || cz == (World.ChunksZ - 1);
|
||||
|
||||
if (onBorder && (cy * CHUNK_SIZE) < maxHeight) {
|
||||
MapRenderer_RefreshChunk(cx, cy, cz);
|
||||
@ -543,7 +542,7 @@ static int UpdateChunksAndVisibility(int* chunkUpdates) {
|
||||
int i, j = 0, distSqr;
|
||||
cc_bool noData;
|
||||
|
||||
for (i = 0; i < MapRenderer_ChunksCount; i++) {
|
||||
for (i = 0; i < World.ChunksCount; i++) {
|
||||
info = sortedChunks[i];
|
||||
if (info->Empty) continue;
|
||||
|
||||
@ -576,7 +575,7 @@ static int UpdateChunksStill(int* chunkUpdates) {
|
||||
int i, j = 0, distSqr;
|
||||
cc_bool noData;
|
||||
|
||||
for (i = 0; i < MapRenderer_ChunksCount; i++) {
|
||||
for (i = 0; i < World.ChunksCount; i++) {
|
||||
info = sortedChunks[i];
|
||||
if (info->Empty) continue;
|
||||
|
||||
@ -661,9 +660,9 @@ static void UpdateSortOrder(void) {
|
||||
/* If in same chunk, don't need to recalculate sort order */
|
||||
if (pos.X == chunkPos.X && pos.Y == chunkPos.Y && pos.Z == chunkPos.Z) return;
|
||||
chunkPos = pos;
|
||||
if (!MapRenderer_ChunksCount) return;
|
||||
if (!World.ChunksCount) return;
|
||||
|
||||
for (i = 0; i < MapRenderer_ChunksCount; i++) {
|
||||
for (i = 0; i < World.ChunksCount; i++) {
|
||||
info = sortedChunks[i];
|
||||
/* Calculate distance to chunk centre */
|
||||
dx = info->CentreX - pos.X; dy = info->CentreY - pos.Y; dz = info->CentreZ - pos.Z;
|
||||
@ -682,7 +681,7 @@ static void UpdateSortOrder(void) {
|
||||
info->DrawYMin = dy >= 0; info->DrawYMax = dy <= 0;
|
||||
}
|
||||
|
||||
SortMapChunks(0, MapRenderer_ChunksCount - 1);
|
||||
SortMapChunks(0, World.ChunksCount - 1);
|
||||
ResetPartFlags();
|
||||
/*SimpleOcclusionCulling();*/
|
||||
}
|
||||
@ -699,10 +698,9 @@ void MapRenderer_Update(double delta) {
|
||||
*#########################################################################################################################*/
|
||||
void MapRenderer_RefreshChunk(int cx, int cy, int cz) {
|
||||
struct ChunkInfo* info;
|
||||
if (cx < 0 || cy < 0 || cz < 0 || cx >= MapRenderer_ChunksX
|
||||
|| cy >= MapRenderer_ChunksY || cz >= MapRenderer_ChunksZ) return;
|
||||
if (cx < 0 || cy < 0 || cz < 0 || cx >= World.ChunksX || cy >= World.ChunksY || cz >= World.ChunksZ) return;
|
||||
|
||||
info = &mapChunks[MapRenderer_Pack(cx, cy, cz)];
|
||||
info = &mapChunks[World_ChunkPack(cx, cy, cz)];
|
||||
if (info->AllAir) return; /* do not recreate chunks completely air */
|
||||
info->Empty = false;
|
||||
info->PendingDelete = true;
|
||||
@ -712,7 +710,7 @@ void MapRenderer_OnBlockChanged(int x, int y, int z, BlockID block) {
|
||||
int cx = x >> CHUNK_SHIFT, cy = y >> CHUNK_SHIFT, cz = z >> CHUNK_SHIFT;
|
||||
struct ChunkInfo* chunk;
|
||||
|
||||
chunk = &mapChunks[MapRenderer_Pack(cx, cy, cz)];
|
||||
chunk = &mapChunks[World_ChunkPack(cx, cy, cz)];
|
||||
chunk->AllAir &= Blocks.Draw[block] == DRAW_GAS;
|
||||
/* TODO: Don't lookup twice, refresh directly using chunk pointer */
|
||||
MapRenderer_RefreshChunk(cx, cy, cz);
|
||||
@ -767,15 +765,9 @@ static void OnNewMap(void) {
|
||||
}
|
||||
|
||||
static void OnNewMapLoaded(void) {
|
||||
int count;
|
||||
MapRenderer_ChunksX = (World.Width + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
MapRenderer_ChunksY = (World.Height + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
MapRenderer_ChunksZ = (World.Length + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
|
||||
count = MapRenderer_ChunksX * MapRenderer_ChunksY * MapRenderer_ChunksZ;
|
||||
/* TODO: Only perform reallocation when map volume has changed */
|
||||
/*if (MapRenderer_ChunksCount != count) { */
|
||||
MapRenderer_ChunksCount = count;
|
||||
/*if (MapRenderer_ChunksCount != World.ChunksCount) { */
|
||||
/* MapRenderer_ChunksCount = World.ChunksCount; */
|
||||
FreeChunks();
|
||||
FreeParts();
|
||||
AllocateChunks();
|
||||
|
@ -10,14 +10,8 @@
|
||||
struct IGameComponent;
|
||||
extern struct IGameComponent MapRenderer_Component;
|
||||
|
||||
extern int MapRenderer_ChunksX, MapRenderer_ChunksY, MapRenderer_ChunksZ;
|
||||
#define MapRenderer_Pack(cx, cy, cz) (((cz) * MapRenderer_ChunksY + (cy)) * MapRenderer_ChunksX + (cx))
|
||||
/* TODO: Swap Y and Z? Make sure to update ChunkUpdater's ResetChunkCache and ClearChunkCache methods! */
|
||||
|
||||
/* Max used 1D atlases. (i.e. Atlas1D_Index(maxTextureLoc) + 1) */
|
||||
extern int MapRenderer_1DUsedCount;
|
||||
/* Number of chunks in the world, or ChunksX * ChunksY * ChunksZ */
|
||||
extern int MapRenderer_ChunksCount;
|
||||
|
||||
/* Buffer for all chunk parts. There are (MapRenderer_ChunksCount * Atlas1D_Count) parts in the buffer,
|
||||
with parts for 'normal' buffer being in lower half. */
|
||||
|
@ -197,7 +197,7 @@ static LRESULT CALLBACK Window_Procedure(HWND handle, UINT message, WPARAM wPara
|
||||
/* To understand reasoning behind the following code, see Remarks in */
|
||||
/* https://docs.microsoft.com/en-us/windows/win32/api/winuser/ns-winuser-rawmouse */
|
||||
static int prevPosX, prevPosY;
|
||||
isVirtual = (raw.data.mouse.usFlags & MOUSE_VIRTUAL_DESKTOP);
|
||||
isVirtual = raw.data.mouse.usFlags & MOUSE_VIRTUAL_DESKTOP;
|
||||
|
||||
width = GetSystemMetrics(isVirtual ? SM_CXVIRTUALSCREEN : SM_CXSCREEN);
|
||||
height = GetSystemMetrics(isVirtual ? SM_CYVIRTUALSCREEN : SM_CYSCREEN);
|
||||
|
@ -91,6 +91,12 @@ CC_NOINLINE void World_SetDimensions(int width, int height, int length) {
|
||||
World.MaxX = width - 1;
|
||||
World.MaxY = height - 1;
|
||||
World.MaxZ = length - 1;
|
||||
|
||||
World.ChunksX = (width + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
World.ChunksY = (height + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
World.ChunksZ = (length + CHUNK_MAX) >> CHUNK_SHIFT;
|
||||
|
||||
World.ChunksCount = World.ChunksX * World.ChunksY * World.ChunksZ;
|
||||
}
|
||||
|
||||
#ifdef EXTENDED_BLOCKS
|
||||
|
@ -15,6 +15,10 @@ extern struct IGameComponent World_Component;
|
||||
#define World_Pack(x, y, z) (((y) * World.Length + (z)) * World.Width + (x))
|
||||
#define WORLD_UUID_LEN 16
|
||||
|
||||
#define World_ChunkPack(cx, cy, cz) (((cz) * World.ChunksY + (cy)) * World.ChunksX + (cx))
|
||||
/* TODO: Swap Y and Z? Make sure to update MapRenderer's ResetChunkCache and ClearChunkCache methods! */
|
||||
|
||||
|
||||
CC_VAR extern struct _WorldData {
|
||||
/* The blocks in the world. */
|
||||
BlockRaw* Blocks;
|
||||
@ -48,6 +52,10 @@ CC_VAR extern struct _WorldData {
|
||||
double LastSave;
|
||||
/* Default name of the world when saving */
|
||||
cc_string Name;
|
||||
/* Number of chunks on each axis the world is subdivided into */
|
||||
int ChunksX, ChunksY, ChunksZ;
|
||||
/* Number of chunks in the world, or ChunksX * ChunksY * ChunksZ */
|
||||
int ChunksCount;
|
||||
} World;
|
||||
|
||||
/* Frees the blocks array, sets dimensions to 0, resets environment to default. */
|
||||
|
Loading…
x
Reference in New Issue
Block a user