From e2e7c0bf0747d55967c4be6374f3611cd96babb6 Mon Sep 17 00:00:00 2001 From: dec05eba Date: Fri, 5 Nov 2021 21:38:20 +0100 Subject: Add bounds calculation to text --- src/gl.c | 3 ++- src/graphics/image.c | 6 +++++- src/graphics/shader.c | 17 +++++++++++++++- src/graphics/text.c | 55 +++++++++++++++++++++++++++++++++++++++++++++++---- 4 files changed, 74 insertions(+), 7 deletions(-) (limited to 'src') diff --git a/src/gl.c b/src/gl.c index efcfbd4..966023a 100644 --- a/src/gl.c +++ b/src/gl.c @@ -80,7 +80,8 @@ int mgl_gl_load(mgl_gl *self) { { &self->glUseProgram, "glUseProgram" }, { &self->glAttachShader, "glAttachShader" }, { &self->glGetUniformLocation, "glGetUniformLocation" }, - { &self->glUniform2fv, "glUniform2fv" }, + { &self->glUniform1f, "glUniform1f" }, + { &self->glUniform2f, "glUniform2f" }, { &self->glGetError, "glGetError" }, { &self->glGetString, "glGetString" }, diff --git a/src/graphics/image.c b/src/graphics/image.c index 9934b42..0a6a88a 100644 --- a/src/graphics/image.c +++ b/src/graphics/image.c @@ -88,6 +88,10 @@ void mgl_image_unload(mgl_image *self) { self->format = 0; } -size_t mgl_image_get_size(mgl_image *self) { +size_t mgl_image_get_size(const mgl_image *self) { return (size_t)self->width * (size_t)self->height * mgl_image_format_num_channels(self->format); } + +int mgl_image_get_num_channels(const mgl_image *self) { + return mgl_image_format_num_channels(self->format); +} diff --git a/src/graphics/shader.c b/src/graphics/shader.c index 9afde0e..8f44f0f 100644 --- a/src/graphics/shader.c +++ b/src/graphics/shader.c @@ -173,6 +173,21 @@ int mgl_shader_program_finalize(mgl_shader_program *self) { /* TODO: Optimize glUseProgram */ /* TODO: Optimize glGetUniformLocation */ +/* TODO: Check if the uniform type matches the type of the value we want to set it to */ + +int mgl_shader_program_set_uniform_float(mgl_shader_program *self, const char *uniform_name, float value) { + mgl_context *context = mgl_get_context(); + int uniform_location = context->gl.glGetUniformLocation(self->id, uniform_name); + if(uniform_location == -1) { + fprintf(stderr, "Error: no uniform by the name %s was found in the shader\n", uniform_name); + return -1; + } + + context->gl.glUseProgram(self->id); + context->gl.glUniform1f(uniform_location, value); + context->gl.glUseProgram(0); + return 0; +} int mgl_shader_program_set_uniform_vec2f(mgl_shader_program *self, const char *uniform_name, mgl_vec2f value) { mgl_context *context = mgl_get_context(); @@ -183,7 +198,7 @@ int mgl_shader_program_set_uniform_vec2f(mgl_shader_program *self, const char *u } context->gl.glUseProgram(self->id); - context->gl.glUniform2fv(uniform_location, 1, &value.x); + context->gl.glUniform2f(uniform_location, value.x, value.y); context->gl.glUseProgram(0); return 0; } diff --git a/src/graphics/text.c b/src/graphics/text.c index 723b37a..31ae794 100644 --- a/src/graphics/text.c +++ b/src/graphics/text.c @@ -11,6 +11,8 @@ takes a while. */ +#define TAB_WIDTH 4 + static bool default_syntax_highlight(void *userdata, const char *str, size_t size, mgl_color *color) { (void)userdata; (void)str; @@ -19,10 +21,42 @@ static bool default_syntax_highlight(void *userdata, const char *str, size_t siz return false; } +static float fmax(float a, float b) { + return a >= b ? a : b; +} + +static mgl_vec2f mgl_text_calculate_bounds(mgl_text *self) { + mgl_vec2f bounds; + bounds.x = 0.0f; + bounds.y = self->font->character_size; + + /* TODO: Combine this with the loop in mgl_text_draw */ + mgl_font_glyph glyph; + float width = 0.0f; + for(size_t i = 0; i < self->text_size; ++i) { + unsigned char c = *(unsigned char*)&self->text[i]; + if((c >= 32 && c < 128)) { + if(mgl_font_get_glyph(self->font, c, &glyph) == 0) { + width += glyph.advance; + bounds.x = fmax(bounds.x, width); + } + } else if(c == '\t') { + if(mgl_font_get_glyph(self->font, ' ', &glyph) == 0) { + width += (glyph.advance * TAB_WIDTH); + bounds.x = fmax(bounds.x, width); + } + } else if(c == '\n') { + width = 0.0f; + bounds.y += self->font->character_size; + } + } + + return bounds; +} + int mgl_text_init(mgl_text *self, mgl_font *font, const char *str, size_t str_size, mgl_text_options *options) { self->font = font; - self->text = str; - self->text_size = str_size; + mgl_text_set_string(self, str, str_size); self->color = (mgl_color){ 255, 255, 255, 255 }; self->position = (mgl_vec2f){ 0.0f, 0.0f }; @@ -46,10 +80,20 @@ void mgl_text_deinit(mgl_text *self) { void mgl_text_set_string(mgl_text *self, const char *str, size_t str_size) { self->text = str; self->text_size = str_size; + if(self->text && self->text_size > 0 && self->font) + self->bounds = mgl_text_calculate_bounds(self); + else + self->bounds = (mgl_vec2f){ 0.0f, 0.0f }; } void mgl_text_set_font(mgl_text *self, mgl_font *font) { self->font = font; + if(self->font) { + if(self->bounds.x < 0.001f && self->bounds.y < 0.001f) + self->bounds = mgl_text_calculate_bounds(self); + } else { + self->bounds = (mgl_vec2f){ 0.0f, 0.0f }; + } } void mgl_text_set_position(mgl_text *self, mgl_vec2f position) { @@ -60,6 +104,10 @@ void mgl_text_set_color(mgl_text *self, mgl_color color) { self->color = color; } +mgl_vec2f mgl_text_get_bounds(const mgl_text *self) { + return self->bounds; +} + static void mgl_text_draw_glyph(mgl_context *context, mgl_font_glyph *glyph, mgl_vec2f position) { context->gl.glTexCoord2f(glyph->texture_position.x, glyph->texture_position.y); context->gl.glVertex3f(position.x + glyph->position.x, position.y + glyph->position.y, 0.0f); @@ -116,8 +164,7 @@ void mgl_text_draw(mgl_context *context, mgl_text *text) { } } else if(c == '\t') { if(mgl_font_get_glyph(text->font, ' ', &glyph) == 0) { - const int tab_width = 4; - for(int i = 0; i < tab_width; ++i) { + for(int i = 0; i < TAB_WIDTH; ++i) { mgl_text_draw_glyph(context, &glyph, position); position.x += glyph.advance; } -- cgit v1.2.3