Stats::Stats(int viewport_width, int viewport_height) : texture_atlas(0) , texture_font(0) , vertex_count(0) , position_vbo(0) , texcoord_vbo(0) , vao(0) , sampler(0) , text_vs(0) , text_fs(0) , text_program(0) , uniform_instance_buffer(0) { texture_atlas = texture_atlas_new(512, 512, 1); texture_font = texture_font_new_from_file(texture_atlas, 11, (DIRECTORY_FONTS + FILE_DEFAULT_FONT).c_str()); texture_font_load_glyphs(texture_font, FONT_CHARSET_CACHE); // Create a sampler object for the font. glGenSamplers(1, &sampler); glSamplerParameteri(sampler, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glSamplerParameteri(sampler, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glSamplerParameteri(sampler, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glSamplerParameteri(sampler, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); // Load the shader program. text_vs = compile_shader_from_file(DIRECTORY_SHADERS + FILE_TEXT_VS, GL_VERTEX_SHADER); text_fs = compile_shader_from_file(DIRECTORY_SHADERS + FILE_TEXT_FS, GL_FRAGMENT_SHADER); text_program = glCreateProgram(); glAttachShader(text_program, text_vs); glAttachShader(text_program, text_fs); link_program(text_program); // Setup a scale matrix to go from screen space to normalized device space. glm::mat3 scale(2.0f / viewport_width, 0.0f, 0.0f, 0.0f, 2.0f / viewport_height, 0.0f, 0.0f, 0.0f, 1.0f); glm::mat3 translation(1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, MARGIN_X, MARGIN_Y, 1.0f); uniform_instance_data.model_matrix = glm::mat3x4(translation * scale); uniform_instance_data.color = glm::vec4(1.0f, 1.0f, 0.0f, 1.0f); glGenBuffers(1, &uniform_instance_buffer); glBindBufferBase(GL_UNIFORM_BUFFER, UNIFORM_INSTANCE_BINDING, uniform_instance_buffer); glBufferData(GL_UNIFORM_BUFFER, sizeof(TextPerInstance), &uniform_instance_data, GL_DYNAMIC_DRAW); }
/** * edges using geometry shader. */ int build_triangle_edges(lulog *log, GLuint *program) { int status = LU_OK; luary_uint32 *shaders = NULL; try(compile_shader_from_file(log, GL_VERTEX_SHADER, "flat_model_g.vert", &shaders)); try(compile_shader_from_file(log, GL_GEOMETRY_SHADER, "edge_lines.geom", &shaders)); try(compile_shader_from_file(log, GL_FRAGMENT_SHADER, "direct_colour.frag", &shaders)); try(link_program(log, shaders, program)); finally: status = free_shaders(log, &shaders, status); return status; } /** * copy a frame by rendering a texture directly (needs a quad to select the area). */ int build_direct_texture(lulog *log, direct_texture *program) { int status = LU_OK; luary_uint32 *shaders = NULL; try(compile_shader_from_file(log, GL_VERTEX_SHADER, "direct_texture.vert", &shaders)); try(compile_shader_from_file(log, GL_FRAGMENT_SHADER, "direct_texture.frag", &shaders)); try(link_program(log, shaders, &program->name)); try(set_uniform(log, program->name, "frame", &program->frame, 0)); finally: status = free_shaders(log, &shaders, status); return status; } /** * merge two frames via textures. */ int build_merge_frames(lulog *log, merge_frames *program) { int status = LU_OK; luary_uint32 *shaders = NULL; try(compile_shader_from_file(log, GL_VERTEX_SHADER, "direct_texture.vert", &shaders)); try(compile_shader_from_file(log, GL_FRAGMENT_SHADER, "merge_frames.frag", &shaders)); try(link_program(log, shaders, &program->name)); try(set_uniform(log, program->name, "frame1", &program->frame1, 0)); try(set_uniform(log, program->name, "frame2", &program->frame2, 1)); finally: status = free_shaders(log, &shaders, status); return status; } /** * blur a frame (roughly uniform over 5 pixels radius). */ int build_blur(lulog *log, blur *program) { int status = LU_OK; luary_uint32 *shaders = NULL; try(compile_shader_from_file(log, GL_VERTEX_SHADER, "direct_texture.vert", &shaders)); try(compile_shader_from_file(log, GL_FRAGMENT_SHADER, "blur.frag", &shaders)); try(link_program(log, shaders, &program->name)); try(set_uniform(log, program->name, "frame", &program->frame, 0)); try(set_uniform(log, program->name, "horizontal", &program->horizontal, 1)); finally: status = free_shaders(log, &shaders, status); return status; } int draw_triangle_edges(lulog *log, model *model, programs *programs) { int status = LU_OK; gl_try(glBindVertexArray(model->vao)); // gl_try(glPolygonMode(GL_FRONT_AND_BACK, GL_LINE)); gl_try(glUseProgram(programs->triangle_edges)); gl_try(glMultiDrawArrays(GL_TRIANGLE_STRIP, model->offsets->i, model->counts->i, model->counts->mem.used)); // gl_try(glPolygonMode(GL_FRONT_AND_BACK, GL_FILL)); finally: GL_CLEAN(glBindVertexArray(0)) GL_CLEAN(glUseProgram(0)) return status; }
GLuint compile_shader(std::string source, GLuint type) { return compile_shader_from_file("internal", source, type); }