diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/core/camera.c | 9 | ||||
-rw-r--r-- | src/core/camera.h | 4 | ||||
-rw-r--r-- | src/core/core.c | 4 | ||||
-rw-r--r-- | src/maths/primitives.c | 10 | ||||
-rw-r--r-- | src/new_render/pbr.c | 2 | ||||
-rw-r--r-- | src/new_render/pbr.h | 9 | ||||
-rw-r--r-- | src/new_render/render.c | 8 | ||||
-rw-r--r-- | src/new_render/render.h | 5 | ||||
-rw-r--r-- | src/new_render/render_types.h | 7 | ||||
-rw-r--r-- | src/ral/backends/opengl/backend_opengl.c | 3 | ||||
-rw-r--r-- | src/resources/gltf.c | 476 | ||||
-rw-r--r-- | src/systems/input.h | 14 | ||||
-rw-r--r-- | src/systems/terrain.h | 10 |
13 files changed, 302 insertions, 259 deletions
diff --git a/src/core/camera.c b/src/core/camera.c index cde457b..7bddb7e 100644 --- a/src/core/camera.c +++ b/src/core/camera.c @@ -4,6 +4,9 @@ #include "keys.h" #include "maths.h" +#define CAMERA_SPEED 0.2 +#define CAMERA_SENSITIVITY 0.5 + Camera Camera_Create(Vec3 pos, Vec3 front, Vec3 up, f32 fov) { Camera c = { .position = pos, .front = front, .up = up, .fov = fov }; return c; @@ -22,12 +25,12 @@ Mat4 Camera_ViewProj(Camera *c, f32 lens_height, f32 lens_width, Mat4 *out_view, return mat4_mult(view, proj); } -void Camera_Update(Camera *camera) { +void FlyCamera_Update(Camera *camera) { static f32 yaw = 0.0; static f32 pitch = 0.0; // Keyboard - f32 speed = 0.25; + f32 speed = CAMERA_SPEED; Vec3 horizontal = vec3_cross(camera->front, camera->up); if (key_is_pressed(KEYCODE_A) || key_is_pressed(KEYCODE_KEY_LEFT)) { Vec3 displacement = vec3_mult(horizontal, -speed); @@ -62,7 +65,7 @@ void Camera_Update(Camera *camera) { f32 x_offset = mouse.x_delta; f32 y_offset = -mouse.y_delta; - f32 sensitivity = 0.7f; // change this value to your liking + f32 sensitivity = CAMERA_SENSITIVITY; // change this value to your liking x_offset *= sensitivity; y_offset *= sensitivity; diff --git a/src/core/camera.h b/src/core/camera.h index 450f81e..536feca 100644 --- a/src/core/camera.h +++ b/src/core/camera.h @@ -15,7 +15,7 @@ typedef struct Camera { } Camera; /** @brief create a camera */ -Camera Camera_Create(Vec3 pos, Vec3 front, Vec3 up, f32 fov); +PUB Camera Camera_Create(Vec3 pos, Vec3 front, Vec3 up, f32 fov); /** * @brief Get 3D camera transform matrix @@ -31,7 +31,7 @@ PUB Mat4 Camera_View2D(Camera* c); // TODO: 2D cameras struct Input_State; -void Camera_Update(Camera* camera); +PUB void FlyCamera_Update(Camera* camera); // TODO: (HIGH) Basic reusable camera controls /* diff --git a/src/core/core.c b/src/core/core.c index 20bc813..fffb43d 100644 --- a/src/core/core.c +++ b/src/core/core.c @@ -78,6 +78,4 @@ Core* get_global_core() { return &g_core; } GLFWwindow* Core_GetGlfwWindowPtr(Core* core) { return g_core.window; } -struct Renderer* Core_GetRenderer(Core* core) { - return core->renderer; -}
\ No newline at end of file +struct Renderer* Core_GetRenderer(Core* core) { return core->renderer; }
\ No newline at end of file diff --git a/src/maths/primitives.c b/src/maths/primitives.c index 32e7919..ceae260 100644 --- a/src/maths/primitives.c +++ b/src/maths/primitives.c @@ -45,9 +45,11 @@ Geometry Geo_CreatePlane(f32x2 extents) { push_triangle(indices, 2, 1, 0); push_triangle(indices, 3, 1, 2); - Geometry geo = { - .format = VERTEX_STATIC_3D, .vertices = vertices, .has_indices = true, .indices = indices - }; + Geometry geo = { .format = VERTEX_STATIC_3D, + .vertices = vertices, + .has_indices = true, + .index_count = indices->len, + .indices = indices }; // .colour = (rgba){ 0, 0, 0, 1 } }; return geo; @@ -126,6 +128,7 @@ Geometry Geo_CreateCuboid(f32x3 extents) { .format = VERTEX_STATIC_3D, .vertices = vertices, .has_indices = true, + .index_count = indices->len, .indices = indices, // FIXME: make darray methods that return stack allocated struct }; @@ -233,6 +236,7 @@ Geometry geo_create_uvsphere(f32 radius, u32 north_south_lines, u32 east_west_li .format = VERTEX_STATIC_3D, .vertices = vertices, .has_indices = true, + .index_count = indices->len, .indices = indices, }; return geo; diff --git a/src/new_render/pbr.c b/src/new_render/pbr.c index 09da50e..4a91080 100644 --- a/src/new_render/pbr.c +++ b/src/new_render/pbr.c @@ -94,7 +94,7 @@ void PBR_Execute(PBR_Storage* storage, Camera camera, TextureHandle shadowmap_te lights_data = { .pointLights = { // FIXME: add lights to our RenderScene structure. for now these are // hardcoded - (pbr_point_light){ .pos = vec3(10, 10, 10), .color = light_color }, + (pbr_point_light){ .pos = vec3(0.0, 2.0, 2.0), .color = light_color }, (pbr_point_light){ .pos = vec3(-10, 10, 10), .color = light_color }, (pbr_point_light){ .pos = vec3(10, -10, 10), .color = light_color }, (pbr_point_light){ .pos = vec3(-10, -10, 10), .color = light_color }, diff --git a/src/new_render/pbr.h b/src/new_render/pbr.h index d8c9405..cbdc577 100644 --- a/src/new_render/pbr.h +++ b/src/new_render/pbr.h @@ -48,11 +48,10 @@ typedef struct PBR_Textures { TextureHandle ao_map; } PBR_Textures; -// --- Internal - -typedef struct MaterialMap MaterialMap; +PUB Material PBRMaterialDefault(); +PUB ShaderDataLayout PBRMaterial_GetLayout(void* data); -Material PBRMaterialDefault(); +// --- Internal GPU_Renderpass* PBR_RPassCreate(); @@ -60,5 +59,3 @@ GPU_Pipeline* PBR_PipelineCreate(GPU_Renderpass* rpass); void PBR_Execute(PBR_Storage* storage, Camera camera, TextureHandle shadowmap_tex, RenderEnt* entities, size_t entity_count); - -ShaderDataLayout PBRMaterial_GetLayout(void* data);
\ No newline at end of file diff --git a/src/new_render/render.c b/src/new_render/render.c index 235f1cb..77a3269 100644 --- a/src/new_render/render.c +++ b/src/new_render/render.c @@ -37,6 +37,7 @@ struct Renderer { GPU_Swapchain swapchain; GPU_Renderpass* default_renderpass; bool frame_aborted; + RenderMode render_mode; RenderScene scene; PBR_Storage* pbr; Shadow_Storage* shadows; @@ -54,6 +55,7 @@ Renderer* get_renderer() { return g_core.renderer; } bool Renderer_Init(RendererConfig config, Renderer* ren, GLFWwindow** out_window, GLFWwindow* optional_window) { INFO("Renderer init"); + ren->render_mode = RENDER_MODE_DEFAULT; ren->frame_arena = arena_create(malloc(FRAME_ARENA_SIZE), FRAME_ARENA_SIZE); @@ -293,6 +295,7 @@ TextureHandle Render_GetWhiteTexture() { return ren->white_1x1; } +/** @return an arena allocator that gets cleared at the beginning of every render frame */ arena* Render_GetFrameArena() { Renderer* ren = Core_GetRenderer(&g_core); return &ren->frame_arena; @@ -305,4 +308,9 @@ Mesh_pool* Render_GetMeshPool() { Material_pool* Render_GetMaterialPool() { Renderer* ren = Core_GetRenderer(&g_core); return &ren->material_pool; +} + +void Render_SetRenderMode(RenderMode mode) { + Renderer* ren = Core_GetRenderer(&g_core); + ren->render_mode = mode; }
\ No newline at end of file diff --git a/src/new_render/render.h b/src/new_render/render.h index ef11b5f..b7af7cb 100644 --- a/src/new_render/render.h +++ b/src/new_render/render.h @@ -84,4 +84,7 @@ Terrain_Storage* Render_GetTerrainStorage(); TextureHandle Render_GetWhiteTexture(); arena* Render_GetFrameArena(); Mesh_pool* Render_GetMeshPool(); -Material_pool* Render_GetMaterialPool();
\ No newline at end of file +Material_pool* Render_GetMaterialPool(); + +// --- Setters +void Render_SetRenderMode(RenderMode mode);
\ No newline at end of file diff --git a/src/new_render/render_types.h b/src/new_render/render_types.h index 2b7a77a..5fdca8a 100644 --- a/src/new_render/render_types.h +++ b/src/new_render/render_types.h @@ -17,6 +17,13 @@ CORE_DEFINE_HANDLE(MeshHandle); #define INVALID_MATERIAL_HANDLE ((MaterialHandle){ .raw = 9999992 }) #define INVALID_MESH_HANDLE ((MeshHandle){ .raw = 9999993 }) +typedef enum RenderMode { + RENDER_MODE_DEFAULT, + RENDER_MODE_WIREFRAME, + RENDER_MODE_WIREFRAME_ON_LIT, + RENDER_MODE_COUNT +} RenderMode; + typedef struct Geometry { VertexFormat format; Vertex_darray* vertices; diff --git a/src/ral/backends/opengl/backend_opengl.c b/src/ral/backends/opengl/backend_opengl.c index 305ab36..7929a16 100644 --- a/src/ral/backends/opengl/backend_opengl.c +++ b/src/ral/backends/opengl/backend_opengl.c @@ -57,8 +57,7 @@ bool GPU_Backend_Init(const char* window_name, struct GLFWwindow* window, } // All of these are no-ops in OpenGL -void GPU_Backend_Shutdown() { /* TODO */ -} +void GPU_Backend_Shutdown() { /* TODO */ } bool GPU_Device_Create(GPU_Device* out_device) { return true; } void GPU_Device_Destroy(GPU_Device* device) {} bool GPU_Swapchain_Create(GPU_Swapchain* out_swapchain) { return true; } diff --git a/src/resources/gltf.c b/src/resources/gltf.c index ef7569f..8b949ce 100644 --- a/src/resources/gltf.c +++ b/src/resources/gltf.c @@ -41,6 +41,8 @@ KITC_DECL_TYPED_ARRAY(face) bool model_load_gltf_str(const char *file_string, const char *filepath, Str8 relative_path, Model *out_model, bool invert_textures_y); +size_t GLTF_LoadMaterials(cgltf_data *data, Str8 relative_path, Material_darray *out_materials); + ModelHandle ModelLoad_gltf(const char *path, bool invert_texture_y) { size_t arena_size = MB(1); arena scratch = arena_create(malloc(arena_size), arena_size); @@ -55,8 +57,6 @@ ModelHandle ModelLoad_gltf(const char *path, bool invert_texture_y) { ModelHandle handle; Model *model = Model_pool_alloc(&g_core.models, &handle); model->name = Str8_cstr_view(path); - model->meshes = Mesh_darray_new(1); - model->materials = Material_darray_new(1); bool success = model_load_gltf_str(file_string, path, relative_path.path, model, invert_texture_y); @@ -132,6 +132,10 @@ bool model_load_gltf_str(const char *file_string, const char *filepath, Str8 rel Vec2_darray *tmp_uvs = Vec2_darray_new(1000); Vec4u_darray *tmp_joint_indices = Vec4u_darray_new(1000); Vec4_darray *tmp_weights = Vec4_darray_new(1000); + Material_darray *tmp_materials = Material_darray_new(1); + Mesh_darray *tmp_meshes = Mesh_darray_new(1); + u32_darray *tmp_material_indexes = u32_darray_new(1); + // FIXME // joint_darray *tmp_joints = joint_darray_new(256); // vertex_bone_data_darray *tmp_vertex_bone_data = vertex_bone_data_darray_new(1000); @@ -197,246 +201,182 @@ bool model_load_gltf_str(const char *file_string, const char *filepath, Str8 rel // } // --- Materials - size_t num_materials = data->materials_count; - TRACE("Num materials %d", num_materials); - for (size_t m = 0; m < num_materials; m++) { - cgltf_material gltf_material = data->materials[m]; - cgltf_pbr_metallic_roughness pbr = gltf_material.pbr_metallic_roughness; - - Material our_material = PBRMaterialDefault(); - - TRACE("Has PBR metallic roughness "); - // we will use base color texture like blinn phong - cgltf_texture_view albedo_tex_view = pbr.base_color_texture; // albedo - if (albedo_tex_view.texture != NULL) { - char albedo_map_path[1024]; - snprintf(albedo_map_path, sizeof(albedo_map_path), "%s/%s", relative_path.buf, - albedo_tex_view.texture->image->uri); - our_material.albedo_map = TextureLoadFromFile(albedo_map_path); - } else { - WARN("GLTF model has no albedo map"); - } - - cgltf_texture_view metal_rough_tex_view = pbr.metallic_roughness_texture; - if (metal_rough_tex_view.texture != NULL) { - char metal_rough_map_path[1024]; - snprintf(metal_rough_map_path, sizeof(metal_rough_map_path), "%s/%s", relative_path.buf, - metal_rough_tex_view.texture->image->uri); - our_material.metallic_roughness_map = TextureLoadFromFile(metal_rough_map_path); - } else { - WARN("GLTF model has no metal/roughness map"); - } + size_t num_materials = GLTF_LoadMaterials(data, relative_path, tmp_materials); - cgltf_texture_view normal_tex_view = gltf_material.normal_texture; - if (normal_tex_view.texture != NULL) { - char normal_map_path[1024]; - snprintf(normal_map_path, sizeof(normal_map_path), "%s/%s", relative_path.buf, - normal_tex_view.texture->image->uri); - our_material.normal_map = TextureLoadFromFile(normal_map_path); - } else { - WARN("GLTF model has no normal map"); - } + // --- Meshes + size_t num_meshes = data->meshes_count; + TRACE("Num meshes %d", num_meshes); + for (size_t m = 0; m < num_meshes; m++) { + printf("Primitive count %d\n", data->meshes[m].primitives_count); + for (size_t prim_i = 0; prim_i < data->meshes[m].primitives_count; prim_i++) { + DEBUG("Primitive %d\n", prim_i); - // TextureHandle albedo_map = TextureLoadFromFile(albedo_map_path); - // TextureHandle metal_roughness_map = TextureLoadFromFile(metal_rough_map_path); - // TextureHandle normal_map = TextureLoadFromFile(normal_map_path); + cgltf_primitive primitive = data->meshes[m].primitives[prim_i]; + DEBUG("Found %d attributes", primitive.attributes_count); - // Material our_material = { - // .kind = MAT_PBR, - // // .metal_roughness_combined = true, - // .albedo_map = albedo_map, - // .metallic_roughness_map = metal_roughness_map, - // .normal_map= normal_map, - // .ambient_occlusion_map = INVALID_TEX_HANDLE, + for (cgltf_size a = 0; a < primitive.attributes_count; a++) { + cgltf_attribute attribute = primitive.attributes[a]; + if (attribute.type == cgltf_attribute_type_position) { + cgltf_accessor *accessor = attribute.data; + load_position_components(tmp_positions, accessor); + } else if (attribute.type == cgltf_attribute_type_normal) { + cgltf_accessor *accessor = attribute.data; + load_normal_components(tmp_normals, accessor); + } else if (attribute.type == cgltf_attribute_type_texcoord) { + cgltf_accessor *accessor = attribute.data; + load_texcoord_components(tmp_uvs, accessor); + } else if (attribute.type == cgltf_attribute_type_joints) { + // FIXME: joints + // TRACE("Load joint indices from accessor"); + // cgltf_accessor *accessor = attribute.data; + // assert(accessor->component_type == cgltf_component_type_r_16u); + // assert(accessor->type == cgltf_type_vec4); + // vec4u joint_indices; + // vec4 joints_as_floats; + // for (cgltf_size v = 0; v < accessor->count; ++v) { + // cgltf_accessor_read_float(accessor, v, &joints_as_floats.x, 4); + // joint_indices.x = (u32)joints_as_floats.x; + // joint_indices.y = (u32)joints_as_floats.y; + // joint_indices.z = (u32)joints_as_floats.z; + // joint_indices.w = (u32)joints_as_floats.w; + // printf("Joints affecting vertex %d : %d %d %d %d\n", v, joint_indices.x, + // joint_indices.y, + // joint_indices.z, joint_indices.w); + // vec4u_darray_push(tmp_joint_indices, joint_indices); + // } + + } else if (attribute.type == cgltf_attribute_type_weights) { + // FIXME: weights + // TRACE("Load joint weights from accessor"); + // cgltf_accessor *accessor = attribute.data; + // assert(accessor->component_type == cgltf_component_type_r_32f); + // assert(accessor->type == cgltf_type_vec4); + + // for (cgltf_size v = 0; v < accessor->count; ++v) { + // vec4 weights; + // cgltf_accessor_read_float(accessor, v, &weights.x, 4); + // printf("Weights affecting vertex %d : %f %f %f %f\n", v, weights.x, weights.y, + // weights.z, + // weights.w); + // vec4_darray_push(tmp_weights, weights); + // } + } else { + WARN("Unhandled cgltf_attribute_type: %s. skipping..", attribute.name); + } + } + // mesh.vertex_bone_data = vertex_bone_data_darray_new(1); + i32 mat_idx = -1; + if (primitive.material != NULL) { + DEBUG("Primitive Material %s", primitive.material->name); + // FIXME! + for (u32 i = 0; i < Material_darray_len(tmp_materials); i++) { + printf("%s vs %s \n", primitive.material->name, tmp_materials->data[i].name); + if (strcmp(primitive.material->name, tmp_materials->data[i].name) == 0) { + INFO("Found material"); + mat_idx = i; + u32_darray_push(tmp_material_indexes, mat_idx); + break; + } + } + } - // }; + TRACE("Vertex data has been loaded"); + + // // FIXME + // // if (is_skinned) { + // // mesh.is_skinned = true; + // // // mesh.vertex_bone_data = vertex_bone_data_darray_new(tmp_joint_indices->len); + // // mesh.bones = joint_darray_new(tmp_joints->len); + // // for (int i = 0; i < tmp_joint_indices->len; i++) { + // // vertex_bone_data data; + // // data.joints = tmp_joint_indices->data[i]; + // // data.weights = tmp_weights->data[i]; + // // vertex_bone_data_darray_push(tmp_vertex_bone_data, + // // data); // Push the temp data that aligns with raw + // vertices + // // } + // // for (int i = 0; i < tmp_joints->len; i++) { + // // joint data = tmp_joints->data[i]; + // // joint_darray_push(mesh.bones, data); + // // } + // // } + + bool has_indices = false; + Vertex_darray *geo_vertices = Vertex_darray_new(3); + u32_darray *geo_indices = u32_darray_new(0); + + // Store vertices + printf("Positions %d Normals %d UVs %d\n", tmp_positions->len, tmp_normals->len, + tmp_uvs->len); + assert(tmp_positions->len == tmp_normals->len); + assert(tmp_normals->len == tmp_uvs->len); + for (u32 v_i = 0; v_i < tmp_positions->len; v_i++) { + Vertex v = { .static_3d = { + .position = tmp_positions->data[v_i], + .normal = tmp_normals->data[v_i], + .tex_coords = tmp_uvs->data[v_i], + } }; + Vertex_darray_push(geo_vertices, v); + } - // our_material.name = malloc(strlen(gltf_material.name) + 1); - u32 string_length = strlen(gltf_material.name) + 1; - assert(string_length < 64); - strcpy(our_material.name, gltf_material.name); + // Store indices + cgltf_accessor *indices = primitive.indices; + if (primitive.indices > 0) { + WARN("indices! %d", indices->count); + has_indices = true; - Material_darray_push(out_model->materials, our_material); - } + // store indices + for (cgltf_size i = 0; i < indices->count; ++i) { + cgltf_uint ei; + cgltf_accessor_read_uint(indices, i, &ei, 1); + u32_darray_push(geo_indices, ei); + } - // --- Meshes - size_t num_meshes = data->meshes_count; - TRACE("Num meshes %d", num_meshes); - for (size_t m = 0; m < num_meshes; m++) { - cgltf_primitive primitive = data->meshes[m].primitives[0]; - DEBUG("Found %d attributes", primitive.attributes_count); - - for (cgltf_size a = 0; a < data->meshes[m].primitives[0].attributes_count; a++) { - cgltf_attribute attribute = data->meshes[m].primitives[0].attributes[a]; - if (attribute.type == cgltf_attribute_type_position) { - cgltf_accessor *accessor = attribute.data; - load_position_components(tmp_positions, accessor); - } else if (attribute.type == cgltf_attribute_type_normal) { - cgltf_accessor *accessor = attribute.data; - load_normal_components(tmp_normals, accessor); - } else if (attribute.type == cgltf_attribute_type_texcoord) { - cgltf_accessor *accessor = attribute.data; - load_texcoord_components(tmp_uvs, accessor); - } else if (attribute.type == cgltf_attribute_type_joints) { - // FIXME: joints - // TRACE("Load joint indices from accessor"); - // cgltf_accessor *accessor = attribute.data; - // assert(accessor->component_type == cgltf_component_type_r_16u); - // assert(accessor->type == cgltf_type_vec4); - // vec4u joint_indices; - // vec4 joints_as_floats; - // for (cgltf_size v = 0; v < accessor->count; ++v) { - // cgltf_accessor_read_float(accessor, v, &joints_as_floats.x, 4); - // joint_indices.x = (u32)joints_as_floats.x; - // joint_indices.y = (u32)joints_as_floats.y; - // joint_indices.z = (u32)joints_as_floats.z; - // joint_indices.w = (u32)joints_as_floats.w; - // printf("Joints affecting vertex %d : %d %d %d %d\n", v, joint_indices.x, - // joint_indices.y, - // joint_indices.z, joint_indices.w); - // vec4u_darray_push(tmp_joint_indices, joint_indices); + // fetch and store vertices for each index + // for (cgltf_size i = 0; i < indices->count; ++i) { + // Vertex vert; + // cgltf_uint index = mesh.indices[i]; + // vert.position = tmp_positions->data[index]; + // vert.normal = tmp_normals->data[index]; + // vert.uv = tmp_uvs->data[index]; + // vertex_darray_push(mesh.vertices, vert); + + // if (is_skinned) { + // vertex_bone_data vbd = tmp_vertex_bone_data->data[index]; // create a copy + // vertex_bone_data_darray_push(mesh.vertex_bone_data, vbd); // } - - } else if (attribute.type == cgltf_attribute_type_weights) { - // FIXME: weights - // TRACE("Load joint weights from accessor"); - // cgltf_accessor *accessor = attribute.data; - // assert(accessor->component_type == cgltf_component_type_r_32f); - // assert(accessor->type == cgltf_type_vec4); - - // for (cgltf_size v = 0; v < accessor->count; ++v) { - // vec4 weights; - // cgltf_accessor_read_float(accessor, v, &weights.x, 4); - // printf("Weights affecting vertex %d : %f %f %f %f\n", v, weights.x, weights.y, - // weights.z, - // weights.w); - // vec4_darray_push(tmp_weights, weights); + // for each vertex do the bone data + // } + // } else { + // has_indices = false; + // return false; // TODO: handle this // } - } else { - WARN("Unhandled cgltf_attribute_type: %s. skipping..", attribute.name); - } - } - // mesh.vertex_bone_data = vertex_bone_data_darray_new(1); - i32 mat_idx = -1; - if (primitive.material != NULL) { - DEBUG("Primitive Material %s", primitive.material->name); - // FIXME! - // for (u32 i = 0; i < Material_darray_len(out_model->materials); i++) { - // printf("%s vs %s \n", primitive.material->name, out_model->materials->data[i].name); - // if (strcmp(primitive.material->name, out_model->materials->data[i].name) == 0) { - // INFO("Found material"); - // mat_idx = i; - // // mesh.material_index = i; - // break; - // } - // } - } - - TRACE("Vertex data has been loaded"); - - // // FIXME - // // if (is_skinned) { - // // mesh.is_skinned = true; - // // // mesh.vertex_bone_data = vertex_bone_data_darray_new(tmp_joint_indices->len); - // // mesh.bones = joint_darray_new(tmp_joints->len); - // // for (int i = 0; i < tmp_joint_indices->len; i++) { - // // vertex_bone_data data; - // // data.joints = tmp_joint_indices->data[i]; - // // data.weights = tmp_weights->data[i]; - // // vertex_bone_data_darray_push(tmp_vertex_bone_data, - // // data); // Push the temp data that aligns with raw - // vertices - // // } - // // for (int i = 0; i < tmp_joints->len; i++) { - // // joint data = tmp_joints->data[i]; - // // joint_darray_push(mesh.bones, data); - // // } - // // } - - bool has_indices = false; - Vertex_darray *geo_vertices = Vertex_darray_new(3); - u32_darray *geo_indices = u32_darray_new(0); - - // Store vertices - printf("Positions %d Normals %d UVs %d\n", tmp_positions->len, tmp_normals->len, tmp_uvs->len); - assert(tmp_positions->len == tmp_normals->len); - assert(tmp_normals->len == tmp_uvs->len); - for (u32 v_i = 0; v_i < tmp_positions->len; v_i++) { - Vertex v = { .static_3d = { - .position = tmp_positions->data[v_i], - .normal = tmp_normals->data[v_i], - .tex_coords = tmp_uvs->data[v_i], - } }; - Vertex_darray_push(geo_vertices, v); - } - // Store indices - cgltf_accessor *indices = primitive.indices; - if (primitive.indices > 0) { - WARN("indices! %d", indices->count); - has_indices = true; - - // store indices - for (cgltf_size i = 0; i < indices->count; ++i) { - cgltf_uint ei; - cgltf_accessor_read_uint(indices, i, &ei, 1); - u32_darray_push(geo_indices, ei); + Geometry *geometry = malloc(sizeof(Geometry)); + geometry->format = VERTEX_STATIC_3D; + geometry->has_indices = true; + geometry->vertices = geo_vertices; + geometry->indices = geo_indices; + geometry->index_count = geo_indices->len; + + Mesh m = Mesh_Create(geometry, false); + Mesh_darray_push(tmp_meshes, m); + + Vec3_darray_clear(tmp_positions); + Vec3_darray_clear(tmp_normals); + Vec2_darray_clear(tmp_uvs); + Vec4u_darray_clear(tmp_joint_indices); + Vec4_darray_clear(tmp_weights); } - - // fetch and store vertices for each index - // for (cgltf_size i = 0; i < indices->count; ++i) { - // Vertex vert; - // cgltf_uint index = mesh.indices[i]; - // vert.position = tmp_positions->data[index]; - // vert.normal = tmp_normals->data[index]; - // vert.uv = tmp_uvs->data[index]; - // vertex_darray_push(mesh.vertices, vert); - - // if (is_skinned) { - // vertex_bone_data vbd = tmp_vertex_bone_data->data[index]; // create a copy - // vertex_bone_data_darray_push(mesh.vertex_bone_data, vbd); - // } - // for each vertex do the bone data - // } - // } else { - // has_indices = false; - // return false; // TODO: handle this - // } - - Geometry *geometry = malloc(sizeof(Geometry)); - geometry->format = VERTEX_STATIC_3D; - geometry->has_indices = true; - geometry->vertices = geo_vertices; - geometry->indices = geo_indices; - // geometry->format = VERTEX_STATIC_3D; - // geometry->colour = (rgba){ 1, 1, 1, 1 }; - // geometry->vertices = geo_vertices; - // geometry->indices = geo_indices; - // geometry->has_indices = has_indices; - - // mesh m = mesh_create(geometry, true); - // m.material_index = (u32_opt){ .has_value = mat_idx == 9999, .value = mat_idx }; - - Mesh m = Mesh_Create(geometry, false); - // m.material_index = mat_idx; FIXME - Mesh_darray_push(out_model->meshes, m); } - // // clear data for each mesh - // vec3_darray_clear(tmp_positions); - // vec3_darray_clear(tmp_normals); - // vec2_darray_free(tmp_uvs); - // vec4u_darray_clear(tmp_joint_indices); - // vec4_darray_clear(tmp_weights); - // joint_darray_clear(tmp_joints); - // } - // for (int i = 0; i < out_model->meshes->len; i++) { // u32 mat_idx = out_model->meshes->data[i].material_index; // printf("Mesh %d Mat index %d Mat name %s\n", i, mat_idx, // out_model->materials->data[mat_idx].name); // } + // TODO: GLTF_LoadAnimations() // // Animations // TRACE("Num animations %d", data->animations_count); // size_t num_animations = data->animations_count; @@ -557,9 +497,99 @@ bool model_load_gltf_str(const char *file_string, const char *filepath, Str8 rel // } } + num_meshes = tmp_meshes->len; + + // we now have an array of meshes, materials, and the material which each mesh should get + out_model->meshes = malloc(num_meshes * sizeof(MeshHandle)); + out_model->mesh_count = num_meshes; + out_model->materials = malloc(num_materials * sizeof(MaterialHandle)); + out_model->material_count = num_materials; + + MaterialHandle *mat_handles = calloc(num_materials, sizeof(MaterialHandle)); + for (u32 mat_i = 0; mat_i < num_materials; mat_i++) { + mat_handles[mat_i] = + Material_pool_insert(Render_GetMaterialPool(), &tmp_materials->data[mat_i]); + } + memcpy(out_model->materials, mat_handles, num_materials * sizeof(MaterialHandle)); + + for (u32 mesh_i = 0; mesh_i < num_meshes; mesh_i++) { + u32 mat_idx = tmp_material_indexes->data[mesh_i]; + tmp_meshes->data[mesh_i].material = mat_handles[mat_idx]; + MeshHandle mesh = Mesh_pool_insert(Render_GetMeshPool(), &tmp_meshes->data[mesh_i]); + out_model->meshes[mesh_i] = mesh; + } + + free(mat_handles); + return true; } +const char *bool_yes_no(bool pred) { return pred ? "Yes" : "No"; } + +// Loads all materials +size_t GLTF_LoadMaterials(cgltf_data *data, Str8 relative_path, Material_darray *out_materials) { + size_t num_materials = data->materials_count; + TRACE("Num materials %d", num_materials); + for (size_t m = 0; m < num_materials; m++) { + cgltf_material gltf_material = data->materials[m]; + TRACE("Loading material '%s'", gltf_material.name); + cgltf_pbr_metallic_roughness pbr = gltf_material.pbr_metallic_roughness; + + Material our_material = PBRMaterialDefault(); // focusing on PBR materials for now + + our_material.base_colour = + vec3(pbr.base_color_factor[0], pbr.base_color_factor[1], pbr.base_color_factor[2]); + our_material.metallic = pbr.metallic_factor; + our_material.roughness = pbr.roughness_factor; + + // -- albedo / base colour + cgltf_texture_view albedo_tex_view = pbr.base_color_texture; + bool has_albedo_texture = albedo_tex_view.texture != NULL; + TRACE("Has PBR base colour texture? %s", bool_yes_no(has_albedo_texture)); + printf("Base colour factor: %f %f %f\n", pbr.base_color_factor[0], pbr.base_color_factor[1], + pbr.base_color_factor[2]); + if (has_albedo_texture) { + char albedo_map_path[1024]; + snprintf(albedo_map_path, sizeof(albedo_map_path), "%s/%s", relative_path.buf, + albedo_tex_view.texture->image->uri); + our_material.albedo_map = TextureLoadFromFile(albedo_map_path); + } else { + our_material.albedo_map = Render_GetWhiteTexture(); + WARN("GLTF model has no albedo map"); + } + + // -- metallic + cgltf_texture_view metal_rough_tex_view = pbr.metallic_roughness_texture; + // bool has_metal_ + if (metal_rough_tex_view.texture != NULL) { + char metal_rough_map_path[1024]; + snprintf(metal_rough_map_path, sizeof(metal_rough_map_path), "%s/%s", relative_path.buf, + metal_rough_tex_view.texture->image->uri); + our_material.metallic_roughness_map = TextureLoadFromFile(metal_rough_map_path); + } else { + WARN("GLTF model has no metal/roughness map"); + } + + cgltf_texture_view normal_tex_view = gltf_material.normal_texture; + if (normal_tex_view.texture != NULL) { + char normal_map_path[1024]; + snprintf(normal_map_path, sizeof(normal_map_path), "%s/%s", relative_path.buf, + normal_tex_view.texture->image->uri); + our_material.normal_map = TextureLoadFromFile(normal_map_path); + } else { + WARN("GLTF model has no normal map"); + } + + u32 string_length = strlen(gltf_material.name) + 1; + assert(string_length < 64); + strcpy(our_material.name, gltf_material.name); + + Material_darray_push(out_materials, our_material); + } + + return out_materials->len; +} + /* bool model_load_gltf(const char *path, model *out_model) { TRACE("Load GLTF %s", path); diff --git a/src/systems/input.h b/src/systems/input.h index bf80a84..2665a11 100644 --- a/src/systems/input.h +++ b/src/systems/input.h @@ -32,22 +32,22 @@ typedef struct Input_State { } Input_State; /** @brief `key` is currently being held down */ -bool key_is_pressed(keycode key); +PUB bool key_is_pressed(keycode key); /** @brief `key` was just pressed */ -bool key_just_pressed(keycode key); +PUB bool key_just_pressed(keycode key); /** @brief `key` was just released */ -bool key_just_released(keycode key); +PUB bool key_just_released(keycode key); // TODO: right btn as well -bool MouseBtn_Held(MouseBtn btn); +PUB bool MouseBtn_Held(MouseBtn btn); // --- Lifecycle -bool Input_Init(Input_State *input, struct GLFWwindow *window); -void Input_Shutdown(Input_State *input); +PUB bool Input_Init(Input_State *input, struct GLFWwindow *window); +PUB void Input_Shutdown(Input_State *input); -void Input_Update(Input_State *state); // must be run once per main loop +PUB void Input_Update(Input_State *state); // must be run once per main loop PUB mouse_state Input_GetMouseState();
\ No newline at end of file diff --git a/src/systems/terrain.h b/src/systems/terrain.h index 4399e6b..5a96132 100644 --- a/src/systems/terrain.h +++ b/src/systems/terrain.h @@ -13,8 +13,6 @@ Future: #include "defines.h" #include "maths_types.h" -#include "mem.h" -#include "ral.h" #include "ral_types.h" #include "render.h" #include "str.h" @@ -57,16 +55,12 @@ PUB Heightmap Heightmap_FromPerlin(/* TODO: perlin noise generation parameters * PUB bool Terrain_IsActive(); // checks whether we have a loaded heightmap and it's being rendered -// --- Internal - -// TODO: void terrain_system_render_hmap(renderer* rend, terrain_state* state); - /** @brief Get the height (the Y component) for a vertex at a particular coordinate in the heightmap */ -f32 Heightmap_HeightXZ(const Heightmap* hmap, u32 x, u32 z); +PUB f32 Heightmap_HeightXZ(const Heightmap* hmap, u32 x, u32 z); /** @brief Calculate the normal vector of a vertex at a particular coordinate in the heightmap */ -Vec3 Heightmap_NormalXZ(const Heightmap* hmap, f32 x, f32 z); +PUB Vec3 Heightmap_NormalXZ(const Heightmap* hmap, f32 x, f32 z); // /** @brief Generate the `geometry_data` for a heightmap ready to be uploaded to the GPU */ // Geometry geo_heightmap(arena* a, Heightmap heightmap); |