Created chunk renderer
This commit is contained in:
parent
fec3d35fe9
commit
132f84a43f
|
@ -20,6 +20,7 @@ typedef struct tc_block_attribute
|
||||||
typedef struct tc_block_entry
|
typedef struct tc_block_entry
|
||||||
{
|
{
|
||||||
char *name;
|
char *name;
|
||||||
|
uint32_t identifier;
|
||||||
|
|
||||||
uint32_t attributes_capacity;
|
uint32_t attributes_capacity;
|
||||||
uint32_t num_attributes;
|
uint32_t num_attributes;
|
||||||
|
|
|
@ -0,0 +1,31 @@
|
||||||
|
#include "world.h"
|
||||||
|
|
||||||
|
bool tc_generate_default_terrain_chunk(tc_worldgen_s *gen, tc_chunk_s *chunk)
|
||||||
|
{
|
||||||
|
tc_block_s block;
|
||||||
|
block.type_identifier = 1;
|
||||||
|
block.position.x = 0.0f;
|
||||||
|
block.position.y = 0.0f;
|
||||||
|
block.position.z = 0.0f;
|
||||||
|
|
||||||
|
uint32_t x_in_chunk = 0;
|
||||||
|
uint32_t y_in_chunk = 0;
|
||||||
|
uint32_t z_in_chunk = 0;
|
||||||
|
while(x_in_chunk < 32)
|
||||||
|
{
|
||||||
|
y_in_chunk = 0;
|
||||||
|
while(y_in_chunk < 32)
|
||||||
|
{
|
||||||
|
z_in_chunk = 0;
|
||||||
|
while(z_in_chunk < 32)
|
||||||
|
{
|
||||||
|
tc_set_block_in_chunk(chunk, x_in_chunk, y_in_chunk, z_in_chunk, block);
|
||||||
|
++z_in_chunk;
|
||||||
|
}
|
||||||
|
++y_in_chunk;
|
||||||
|
}
|
||||||
|
++x_in_chunk;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
|
@ -1,4 +1,5 @@
|
||||||
#include "state.h"
|
#include "state.h"
|
||||||
|
#include "world.h"
|
||||||
|
|
||||||
#include <SDL2/SDL.h>
|
#include <SDL2/SDL.h>
|
||||||
|
|
||||||
|
@ -17,6 +18,10 @@ void tc_init_renderer(techneck_s *techneck)
|
||||||
SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE
|
SDL_WINDOW_OPENGL | SDL_WINDOW_RESIZABLE
|
||||||
);
|
);
|
||||||
|
|
||||||
|
techneck->renderer.active_camera.position.x = 0.0f;
|
||||||
|
techneck->renderer.active_camera.position.y = 0.0f;
|
||||||
|
techneck->renderer.active_camera.position.z = 0.0f;
|
||||||
|
|
||||||
techneck->renderer.gl_context = SDL_GL_CreateContext(techneck->renderer.window);
|
techneck->renderer.gl_context = SDL_GL_CreateContext(techneck->renderer.window);
|
||||||
gladLoadGLLoader(&SDL_GL_GetProcAddress);
|
gladLoadGLLoader(&SDL_GL_GetProcAddress);
|
||||||
gladLoadGL();
|
gladLoadGL();
|
||||||
|
@ -31,6 +36,8 @@ techneck_s tc_init()
|
||||||
{
|
{
|
||||||
techneck_s techneck;
|
techneck_s techneck;
|
||||||
tc_init_renderer(&techneck);
|
tc_init_renderer(&techneck);
|
||||||
|
techneck.main_world = tc_init_worlds();
|
||||||
|
techneck.block_registry = tc_init_blocks();
|
||||||
|
|
||||||
return techneck;
|
return techneck;
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,8 @@ techneck_s tc_game_state_g;
|
||||||
mat4x4 projection_matrix;
|
mat4x4 projection_matrix;
|
||||||
mat4x4 view_matrix;
|
mat4x4 view_matrix;
|
||||||
|
|
||||||
float triangle_vertices[108] = {
|
float triangle_vertices[108] =
|
||||||
|
{
|
||||||
// Front
|
// Front
|
||||||
-0.5f, -0.5f, -0.5f,
|
-0.5f, -0.5f, -0.5f,
|
||||||
-0.5f, 0.5f, -0.5f,
|
-0.5f, 0.5f, -0.5f,
|
||||||
|
@ -62,9 +63,7 @@ float triangle_vertices[108] = {
|
||||||
|
|
||||||
0.5f, -0.5f, 0.5f,
|
0.5f, -0.5f, 0.5f,
|
||||||
-0.5f, -0.5f, 0.5f,
|
-0.5f, -0.5f, 0.5f,
|
||||||
0.5f, -0.5f, -0.5f,
|
0.5f, -0.5f, -0.5f
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
tc_vec3_s tc_camera_position = { 0.0f, 0.0f, 0.0f };
|
tc_vec3_s tc_camera_position = { 0.0f, 0.0f, 0.0f };
|
||||||
|
@ -124,7 +123,8 @@ void render()
|
||||||
glUniformMatrix4fv(view_uniform_location, 1, GL_FALSE, &view_matrix[0][0]);
|
glUniformMatrix4fv(view_uniform_location, 1, GL_FALSE, &view_matrix[0][0]);
|
||||||
// printf("%d\n", view_uniform_location);
|
// printf("%d\n", view_uniform_location);
|
||||||
|
|
||||||
render_block(block);
|
// render_block(block);
|
||||||
|
tc_draw_world(&tc_game_state_g.main_world);
|
||||||
|
|
||||||
SDL_GL_SwapWindow(tc_game_state_g.renderer.window);
|
SDL_GL_SwapWindow(tc_game_state_g.renderer.window);
|
||||||
}
|
}
|
||||||
|
@ -261,7 +261,7 @@ bool update()
|
||||||
int main(int argc, char **argv)
|
int main(int argc, char **argv)
|
||||||
{
|
{
|
||||||
tc_game_state_g = tc_init();
|
tc_game_state_g = tc_init();
|
||||||
tc_game_state_g.block_registry = tc_init_blocks();
|
tc_new_chunk(&tc_game_state_g.main_world, 0.0f, 0.0f, 0.0f);
|
||||||
|
|
||||||
block = tc_new_block_at_3f(0.0, 0.0, 0.0);
|
block = tc_new_block_at_3f(0.0, 0.0, 0.0);
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,147 @@
|
||||||
|
#include "world.h"
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
float tc_block_vertices[108] =
|
||||||
|
{
|
||||||
|
// Front
|
||||||
|
-0.5f, -0.5f, -0.5f,
|
||||||
|
-0.5f, 0.5f, -0.5f,
|
||||||
|
0.5f, -0.5f, -0.5f,
|
||||||
|
|
||||||
|
0.5f, 0.5f, -0.5f,
|
||||||
|
0.5f, -0.5f, -0.5f,
|
||||||
|
-0.5f, 0.5f, -0.5f,
|
||||||
|
|
||||||
|
// Back
|
||||||
|
-0.5f, -0.5f, 0.5f,
|
||||||
|
-0.5f, 0.5f, 0.5f,
|
||||||
|
0.5f, -0.5f, 0.5f,
|
||||||
|
|
||||||
|
0.5f, 0.5f, 0.5f,
|
||||||
|
0.5f, -0.5f, 0.5f,
|
||||||
|
-0.5f, 0.5f, 0.5f,
|
||||||
|
|
||||||
|
// Left
|
||||||
|
-0.5f, 0.5f, -0.5f,
|
||||||
|
-0.5f, -0.5f, -0.5f,
|
||||||
|
-0.5f, -0.5f, 0.5f,
|
||||||
|
|
||||||
|
-0.5f, -0.5f, -0.5f,
|
||||||
|
-0.5f, 0.5f, 0.5f,
|
||||||
|
-0.5f, -0.5f, 0.5f,
|
||||||
|
|
||||||
|
// Right
|
||||||
|
0.5f, 0.5f, -0.5f,
|
||||||
|
0.5f, -0.5f, -0.5f,
|
||||||
|
0.5f, -0.5f, 0.5f,
|
||||||
|
|
||||||
|
0.5f, -0.5f, -0.5f,
|
||||||
|
0.5f, 0.5f, 0.5f,
|
||||||
|
0.5f, -0.5f, 0.5f,
|
||||||
|
|
||||||
|
// Top
|
||||||
|
-0.5f, 0.5f, -0.5f,
|
||||||
|
-0.5f, 0.5f, 0.5f,
|
||||||
|
0.5f, 0.5f, -0.5f,
|
||||||
|
|
||||||
|
0.5f, 0.5f, 0.5f,
|
||||||
|
-0.5f, 0.5f, 0.5f,
|
||||||
|
0.5f, 0.5f, -0.5f,
|
||||||
|
|
||||||
|
// Bottom
|
||||||
|
-0.5f, -0.5f, -0.5f,
|
||||||
|
-0.5f, -0.5f, 0.5f,
|
||||||
|
0.5f, -0.5f, -0.5f,
|
||||||
|
|
||||||
|
0.5f, -0.5f, 0.5f,
|
||||||
|
-0.5f, -0.5f, 0.5f,
|
||||||
|
0.5f, -0.5f, -0.5f
|
||||||
|
};
|
||||||
|
|
||||||
|
uint32_t tc_count_chunk_vertices(tc_chunk_s *chunk)
|
||||||
|
{
|
||||||
|
uint32_t num_vertices = 0;
|
||||||
|
|
||||||
|
uint32_t x_in_chunk = 0;
|
||||||
|
uint32_t y_in_chunk = 0;
|
||||||
|
uint32_t z_in_chunk = 0;
|
||||||
|
while(x_in_chunk < 32)
|
||||||
|
{
|
||||||
|
y_in_chunk = 0;
|
||||||
|
while(y_in_chunk < 32)
|
||||||
|
{
|
||||||
|
z_in_chunk = 0;
|
||||||
|
while(z_in_chunk < 32)
|
||||||
|
{
|
||||||
|
if(chunk->blocks[x_in_chunk][y_in_chunk][z_in_chunk].type_identifier > 0)
|
||||||
|
{
|
||||||
|
num_vertices += 36;
|
||||||
|
}
|
||||||
|
++z_in_chunk;
|
||||||
|
}
|
||||||
|
++y_in_chunk;
|
||||||
|
}
|
||||||
|
++x_in_chunk;
|
||||||
|
}
|
||||||
|
return num_vertices;
|
||||||
|
}
|
||||||
|
|
||||||
|
void tc_meshize_chunk(tc_chunk_s *chunk)
|
||||||
|
{
|
||||||
|
chunk->num_vertices = tc_count_chunk_vertices(chunk);
|
||||||
|
chunk->vertex_positions = malloc(sizeof(float) * 3 * chunk->num_vertices);
|
||||||
|
|
||||||
|
uint32_t vertex_index = 0;
|
||||||
|
float block_positions[36*3];
|
||||||
|
|
||||||
|
uint32_t x_in_chunk = 0;
|
||||||
|
uint32_t y_in_chunk = 0;
|
||||||
|
uint32_t z_in_chunk = 0;
|
||||||
|
while(x_in_chunk < 32)
|
||||||
|
{
|
||||||
|
y_in_chunk = 0;
|
||||||
|
while(y_in_chunk < 32)
|
||||||
|
{
|
||||||
|
z_in_chunk = 0;
|
||||||
|
while(z_in_chunk < 32)
|
||||||
|
{
|
||||||
|
if(chunk->blocks[x_in_chunk][y_in_chunk][z_in_chunk].type_identifier > 0)
|
||||||
|
{
|
||||||
|
memcpy(
|
||||||
|
block_positions,
|
||||||
|
tc_block_vertices,
|
||||||
|
sizeof(float) * 36 * 3
|
||||||
|
);
|
||||||
|
|
||||||
|
// Move the current block to where it is supposed to be
|
||||||
|
|
||||||
|
uint32_t vertex_of_block = 0;
|
||||||
|
while(vertex_of_block < 36)
|
||||||
|
{
|
||||||
|
uint32_t vertex_start = vertex_of_block * 3;
|
||||||
|
block_positions[vertex_start] +=
|
||||||
|
x_in_chunk;
|
||||||
|
block_positions[vertex_start + 1] +=
|
||||||
|
y_in_chunk;
|
||||||
|
block_positions[vertex_start + 2] +=
|
||||||
|
z_in_chunk;
|
||||||
|
++vertex_of_block;
|
||||||
|
}
|
||||||
|
|
||||||
|
memcpy(
|
||||||
|
&chunk->vertex_positions[vertex_index],
|
||||||
|
block_positions,
|
||||||
|
sizeof(float) * 36 * 3
|
||||||
|
);
|
||||||
|
vertex_index += 36;
|
||||||
|
}
|
||||||
|
++z_in_chunk;
|
||||||
|
}
|
||||||
|
++y_in_chunk;
|
||||||
|
}
|
||||||
|
++x_in_chunk;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -8,30 +8,8 @@
|
||||||
|
|
||||||
#include "shaders.h"
|
#include "shaders.h"
|
||||||
#include "blocks.h"
|
#include "blocks.h"
|
||||||
|
#include "world.h"
|
||||||
typedef struct tc_vec3
|
#include "utility.h"
|
||||||
{
|
|
||||||
float x;
|
|
||||||
float y;
|
|
||||||
float z;
|
|
||||||
|
|
||||||
} tc_vec3_s;
|
|
||||||
|
|
||||||
typedef struct tc_object
|
|
||||||
{
|
|
||||||
uint32_t vbo;
|
|
||||||
uint32_t vao;
|
|
||||||
tc_vec3_s position;
|
|
||||||
tc_vec3_s rotation;
|
|
||||||
|
|
||||||
} tc_object_s;
|
|
||||||
|
|
||||||
typedef struct tc_block
|
|
||||||
{
|
|
||||||
tc_vec3_s position;
|
|
||||||
tc_object_s drawing;
|
|
||||||
|
|
||||||
} tc_block_s;
|
|
||||||
|
|
||||||
typedef struct tc_camera
|
typedef struct tc_camera
|
||||||
{
|
{
|
||||||
|
@ -55,6 +33,7 @@ typedef struct
|
||||||
{
|
{
|
||||||
tc_renderer_s renderer;
|
tc_renderer_s renderer;
|
||||||
tc_block_registry_s block_registry;
|
tc_block_registry_s block_registry;
|
||||||
|
tc_world_s main_world;
|
||||||
|
|
||||||
} techneck_s;
|
} techneck_s;
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,23 @@
|
||||||
|
|
||||||
|
#ifndef TC_UTILITY_H
|
||||||
|
#define TC_UTILITY_H
|
||||||
|
|
||||||
|
typedef struct tc_vec3
|
||||||
|
{
|
||||||
|
float x;
|
||||||
|
float y;
|
||||||
|
float z;
|
||||||
|
|
||||||
|
} tc_vec3_s;
|
||||||
|
|
||||||
|
typedef struct tc_object
|
||||||
|
{
|
||||||
|
uint32_t vbo;
|
||||||
|
uint32_t vao;
|
||||||
|
tc_vec3_s position;
|
||||||
|
tc_vec3_s rotation;
|
||||||
|
|
||||||
|
} tc_object_s;
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
|
@ -0,0 +1,106 @@
|
||||||
|
#include "world.h"
|
||||||
|
#include "state.h"
|
||||||
|
#include <linmath.h>
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
tc_worldgen_s tc_default_terrain_generator_g;
|
||||||
|
|
||||||
|
void tc_draw_chunk(tc_chunk_s *chunk)
|
||||||
|
{
|
||||||
|
mat4x4 model_matrix;
|
||||||
|
mat4x4_translate(model_matrix, chunk->position.x*32, chunk->position.y*32, chunk->position.z*32);
|
||||||
|
|
||||||
|
int model_matrix_uniform_location =
|
||||||
|
glGetUniformLocation(tc_game_state_g.renderer.draw_shader.program_id, "model_matrix");
|
||||||
|
glUniformMatrix4fv(model_matrix_uniform_location, 1, GL_FALSE, &model_matrix[0][0]);
|
||||||
|
|
||||||
|
// glBindVertexArray(chunk->vao);
|
||||||
|
glBindBuffer(GL_ARRAY_BUFFER, chunk->vertex_data);
|
||||||
|
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void *) 0);
|
||||||
|
glEnableVertexAttribArray(0);
|
||||||
|
|
||||||
|
glDrawArrays(GL_TRIANGLES, 0, chunk->num_vertices);
|
||||||
|
|
||||||
|
glBindVertexArray(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tc_init_world_generators()
|
||||||
|
{
|
||||||
|
tc_default_terrain_generator_g.name = "Default Terrain Generator";
|
||||||
|
tc_default_terrain_generator_g.fn_generate_chunk = &tc_generate_default_terrain_chunk;
|
||||||
|
}
|
||||||
|
|
||||||
|
tc_world_s tc_init_worlds()
|
||||||
|
{
|
||||||
|
tc_init_world_generators();
|
||||||
|
|
||||||
|
tc_world_s world;
|
||||||
|
world.chunks_capacity = 256;
|
||||||
|
world.num_chunks = 0;
|
||||||
|
world.chunks = calloc(sizeof(tc_chunk_s *), world.chunks_capacity);
|
||||||
|
world.worldgen = &tc_default_terrain_generator_g;
|
||||||
|
|
||||||
|
return world;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void tc_set_block_in_chunk(
|
||||||
|
tc_chunk_s *chunk,
|
||||||
|
uint32_t x, uint32_t y, uint32_t z,
|
||||||
|
tc_block_s block
|
||||||
|
) {
|
||||||
|
chunk->blocks[x][y][z] = block;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void tc_draw_world(tc_world_s *world)
|
||||||
|
{
|
||||||
|
uint32_t chunk_index = 0;
|
||||||
|
while(chunk_index < world->num_chunks)
|
||||||
|
{
|
||||||
|
tc_draw_chunk(world->chunks[chunk_index]);
|
||||||
|
++chunk_index;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void tc_add_chunk(tc_world_s *world, tc_chunk_s *chunk)
|
||||||
|
{
|
||||||
|
if(world->num_chunks >= world->chunks_capacity)
|
||||||
|
{
|
||||||
|
world->chunks_capacity *= 2;
|
||||||
|
world->chunks = realloc(world->chunks, sizeof(tc_chunk_s *) * world->chunks_capacity);
|
||||||
|
}
|
||||||
|
world->chunks[world->num_chunks] = chunk;
|
||||||
|
++world->num_chunks;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Creates & Generates a chunk and provides a pointer to it
|
||||||
|
tc_chunk_s * tc_new_chunk(tc_world_s *world, float x, float y, float z)
|
||||||
|
{
|
||||||
|
tc_chunk_s *chunk = malloc(sizeof(tc_chunk_s));
|
||||||
|
chunk->position.x = x;
|
||||||
|
chunk->position.y = y;
|
||||||
|
chunk->position.z = z;
|
||||||
|
world->worldgen->fn_generate_chunk(world->worldgen, chunk);
|
||||||
|
tc_meshize_chunk(chunk);
|
||||||
|
|
||||||
|
glGenVertexArrays(1, &chunk->vao);
|
||||||
|
glBindVertexArray(chunk->vao);
|
||||||
|
|
||||||
|
glGenBuffers(1, &chunk->vertex_data);
|
||||||
|
glBindBuffer(GL_ARRAY_BUFFER, chunk->vertex_data);
|
||||||
|
|
||||||
|
glBufferData(GL_ARRAY_BUFFER, chunk->num_vertices * 3 * sizeof(float), chunk->vertex_positions, GL_STATIC_DRAW);
|
||||||
|
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 3 * sizeof(float), (void *) 0);
|
||||||
|
glEnableVertexAttribArray(0);
|
||||||
|
|
||||||
|
glBindVertexArray(0);
|
||||||
|
|
||||||
|
tc_add_chunk(world, chunk);
|
||||||
|
|
||||||
|
return chunk;
|
||||||
|
}
|
||||||
|
|
|
@ -0,0 +1,70 @@
|
||||||
|
|
||||||
|
#ifndef TC_WORLD_H
|
||||||
|
#define TC_WORLD_H
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
#include "blocks.h"
|
||||||
|
#include "utility.h"
|
||||||
|
|
||||||
|
typedef struct tc_worldgen tc_worldgen_s;
|
||||||
|
typedef struct tc_block tc_block_s;
|
||||||
|
typedef struct tc_chunk tc_chunk_s;
|
||||||
|
typedef struct tc_world tc_world_s;
|
||||||
|
|
||||||
|
struct tc_worldgen
|
||||||
|
{
|
||||||
|
char *name;
|
||||||
|
bool (*fn_generate_chunk) (tc_worldgen_s *gen, tc_chunk_s *chunk);
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
struct tc_block
|
||||||
|
{
|
||||||
|
uint32_t type_identifier;
|
||||||
|
tc_vec3_s position;
|
||||||
|
tc_object_s drawing;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
struct tc_chunk
|
||||||
|
{
|
||||||
|
tc_vec3_s position;
|
||||||
|
tc_block_s blocks[32][32][32];
|
||||||
|
|
||||||
|
uint32_t num_vertices;
|
||||||
|
float *vertex_positions;
|
||||||
|
|
||||||
|
uint32_t vao;
|
||||||
|
uint32_t vertex_data;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
struct tc_world
|
||||||
|
{
|
||||||
|
uint32_t chunks_capacity;
|
||||||
|
uint32_t num_chunks;
|
||||||
|
tc_chunk_s **chunks;
|
||||||
|
|
||||||
|
tc_worldgen_s *worldgen;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
tc_world_s tc_init_worlds ();
|
||||||
|
void tc_draw_world (tc_world_s *world);
|
||||||
|
|
||||||
|
tc_chunk_s * tc_new_chunk (tc_world_s *world, float x, float y, float z);
|
||||||
|
|
||||||
|
void tc_set_block_in_chunk(
|
||||||
|
tc_chunk_s *chunk,
|
||||||
|
uint32_t x, uint32_t y, uint32_t z,
|
||||||
|
tc_block_s block
|
||||||
|
);
|
||||||
|
|
||||||
|
void tc_meshize_chunk (tc_chunk_s *chunk);
|
||||||
|
|
||||||
|
bool tc_generate_default_terrain_chunk (tc_worldgen_s *gen, tc_chunk_s *chunk);
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
Loading…
Reference in New Issue