diff --git a/examples/simple_mesh/main.cpp b/examples/simple_mesh/main.cpp index 8b3fa43..343cbc4 100644 --- a/examples/simple_mesh/main.cpp +++ b/examples/simple_mesh/main.cpp @@ -16,6 +16,25 @@ doFrameCallback(render_state* rs) entRotate(e, angle, axis); } +simple_mesh* +makeSquareMesh() +{ + uint num_vertices = 4; + simple_mesh* sm = meInitMesh(num_vertices); + sm->num_vertices = num_vertices; + + sm->vertices[0] = glm::vec3(-200, 0, 200); + sm->vertices[1] = glm::vec3(-200, 0, -200); + sm->vertices[2] = glm::vec3(200, 0, -200); + sm->vertices[3] = glm::vec3(200, 0, 200); + sm->vert_colors[0] = glm::vec3(255, 0, 0); + sm->vert_colors[1] = glm::vec3(255, 0, 0); + sm->vert_colors[2] = glm::vec3(255, 0, 0); + sm->vert_colors[3] = glm::vec3(255, 0, 0); + + return sm; +} + int main() { @@ -32,23 +51,12 @@ main() rs->render_group_count = 1; entity& e = rs->render_groups[0].entities[0]; - // manually construct a simple mesh - simple_mesh mesh = { glm::mat4(1), 0, 0, 0 }; - mesh.num_vertices = 4; - mesh.vertices = UTIL_ALLOC(mesh.num_vertices, glm::vec3); - mesh.vertices[0] = glm::vec3(-200, 0, 200); - mesh.vertices[1] = glm::vec3(-200, 0, -200); - mesh.vertices[2] = glm::vec3(200, 0, -200); - mesh.vertices[3] = glm::vec3(200, 0, 200); - mesh.vert_colors = UTIL_ALLOC(mesh.num_vertices, glm::vec3); - mesh.vert_colors[0] = glm::vec3(255, 0, 0); - mesh.vert_colors[1] = glm::vec3(255, 0, 0); - mesh.vert_colors[2] = glm::vec3(255, 0, 0); - mesh.vert_colors[3] = glm::vec3(255, 0, 0); - //initialize entity with new mesh - entInitSimpleMesh(e, mesh, GL_LINE_LOOP); - utilSafeFree(mesh.vertices); - utilSafeFree(mesh.vert_colors); + simple_mesh* sm = makeSquareMesh(); + + // TODO: better usage would be: renPushEntity(rs->render_groups[0], e); + // would need to allocate a reasonable block size by default (~64), and + // double it if pushing to render_group would overflow + entInitMesh(e, sm, GL_LINE_LOOP); cameraInitPerspective( rs->cam, diff --git a/include/entity.h b/include/entity.h index 121521f..08d76cb 100644 --- a/include/entity.h +++ b/include/entity.h @@ -14,11 +14,13 @@ // level functions based on the mesh_type property struct entity { +#if 0 mesh_t mesh_type; - - simple_mesh mesh; simple_render_object* simple_ro; GLenum draw_mode; +#endif + + simple_mesh* mesh; // TODO: should be a pointer into a global array of mesh_info(s) or // mesh_groups stored on the render_state object @@ -28,7 +30,7 @@ struct entity bool entInitModel(entity& e, const char* model_path); -bool entInitSimpleMesh(entity& e, simple_mesh& mesh, GLenum draw_mode); +bool entInitMesh(entity& e, simple_mesh* mesh, GLenum draw_mode); void entFree(entity& e); diff --git a/include/mesh.h b/include/mesh.h index f0af702..72cc7bf 100644 --- a/include/mesh.h +++ b/include/mesh.h @@ -37,21 +37,29 @@ struct mesh_group struct simple_mesh { glm::mat4 model_transform; + uint num_vertices; glm::vec3* vertices; glm::vec3* vert_colors; - uint num_vertices; }; -bool meInitAssimp(); +bool +meInitAssimp(); // NOTE: meshes loaded from assimp require texture coordinates, and a diffuse // texture, which can be a seperate file, or embedded in the input file -bool meLoadFromFile(mesh_group& mesh_group, const char* filepath); +bool +meLoadFromFile(mesh_group& mesh_group, const char* filepath); + +simple_mesh* +meInitMesh(uint num_vertices); -void meFreeMeshGroup(mesh_group& mesh_group); +void +meFreeMeshGroup(mesh_group& mesh_group); -void meFreeSimpleMesh(simple_mesh& mesh); +void +meFreeSimpleMesh(simple_mesh& mesh); -void meShutdownAssimp(); +void +meShutdownAssimp(); diff --git a/include/render_object.h b/include/render_object.h index 8c0d7f5..e61c53c 100644 --- a/include/render_object.h +++ b/include/render_object.h @@ -11,19 +11,16 @@ struct render_objects; -struct simple_render_object; +//struct simple_render_object; render_objects* roInitModel(mesh_group meshes); -void -roFree(render_objects* r_objs); - -simple_render_object* -roInitSimpleMesh(simple_mesh& mesh_in); +render_objects* +roInitSimpleMesh(simple_mesh& mesh_in, GLenum draw_mode); void -roFreeSimple(simple_render_object* ro); +roFree(render_objects* r_objs); void roTranslate(render_objects* r_objs, glm::mat4 xform); @@ -43,9 +40,11 @@ roDraw(render_objects* r_ojbs, shader_wrapper sw, light_group* lights); +#if 0 void roDrawSimple(simple_render_object* ro, camera& cam, simple_shader_program& shader, GLenum draw_mode); +#endif diff --git a/src/entity.cpp b/src/entity.cpp index 5ad39db..25e4aeb 100644 --- a/src/entity.cpp +++ b/src/entity.cpp @@ -11,8 +11,6 @@ // forward declarations void initDefaults(entity& e); -bool loadMeshesIntoGL(entity& e); -bool loadSimpleMeshIntoGL(entity& e); // interface @@ -21,7 +19,6 @@ bool entInitModel(entity& e, const char* model_path) { initDefaults(e); - e.mesh_type = DEFAULT_MESHES; if (meLoadFromFile(e.meshes, model_path)) { @@ -36,28 +33,18 @@ entInitModel(entity& e, const char* model_path) } bool -entInitSimpleMesh(entity& e, simple_mesh& mesh, GLenum draw_mode) +entInitMesh(entity& e, simple_mesh* mesh, GLenum draw_mode) { - assert(mesh.num_vertices > 0); + // TODO: test that this doesn't really do anything, then remove, and in + // entInitModel initDefaults(e); - e.mesh_type = SIMPLE_MESH; - e.draw_mode = draw_mode; + e.mesh = mesh; + e.render_objs = roInitSimpleMesh(*e.mesh, draw_mode); - e.mesh.model_transform = mesh.model_transform; - e.mesh.num_vertices = mesh.num_vertices; - e.mesh.vertices = UTIL_ALLOC(mesh.num_vertices, glm::vec3); - e.mesh.vert_colors = UTIL_ALLOC(mesh.num_vertices, glm::vec3); - - for (uint i = 0; i < mesh.num_vertices; i++) { - e.mesh.vertices[i] = mesh.vertices[i]; - e.mesh.vert_colors[i] = mesh.vert_colors[i]; - } - - if (loadSimpleMeshIntoGL(e)) - return true; + if (e.render_objs == nullptr) + return false; - entFree(e); - return false; + return true; } void @@ -74,7 +61,6 @@ entSetWorldPosition(entity& e, glm::vec3 v) e.world_transform[3][0] = v.x; e.world_transform[3][1] = v.y; e.world_transform[3][2] = v.z; -#endif if (e.mesh_type == SIMPLE_MESH) { // } @@ -82,6 +68,7 @@ entSetWorldPosition(entity& e, glm::vec3 v) if (e.mesh_type == DEFAULT_MESHES) { // } +#endif } void @@ -89,7 +76,6 @@ entTranslate(entity& e, glm::vec3 v) { #if 0 e.world_transform = glm::translate(e.world_transform, v); -#endif if (e.mesh_type == SIMPLE_MESH) { // } @@ -97,6 +83,7 @@ entTranslate(entity& e, glm::vec3 v) if (e.mesh_type == DEFAULT_MESHES) { // } +#endif } void @@ -148,17 +135,3 @@ initDefaults(entity& e) entSetWorldPosition(e, glm::vec3(0, 0, 0)); } -bool -loadSimpleMeshIntoGL(entity& e) -{ - assert(e.mesh.num_vertices > 0); - e.simple_ro = roInitSimpleMesh(e.mesh); - - if (e.simple_ro == nullptr) { - LOG(Error) << "Error initializing render object\n"; - entFree(e); - return false; - } - - return true; -} diff --git a/src/mesh.cpp b/src/mesh.cpp index 2b3bf30..b51c96a 100644 --- a/src/mesh.cpp +++ b/src/mesh.cpp @@ -14,6 +14,7 @@ // forward declarations +// mesh_info* allocateMeshInfo(uint num_vertices, uint num_indices); void assimpLogCB(const char* message, char* user); mesh_info* copyMeshInfo(const aiScene* scene, aiMesh* mesh); @@ -67,6 +68,18 @@ meLoadFromFile(mesh_group& mesh_group, const char* filepath) return true; } +simple_mesh* +meInitMesh(uint num_vertices) +{ + assert(num_vertices > 0); + simple_mesh* sm = UTIL_ALLOC(1, simple_mesh); + sm->model_transform = glm::mat4(1.0); + sm->num_vertices = num_vertices; + sm->vertices = UTIL_ALLOC(num_vertices, glm::vec3); + sm->vert_colors = UTIL_ALLOC(num_vertices, glm::vec3); + return sm; +} + void meFreeMeshGroup(mesh_group& mesh_group) { diff --git a/src/render_object.cpp b/src/render_object.cpp index d06e590..6ee6f51 100644 --- a/src/render_object.cpp +++ b/src/render_object.cpp @@ -25,6 +25,7 @@ struct simple_render_object GLuint vertex_buffer_id; GLuint vertex_color_buffer_id; uint vertex_count; + GLenum draw_mode; }; struct render_objects @@ -42,6 +43,7 @@ void drawDefault(render_objects* r_objs, camera& cam, shader_wrapper sw, light_group* lights); +inline void enableGLFloatBuffer(uint buffer_id, uint location); bool initGLFloatBuffer(glm::vec3* buffer, uint count, GLuint& buffer_id); bool initGLIndexBuffer(uint* buffer, uint num_indices, GLuint& buffer_id); bool initGLTexture(const util_image image, GLuint& tex_id); @@ -49,7 +51,6 @@ bool loadMeshIntoGL(default_render_object* ro_out, mesh_info* mi_in); inline void updateMatrices(default_shader_program* shader, camera& cam, glm::mat4 node_xform); -inline void enableGLFloatBuffer(uint buffer_id, uint location); // interface @@ -77,6 +78,34 @@ roInitModel(mesh_group mg) return r_objs; } +render_objects* +roInitSimpleMesh(simple_mesh& mesh_in, GLenum draw_mode) +{ + render_objects* r_objs = UTIL_ALLOC(1, render_objects); + r_objs->count = 1; + r_objs->mesh_type = SIMPLE_MESH; + r_objs->objects = UTIL_ALLOC(1, simple_render_object); + + simple_render_object* objects = (simple_render_object*) r_objs->objects; + + if (initGLFloatBuffer(mesh_in.vertices, + mesh_in.num_vertices, + objects->vertex_buffer_id) && + initGLFloatBuffer(mesh_in.vert_colors, + mesh_in.num_vertices, + objects->vertex_color_buffer_id)) + { + objects->model_transform = mesh_in.model_transform; + objects->vertex_count = mesh_in.num_vertices; + objects->draw_mode = draw_mode; + return r_objs; + } + + LOG(Error) << "Failed to initialize render_object\n"; + roFree(r_objs); + return nullptr; +} + void roFree(render_objects* r_objs) { @@ -99,37 +128,6 @@ roFree(render_objects* r_objs) } } -simple_render_object* -roInitSimpleMesh(simple_mesh& mesh_in) -{ - // TODO: switch on mesh type here - simple_render_object* ro_out = UTIL_ALLOC(1, simple_render_object); - - if (initGLFloatBuffer(mesh_in.vertices, - mesh_in.num_vertices, - ro_out->vertex_buffer_id) && - initGLFloatBuffer(mesh_in.vert_colors, - mesh_in.num_vertices, - ro_out->vertex_color_buffer_id)) - { - ro_out->model_transform = mesh_in.model_transform; - ro_out->vertex_count = mesh_in.num_vertices; - return ro_out; - } - - LOG(Error) << "Failed to initialize render_object\n"; - roFreeSimple(ro_out); - return nullptr; -} - -void -roFreeSimple(simple_render_object* ro) -{ - glDeleteBuffers(1, &ro->vertex_buffer_id); - glDeleteBuffers(1, &ro->vertex_color_buffer_id); - utilSafeFree(ro); -} - void roTranslate(render_objects* r_objs, glm::mat4 xform) { @@ -167,23 +165,6 @@ roDraw(render_objects* r_objs, } } -void -roDrawSimple(simple_render_object* ro, - camera& cam, - simple_shader_program& shader, - GLenum draw_mode) -{ - glUseProgram(shader.program_id); - cam.MVP = cam.projection * cam.view * ro->model_transform; - glUniformMatrix4fv(shader.MVP_id, 1, GL_FALSE, &cam.MVP[0][0]); - enableGLFloatBuffer(ro->vertex_buffer_id, 0); - enableGLFloatBuffer(ro->vertex_color_buffer_id, 1); - glDrawArrays(draw_mode, 0, ro->vertex_count); - glDisableVertexAttribArray(0); - glDisableVertexAttribArray(1); - glUseProgram(0); -} - // internal @@ -193,7 +174,18 @@ drawSimple(render_objects* r_objs, shader_wrapper sw, light_group* lights) { - + simple_render_object* ro = (simple_render_object*) r_objs->objects; + simple_shader_program* shader = + (simple_shader_program*) sw.simple_shader; + glUseProgram(shader->program_id); + cam.MVP = cam.projection * cam.view * ro->model_transform; + glUniformMatrix4fv(shader->MVP_id, 1, GL_FALSE, &cam.MVP[0][0]); + enableGLFloatBuffer(ro->vertex_buffer_id, 0); + enableGLFloatBuffer(ro->vertex_color_buffer_id, 1); + glDrawArrays(ro->draw_mode, 0, ro->vertex_count); + glDisableVertexAttribArray(0); + glDisableVertexAttribArray(1); + glUseProgram(0); } void diff --git a/src/renderer.cpp b/src/renderer.cpp index d74c538..eeaccd3 100644 --- a/src/renderer.cpp +++ b/src/renderer.cpp @@ -142,38 +142,11 @@ renRenderFrame(render_state* rs) for (uint i = 0; i < rs->render_group_count; i++) { render_group& rg = rs->render_groups[i]; - if (rg.shader.shader_type == SIMPLE_SHADER) { - for (uint j = 0; j < rg.entity_count; j++) { - entity& e = rg.entities[j]; - - roDrawSimple(e.simple_ro, - rs->cam, - *rg.shader.simple_shader, - e.draw_mode); - } - } - -#if 0 - if (rg.shader.shader_type == DEFAULT_SHADER) { - for (uint j = 0; j < rg.entity_count; j++) { - entity& e = rg.entities[j]; - - for (uint k = 0; k < e.ro_count; k++) { - roDraw(e.render_objs[k], - rs->cam, - *rg.shader.default_shader, - rs->lights); - } - } - } -#endif - if (rg.shader.shader_type == DEFAULT_SHADER) { - for (uint j = 0; j < rg.entity_count; j++) { - roDraw(rg.entities[j].render_objs, - rs->cam, - rg.shader, - rs->lights); - } + for (uint j = 0; j < rg.entity_count; j++) { + roDraw(rg.entities[j].render_objs, + rs->cam, + rg.shader, + rs->lights); } } }