diff --git a/src/main.c b/src/main.c index bd9cd4d..d8650f5 100644 --- a/src/main.c +++ b/src/main.c @@ -28,22 +28,33 @@ static void log_fn(const char* tag, uint32_t log_level, uint32_t log_item_id, co fprintf(stderr, "[%s - %s]: (%d) %s \nat %s:%d", tag, log_level == 0 ? "FATAL" : log_level == 1 ? "ERROR" : "WARNING", log_item_id, message_or_null, filename_or_null, line_nr); } +//#define _SG_LOG_ITEMS \ + _SG_LOGITEM_XMACRO(COMPUTE_INVALID_BUFFER, "invalid buffer"); + static void draw_scene(userdata_t* ud) { - /* if(ud->scene.dirty) + if(ud->scene.dirty) { - //sg_update_buffer(ud->compute.shared_buffer, SG_RANGE(ud->scene)); + sg_buffer seg_buffer = sg_query_view_buffer(ud->compute.bindings.views[0]); + //_SG_VALIDATE(seg_buffer.id == SG_INVALID_ID, COMPUTE_INVALID_BUFFER); + sg_update_buffer(seg_buffer, &(sg_range) { .ptr = ud->scene.segments, .size = sizeof(segment_t) * ud->scene.num_segments }); + + sg_buffer shape_buffer = sg_query_view_buffer(ud->compute.bindings.views[1]); + //_SG_VALIDATE(shape_buffer.id == SG_INVALID_ID, COMPUTE_INVALID_BUFFER); + sg_update_buffer(shape_buffer, &(sg_range) { .ptr = ud->scene.shapes, .size = sizeof(shape_meta_t) * ud->scene.num_shapes }); + + sg_begin_pass(&(sg_pass){ .compute = true, .label = "Compute Pass" }); + sg_apply_pipeline(ud->compute.pipeline); + sg_apply_uniforms(0, &SG_RANGE(ud->renderer.uniforms)); + sg_apply_uniforms(1, &SG_RANGE(ud->scene.tiles[0])); + sg_apply_bindings(&ud->compute.bindings); + + sg_dispatch(TILE_SIZE / 8, TILE_SIZE / 8, 1); + + sg_end_pass(); + ud->scene.dirty = false; } - - sg_begin_pass(&(sg_pass){ .compute = true, label = "compute-pass" }); - sg_apply_pipeline(ud->compute.pipeline); - sg_apply_uniforms(0, &SG_RANGE(ud->renderer.uniforms)); - sg_apply_bindings(&ud->compute.bindings); - - sg_dispatch(1, 1, 1); - - sg_end_pass(); */ } static void frame(void* _userdata) @@ -64,7 +75,7 @@ static void frame(void* _userdata) .dpi_scale = sapp_dpi_scale(), }); - igBegin("Framerate", (bool*) true, ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoTitleBar); + igBegin("Framerate", (bool*) true, ImGuiWindowFlags_NoResize | ImGuiWindowFlags_NoCollapse | ImGuiWindowFlags_NoTitleBar); igText("%.0f FPS", 1 / sapp_frame_duration()); igText("%.3fms", sapp_frame_duration() * 1000); igEnd(); @@ -214,6 +225,10 @@ static void init(void* _userdata) .colors[0] = { .clear_value = { 0.0f, 0.0f, 0.0f, 1.0f }, .load_action = SG_LOADACTION_CLEAR } } }; + + add_rectangle(&ud->scene, (vec2) { 200.0f, 100.0f }, (vec2) { 100.0f, 150.0f }); + add_circle(&ud->scene, (vec2) { 400.0f, 300.0f }, 125.0f); + scene_add_tile(&ud->scene, (tile_cache_entry) { .id = { .lod = 0, .tile = TILE_SIZE, .world_min = { 0.0f, 0.0f }, .world_max = { 1024.0f, 1024.0f } } }); } static void cleanup(void* _userdata) diff --git a/src/shape.h b/src/shape.h index 70bc32b..5c2a88d 100644 --- a/src/shape.h +++ b/src/shape.h @@ -13,19 +13,7 @@ typedef struct shape_meta_t { float bbox_min_x, bbox_min_y, bbox_max_x, bbox_max_y; } shape_meta_t; -typedef struct scene_t { - uint32_t num_shapes; - uint32_t max_shapes; - shape_meta_t* shapes; - - uint32_t num_segments; - uint32_t max_segments; - segment_t* segments; - - bool dirty; -} scene_t; - -#define TILE_SIZE 64 // pixels per tile (same for all LODs) +#define TILE_SIZE 128 // pixels per tile (same for all LODs) // Tile descriptor typedef struct tile_ID { @@ -41,10 +29,26 @@ typedef struct tile_ID { typedef struct tile_cache_entry { tile_ID id; // GPU texture holding the SDF values (R32Float) - WGPUTexture texture; //TODO + sg_buffer SDF; //TODO bool ready; } tile_cache_entry; +typedef struct scene_t { + uint32_t num_shapes; + uint32_t max_shapes; + shape_meta_t* shapes; + + uint32_t num_segments; + uint32_t max_segments; + segment_t* segments; + + uint32_t num_tiles; + uint32_t max_tiles; + tile_cache_entry* tiles; + + bool dirty; +} scene_t; + // Initialise a scene_t with a given capacity for shapes and segments. static int scene_init(scene_t* s, int init_shape_cap, int init_seg_cap) { s->num_shapes = 0; @@ -55,9 +59,13 @@ static int scene_init(scene_t* s, int init_shape_cap, int init_seg_cap) { s->max_segments = init_seg_cap; s->segments = (segment_t*) malloc(init_seg_cap * sizeof(segment_t)); + s->num_tiles = 0; + s->max_tiles = 8; + s->tiles = (tile_cache_entry*) malloc(8 * sizeof(tile_cache_entry)); + s->dirty = true; - if (!s->shapes || !s->segments) return 0; // allocation failure + if (!s->shapes || !s->segments || !s->tiles) return 0; // allocation failure return 1; } @@ -93,10 +101,26 @@ static int scene_add_shape(scene_t* s, shape_meta_t meta) { return idx; } +static int scene_add_tile(scene_t* s, tile_cache_entry tile) +{ + if (s->num_tiles >= s->max_tiles) { + int new_cap = s->max_tiles * 2; + tile_cache_entry* tmp = (tile_cache_entry*) realloc(s->tiles, new_cap * sizeof(tile_cache_entry)); + if (!tmp) return -1; + s->tiles = tmp; + s->max_tiles = new_cap; + } + int idx = s->num_tiles++; + s->tiles[idx] = tile; + + s->dirty = true; + return idx; +} static int scene_shutdown(scene_t* s) { free(s->segments); free(s->shapes); + free(s->tiles); free(s); return 1;