From 92aa0af44c75fa56866faf1858b22748a197fe74 Mon Sep 17 00:00:00 2001 From: Patrick Cleavelin Date: Sat, 16 Mar 2024 17:05:23 -0500 Subject: [PATCH] array macros --- src/ed_array.h | 34 ++++++++++++++++++++++++++++ src/main.c | 61 ++++++++++++++++---------------------------------- src/ui.h | 3 +++ 3 files changed, 56 insertions(+), 42 deletions(-) create mode 100644 src/ed_array.h diff --git a/src/ed_array.h b/src/ed_array.h new file mode 100644 index 0000000..40ddd27 --- /dev/null +++ b/src/ed_array.h @@ -0,0 +1,34 @@ +#ifndef ED_ARRAY_INCLUDED +#define ED_ARRAY_INCLUDED +#include +#include + +#define array(T) struct T ## Array +#define arrayTemplate(T) array(T) {\ + size_t size, capacity;\ + T *data;\ +};\ +array(T) T ## ArrayConstruct(size_t size) {\ + array(T) this;\ + this.size = 0;\ + this.capacity = size;\ + this.data = malloc(size * sizeof(T));\ + if (!this.data) {\ + assert("failed to allocate memory for array");\ + }\ + return this;\ +};\ +void T ## PushArray(array(T) *arr, T value) {\ + if (arr->size+1 <= arr->capacity) {\ + arr->data[arr->size] = value;\ + arr->size += 1;\ + } else {\ + // TODO: resize array + fprintf(stderr, "failed to push to u8 array, size+num > capacity\n");\ + }\ +}; + +#define newArray(T, size) T ## ArrayConstruct(size) +#define pushArray(T, arr, value) T ## PushArray(arr, (value)) + +#endif diff --git a/src/main.c b/src/main.c index d1cee40..4285586 100644 --- a/src/main.c +++ b/src/main.c @@ -32,6 +32,7 @@ #include "string.h" #include "ht.h" #include "ui.h" +#include "ed_array.h" // static Arena default_arena = {0}; @@ -49,6 +50,7 @@ typedef struct { float size[2]; float border_size[2]; } GpuUiRect; +arrayTemplate(GpuUiRect); typedef struct { float atlas_position[2]; @@ -56,38 +58,12 @@ typedef struct { float position[2]; float y_offset; } GpuGlyph; +arrayTemplate(GpuGlyph); typedef struct { float screen_size[4]; } GpuUniformParams; -typedef struct { - size_t size; - size_t capacity; - uint8_t *data; -} U8Array; - -U8Array new_u8array(size_t capacity) { - return (U8Array) { - .size = 0, - .capacity = capacity, - .data = context_alloc(capacity), - }; -} - -void push_u8array(U8Array *array, uint8_t *items, size_t num) { - if (array->size + num <= array->capacity) { - memcpy(array->data + array->size, items, num); - array->size += num; - } else { - fprintf(stderr, "failed to push to u8 array, size+num > capacity\n"); - } -} - -void clear_u8array(U8Array *array) { - array->size = 0; -} - static struct { sg_pass_action pass_action; sg_pipeline pip; @@ -98,9 +74,9 @@ static struct { sg_shader_desc scratch_shader_desc; - U8Array gpu_ui_rects; - U8Array gpu_glyphs; - U8Array glyph_cache; + array(GpuUiRect) gpu_ui_rects; + array(GpuGlyph) gpu_glyphs; + array(GpuGlyph) glyph_cache; bool should_exit; @@ -111,13 +87,14 @@ void queue_text(string text, float position[2]) { float x = 0; for (size_t i=0; i < text.len; ++i) { if (text.data[i] >= 32) { - GpuGlyph glyph = *((GpuGlyph *)(state.glyph_cache.data+((text.data[i] - 32) * sizeof(GpuGlyph)))); + //GpuGlyph glyph = *((GpuGlyph *)(state.glyph_cache.data+((text.data[i] - 32) * sizeof(GpuGlyph)))); + GpuGlyph glyph = state.glyph_cache.data[text.data[i] - 32]; glyph.position[0] = x+position[0]; glyph.position[1] = position[1]; x += glyph.size[0]/2; - push_u8array(&state.gpu_glyphs, (uint8_t *)(&glyph), sizeof(GpuGlyph)); + pushArray(GpuGlyph, &state.gpu_glyphs, glyph); } } } @@ -230,9 +207,9 @@ void ed_init() { const int rasterized_font_height = 64; uint8_t *font_bitmap = context_alloc(font_bitmap_size*font_bitmap_size * sizeof(uint8_t)); - state.gpu_ui_rects = new_u8array(sizeof(GpuUiRect) * 2000); - state.gpu_glyphs = new_u8array(sizeof(GpuGlyph) * 1024); - state.glyph_cache = new_u8array(sizeof(GpuGlyph) * 97); + state.gpu_ui_rects = newArray(GpuUiRect, 2000); + state.gpu_glyphs = newArray(GpuGlyph, 1024); + state.glyph_cache = newArray(GpuGlyph, 97); int ascent, descent, line_gap; float scale = stbtt_ScaleForPixelHeight(&font, rasterized_font_height); @@ -244,12 +221,12 @@ void ed_init() { } } // manually add glyph for SPACE - push_u8array(&state.glyph_cache, (uint8_t *)(&(GpuGlyph){ + pushArray(GpuGlyph, &state.glyph_cache, ((GpuGlyph){ .atlas_position = { 0 }, .size = { rasterized_font_height/4, rasterized_font_height }, .position = { 0 }, .y_offset = -rasterized_font_height, - }), 1 * sizeof(GpuGlyph)); + })); int x = rasterized_font_height/4; int y = 0; @@ -274,18 +251,18 @@ void ed_init() { xxx += 1; } - push_u8array(&state.glyph_cache, (uint8_t *)(&(GpuGlyph){ + pushArray(GpuGlyph, &state.glyph_cache, ((GpuGlyph){ .atlas_position = { (float)(x), (float)(y) }, .size = { (float)width, (float)height }, .position = { (float)x, (float)y }, .y_offset = (float)(yoff), - }), 1 * sizeof(GpuGlyph)); + })); x += width; } state.bind.vertex_buffers[1] = sg_make_buffer(&(sg_buffer_desc) { - .size = state.gpu_glyphs.capacity, + .size = state.gpu_glyphs.capacity * sizeof(GpuGlyph), .usage = SG_USAGE_STREAM, .label = "glyph buffer" }); @@ -354,7 +331,7 @@ void ed_frame() { if (state.gpu_glyphs.size > 0) { sg_update_buffer(state.bind.vertex_buffers[1], &(sg_range) { .ptr = state.gpu_glyphs.data, - .size = state.gpu_glyphs.size + .size = state.gpu_glyphs.size * sizeof(GpuGlyph) }); } @@ -372,7 +349,7 @@ void ed_frame() { sg_apply_pipeline(state.pip); sg_apply_bindings(&state.bind); sg_apply_uniforms(SG_SHADERSTAGE_VS, 0, &(sg_range) { .ptr = &gpu_uniform_params, .size = sizeof(GpuUniformParams) }); - sg_draw(0, 6, state.gpu_glyphs.size/sizeof(GpuGlyph)); + sg_draw(0, 6, state.gpu_glyphs.size); } sg_end_pass(); sg_commit(); diff --git a/src/ui.h b/src/ui.h index 981755c..48a0220 100644 --- a/src/ui.h +++ b/src/ui.h @@ -8,6 +8,7 @@ #include #include "ht.h" +#include "ed_array.h" typedef enum { UI_AXIS_HORIZONTAL, @@ -71,9 +72,11 @@ typedef struct { size_t prev; size_t parent; } ui_element_frame_data; +arrayTemplate(ui_element_frame_data); typedef struct { ed_ht cached_elements; + array(ui_element_frame_data) frame_elements; } ui_context;