From 1481b0a6313b725eec3e3ebeea085e98703df00f Mon Sep 17 00:00:00 2001 From: skal Date: Sun, 1 Feb 2026 14:58:05 +0100 Subject: feat(assets): Implement robust procedural asset generation pipeline - Updated asset_packer to correctly parse PROC(...) syntax using regex, handling nested commas. - Implemented runtime dispatch in AssetManager for procedural generation with dynamic memory management. - Added procedural generator functions (noise, grid, periodic). - Added comprehensive tests for procedural asset lifecycle (generation, caching, invalidation). - Fixed C++ string literal escaping in asset_packer. --- src/3d/renderer.cc | 101 +++++++++++++++++++++++++++++++++++++++++++++-------- src/3d/renderer.h | 23 +++++++++--- 2 files changed, 105 insertions(+), 19 deletions(-) (limited to 'src/3d') diff --git a/src/3d/renderer.cc b/src/3d/renderer.cc index 0578271..0d0b2d8 100644 --- a/src/3d/renderer.cc +++ b/src/3d/renderer.cc @@ -428,63 +428,136 @@ void Renderer3D::update_uniforms(const Scene& scene, const Camera& camera, } } -void Renderer3D::render(const Scene& scene, const Camera& camera, float time, - WGPUTextureView target_view, - WGPUTextureView depth_view_opt) { +void Renderer3D::draw(WGPURenderPassEncoder pass, const Scene& scene, const Camera& camera, float time) { + update_uniforms(scene, camera, time); - // Lazy Bind Group creation (since noise_texture might change) - if (bind_group_) - wgpuBindGroupRelease(bind_group_); + + + // Lazy Bind Group creation + + if (bind_group_) wgpuBindGroupRelease(bind_group_); + + WGPUBindGroupEntry bg_entries[4] = {}; + bg_entries[0].binding = 0; + bg_entries[0].buffer = global_uniform_buffer_; + bg_entries[0].size = sizeof(GlobalUniforms); + bg_entries[1].binding = 1; + bg_entries[1].buffer = object_storage_buffer_; + bg_entries[1].size = sizeof(ObjectData) * kMaxObjects; + bg_entries[2].binding = 2; + bg_entries[2].textureView = noise_texture_view_; + bg_entries[3].binding = 3; + bg_entries[3].sampler = default_sampler_; + + WGPUBindGroupDescriptor bg_desc = {}; + bg_desc.layout = wgpuRenderPipelineGetBindGroupLayout(pipeline_, 0); + bg_desc.entryCount = 4; + bg_desc.entries = bg_entries; + bind_group_ = wgpuDeviceCreateBindGroup(device_, &bg_desc); + wgpuBindGroupLayoutRelease(bg_desc.layout); + + + wgpuRenderPassEncoderSetPipeline(pass, pipeline_); + + wgpuRenderPassEncoderSetBindGroup(pass, 0, bind_group_, 0, nullptr); + + + + uint32_t instance_count = (uint32_t)std::min((size_t)kMaxObjects, scene.objects.size()); + + if (instance_count > 0) { + + wgpuRenderPassEncoderDraw(pass, 36, instance_count, 0, 0); + + } + +} + + + +void Renderer3D::render(const Scene& scene, const Camera& camera, float time, + + WGPUTextureView target_view, WGPUTextureView depth_view_opt) { + WGPUTextureView depth_view = depth_view_opt ? depth_view_opt : depth_view_; + + if (!depth_view) return; + + + WGPURenderPassColorAttachment color_attachment = {}; + gpu_init_color_attachment(color_attachment, target_view); + color_attachment.clearValue = {0.05, 0.05, 0.1, 1.0}; + + WGPURenderPassDepthStencilAttachment depth_attachment = {}; + depth_attachment.view = depth_view; + depth_attachment.depthLoadOp = WGPULoadOp_Clear; + depth_attachment.depthStoreOp = WGPUStoreOp_Store; + depth_attachment.depthClearValue = 1.0f; + + WGPURenderPassDescriptor pass_desc = {}; + pass_desc.colorAttachmentCount = 1; + pass_desc.colorAttachments = &color_attachment; + pass_desc.depthStencilAttachment = &depth_attachment; + + WGPUCommandEncoder encoder = wgpuDeviceCreateCommandEncoder(device_, nullptr); - WGPURenderPassEncoder pass = - wgpuCommandEncoderBeginRenderPass(encoder, &pass_desc); - wgpuRenderPassEncoderSetPipeline(pass, pipeline_); - wgpuRenderPassEncoderSetBindGroup(pass, 0, bind_group_, 0, nullptr); - uint32_t instance_count = - (uint32_t)std::min((size_t)kMaxObjects, scene.objects.size()); - if (instance_count > 0) - wgpuRenderPassEncoderDraw(pass, 36, instance_count, 0, 0); + + WGPURenderPassEncoder pass = wgpuCommandEncoderBeginRenderPass(encoder, &pass_desc); + + + + draw(pass, scene, camera, time); + + + wgpuRenderPassEncoderEnd(pass); + WGPUCommandBuffer commands = wgpuCommandEncoderFinish(encoder, nullptr); + wgpuQueueSubmit(queue_, 1, &commands); + + + wgpuRenderPassEncoderRelease(pass); + wgpuCommandBufferRelease(commands); + wgpuCommandEncoderRelease(encoder); + } \ No newline at end of file diff --git a/src/3d/renderer.h b/src/3d/renderer.h index dda6229..e87d47a 100644 --- a/src/3d/renderer.h +++ b/src/3d/renderer.h @@ -28,12 +28,25 @@ class Renderer3D { void init(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format); void shutdown(); - // Renders the scene to the given texture view - void render(const Scene& scene, const Camera& camera, float time, - WGPUTextureView target_view, - WGPUTextureView depth_view_opt = nullptr); + // Renders the scene to the given texture view (Convenience: creates a pass) - void set_noise_texture(WGPUTextureView noise_view); + void render(const Scene& scene, const Camera& camera, float time, + + WGPUTextureView target_view, WGPUTextureView depth_view_opt = nullptr); + + + + // Records draw commands to an existing pass. + + // Assumes the pass has a compatible pipeline (or we set it here). + + // Note: Caller must ensure depth/color attachments are set up correctly in the pass. + + void draw(WGPURenderPassEncoder pass, const Scene& scene, const Camera& camera, float time); + + + + void set_noise_texture(WGPUTextureView noise_view); // Resize handler (if needed for internal buffers) void resize(int width, int height); -- cgit v1.2.3