summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/block.c17
-rw-r--r--src/block.h10
-rw-r--r--src/chunk.c35
-rw-r--r--src/chunk.h3
-rw-r--r--src/engine.c9
5 files changed, 61 insertions, 13 deletions
diff --git a/src/block.c b/src/block.c
index 2197b2a..56db3f4 100644
--- a/src/block.c
+++ b/src/block.c
@@ -22,6 +22,12 @@ int block_init(vec3 pos, struct block* blk) {
// Store buffer data into struct
// Initialize vbo and ebo for block
memcpy(blk->coords, pos, sizeof(vec3));
+ block_load_gpu(blk);
+ block_update(blk);
+ return 0;
+}
+
+void block_load_gpu(struct block* blk) {
// ========== Constants of a block ================
// Local world coordinates
float vertices[] = {
@@ -122,8 +128,6 @@ int block_init(vec3 pos, struct block* blk) {
//call is create_vbo. Since VAO is already bound, it gets bound to the OLD
//VAO!! Always clear before use.
glBindVertexArray(0);
- block_update(blk);
- return 0;
}
void block_update(struct block* blk) {
@@ -172,3 +176,12 @@ void block_debug(struct block *blk) {
glm_mat4_print(blk->model, stderr);
}
+
+void block_unload(struct block *blk) {
+ // Clear VBO data
+ glDeleteBuffers(1, &blk->_vbo);
+ // Clear EBO data
+ glDeleteBuffers(1, &blk->_ebo);
+ // Clear VAO
+ glDeleteVertexArrays(1, &blk->_vao);
+}
diff --git a/src/block.h b/src/block.h
index b19265d..f55f784 100644
--- a/src/block.h
+++ b/src/block.h
@@ -24,3 +24,13 @@ int block_init(vec3 pos, struct block* blk);
int block_draw(struct block* blk, struct shader* shader);
void block_debug(struct block* blk);
void block_update(struct block* blk);
+
+/**
+ * Remove GPU related data of a block. This is usually called by chunk_unload
+ *
+ */
+void block_unload(struct block* blk);
+/**
+ * Load GPU data of a block
+ */
+void block_load_gpu(struct block* blk);
diff --git a/src/chunk.c b/src/chunk.c
index 4d15486..4918d22 100644
--- a/src/chunk.c
+++ b/src/chunk.c
@@ -114,6 +114,7 @@ void _chunk_plains_gen(struct chunk* chunk) {
}
}
}
+ chunk->loaded = 1;
}
@@ -125,16 +126,25 @@ void chunk_load(struct chunk *chunk, int coord[2]) {
for (int z = 0; z < CHUNK_LENGTH; z++) {
struct block* blk = chunk->blocks[x][z][y];
if (blk != NULL) {
- // Translate to world coordinates
- // First do block updates, set the position of the block in local
- // chunk coordinates
- block_update(blk);
- // Then translate them to world coordinates
- glm_translate(blk->model, translation);
+ // If chunk is unloaded, send block data to GPU
+ if (chunk->loaded == 0) {
+ // Add GPU data
+ block_load_gpu(blk);
+ }
+ // Translate to world coordinates
+ // First do block updates, set the position of the block in local
+ // chunk coordinates
+ block_update(blk);
+ // Then translate them to world coordinates
+ glm_translate(blk->model, translation);
}
}
}
}
+ if (chunk->loaded == 0) {
+ //We've reloaded all data - flip bit again
+ chunk->loaded = 1;
+ }
}
void chunk_draw(struct chunk* chunk, struct shader* shader) {
@@ -154,4 +164,17 @@ void chunk_draw(struct chunk* chunk, struct shader* shader) {
}
void chunk_unload(struct chunk* chunk) {
+ for (int i = 0; i < CHUNK_WIDTH; i++) {
+ for (int j = 0; j < CHUNK_LENGTH; j++) {
+ for (int k = 0; k < CHUNK_HEIGHT; k++) {
+ struct block* blk = chunk->blocks[i][j][k];
+ if (blk == NULL) {
+ continue;
+ }
+ block_unload(blk);
+ }
+ }
+ }
+ chunk->loaded = 0;
+
}
diff --git a/src/chunk.h b/src/chunk.h
index ac24a2d..0122cf9 100644
--- a/src/chunk.h
+++ b/src/chunk.h
@@ -20,6 +20,7 @@ struct chunk {
struct block* blocks[CHUNK_WIDTH][CHUNK_LENGTH][CHUNK_HEIGHT];
enum biome biome;
vec2 coord;
+ int loaded;
};
/**
@@ -38,7 +39,7 @@ int chunk_gen(struct world* wld, vec2 coord, struct chunk** chunk);
*/
void chunk_load(struct chunk* chunk, int coord[2]);
/**
- * Unload a chunk. Delete GPU data, not the chunk data itself
+ * Unload a chunk. Delete block GPU and memory data, not the chunk data itself
*
* @param chunk Chunk to load
*/
diff --git a/src/engine.c b/src/engine.c
index 2d509f3..b840a2f 100644
--- a/src/engine.c
+++ b/src/engine.c
@@ -63,9 +63,7 @@ void engine_update(struct engine* engine) {
engine->curr_chunk[1],
curr_chunk[0],
curr_chunk[1]);
- // Update the curr_chunk
- memcpy(engine->curr_chunk, curr_chunk, sizeof(vec2));
- // Load chunks of CHUNK_DISTANCE around curr_chunk
+ // Unload existing chunks
for (int i = -CHUNK_DISTANCE; i <= CHUNK_DISTANCE; i++) {
for (int j = -CHUNK_DISTANCE; j <= CHUNK_DISTANCE; j++) {
struct chunk* chunk;
@@ -75,9 +73,12 @@ void engine_update(struct engine* engine) {
int real_coord[2] = { i + CHUNK_DISTANCE, j + CHUNK_DISTANCE };
// engine->loaded_chunks[real_coord[0]][real_coord[1]] = chunk;
// Load chunk
- chunk_load(chunk, chunk_coord);
+ chunk_unload(chunk);
}
}
+ // Update the curr_chunk
+ memcpy(engine->curr_chunk, curr_chunk, sizeof(vec2));
+ // Load chunks of CHUNK_DISTANCE around curr_chunk
}
}