From 32d26371627638570b74d678ab73deb7b87af8e4 Mon Sep 17 00:00:00 2001 From: skal Date: Sat, 31 Jan 2026 17:23:13 +0100 Subject: fix: Cross-compilation and style compliance Fixes seq_compiler build for Windows cross-compilation. Moves common WebGPU compatibility shims to gpu.h. Applies project-wide coding style via clang-format. Verified on both macOS (native) and Windows (cross-compile). --- src/gpu/demo_effects.cc | 268 +++++++++++++++++++++++++++++++++++------------- src/gpu/effect.cc | 42 +++++--- src/gpu/effect.h | 21 ++-- src/gpu/gpu.cc | 16 +-- src/gpu/gpu.h | 25 +++-- 5 files changed, 261 insertions(+), 111 deletions(-) (limited to 'src/gpu') diff --git a/src/gpu/demo_effects.cc b/src/gpu/demo_effects.cc index 5d7419d..71f1284 100644 --- a/src/gpu/demo_effects.cc +++ b/src/gpu/demo_effects.cc @@ -243,14 +243,21 @@ struct Uniforms { time: f32, beat: f32, intensity: f32, aspect_ratio: f32, }; })"; // --- HeptagonEffect --- -HeptagonEffect::HeptagonEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); +HeptagonEffect::HeptagonEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); ResourceBinding bindings[] = {{uniforms_, WGPUBufferBindingType_Uniform}}; pass_ = gpu_create_render_pass(device, format, main_shader_wgsl, bindings, 1); pass_.vertex_count = 21; } -void HeptagonEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float p, a, t, d; } u = {i, a, t, 0.0f}; +void HeptagonEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { + struct { + float p, a, t, d; + } u = {i, a, t, 0.0f}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); wgpuRenderPassEncoderSetPipeline(pass, pass_.pipeline); wgpuRenderPassEncoderSetBindGroup(pass, 0, pass_.bind_group, 0, nullptr); @@ -258,54 +265,91 @@ void HeptagonEffect::render(WGPURenderPassEncoder pass, float t, float b, float } // --- ParticlesEffect --- -ParticlesEffect::ParticlesEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); +ParticlesEffect::ParticlesEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); std::vector init_p(NUM_PARTICLES); - particles_buffer_ = gpu_create_buffer(device, sizeof(Particle) * NUM_PARTICLES, WGPUBufferUsage_Storage | WGPUBufferUsage_Vertex, init_p.data()); - ResourceBinding cb[] = {{particles_buffer_, WGPUBufferBindingType_Storage}, {uniforms_, WGPUBufferBindingType_Uniform}}; + particles_buffer_ = gpu_create_buffer( + device, sizeof(Particle) * NUM_PARTICLES, + WGPUBufferUsage_Storage | WGPUBufferUsage_Vertex, init_p.data()); + ResourceBinding cb[] = {{particles_buffer_, WGPUBufferBindingType_Storage}, + {uniforms_, WGPUBufferBindingType_Uniform}}; compute_pass_ = gpu_create_compute_pass(device, particle_compute_wgsl, cb, 2); compute_pass_.workgroup_size_x = (NUM_PARTICLES + 63) / 64; - ResourceBinding rb[] = {{particles_buffer_, WGPUBufferBindingType_ReadOnlyStorage}, {uniforms_, WGPUBufferBindingType_Uniform}}; - render_pass_ = gpu_create_render_pass(device, format, particle_render_wgsl, rb, 2); - render_pass_.vertex_count = 6; render_pass_.instance_count = NUM_PARTICLES; + ResourceBinding rb[] = { + {particles_buffer_, WGPUBufferBindingType_ReadOnlyStorage}, + {uniforms_, WGPUBufferBindingType_Uniform}}; + render_pass_ = + gpu_create_render_pass(device, format, particle_render_wgsl, rb, 2); + render_pass_.vertex_count = 6; + render_pass_.instance_count = NUM_PARTICLES; } -void ParticlesEffect::compute(WGPUCommandEncoder e, float t, float b, float i, float a) { - struct { float p, a, t, d; } u = {i, a, t, 0.0f}; +void ParticlesEffect::compute(WGPUCommandEncoder e, float t, float b, float i, + float a) { + struct { + float p, a, t, d; + } u = {i, a, t, 0.0f}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); WGPUComputePassEncoder pass = wgpuCommandEncoderBeginComputePass(e, nullptr); wgpuComputePassEncoderSetPipeline(pass, compute_pass_.pipeline); - wgpuComputePassEncoderSetBindGroup(pass, 0, compute_pass_.bind_group, 0, nullptr); - wgpuComputePassEncoderDispatchWorkgroups(pass, compute_pass_.workgroup_size_x, 1, 1); + wgpuComputePassEncoderSetBindGroup(pass, 0, compute_pass_.bind_group, 0, + nullptr); + wgpuComputePassEncoderDispatchWorkgroups(pass, compute_pass_.workgroup_size_x, + 1, 1); wgpuComputePassEncoderEnd(pass); } -void ParticlesEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { +void ParticlesEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { wgpuRenderPassEncoderSetPipeline(pass, render_pass_.pipeline); - wgpuRenderPassEncoderSetBindGroup(pass, 0, render_pass_.bind_group, 0, nullptr); - wgpuRenderPassEncoderDraw(pass, render_pass_.vertex_count, render_pass_.instance_count, 0, 0); + wgpuRenderPassEncoderSetBindGroup(pass, 0, render_pass_.bind_group, 0, + nullptr); + wgpuRenderPassEncoderDraw(pass, render_pass_.vertex_count, + render_pass_.instance_count, 0, 0); } // --- PassthroughEffect --- -PassthroughEffect::PassthroughEffect(WGPUDevice device, WGPUTextureFormat format) : device_(device) { - pipeline_ = create_post_process_pipeline(device, format, passthrough_shader_wgsl); +PassthroughEffect::PassthroughEffect(WGPUDevice device, + WGPUTextureFormat format) + : device_(device) { + pipeline_ = + create_post_process_pipeline(device, format, passthrough_shader_wgsl); } void PassthroughEffect::update_bind_group(WGPUTextureView input_view) { - if (bind_group_) wgpuBindGroupRelease(bind_group_); + if (bind_group_) + wgpuBindGroupRelease(bind_group_); WGPUBindGroupLayout bgl = wgpuRenderPipelineGetBindGroupLayout(pipeline_, 0); - WGPUSamplerDescriptor sd = {}; WGPUSampler sampler = wgpuDeviceCreateSampler(device_, &sd); - WGPUBindGroupEntry bge[2] = {}; bge[0].binding = 0; bge[0].sampler = sampler; bge[1].binding = 1; bge[1].textureView = input_view; - WGPUBindGroupDescriptor bgd = {.layout = bgl, .entryCount = 2, .entries = bge}; + WGPUSamplerDescriptor sd = {}; + WGPUSampler sampler = wgpuDeviceCreateSampler(device_, &sd); + WGPUBindGroupEntry bge[2] = {}; + bge[0].binding = 0; + bge[0].sampler = sampler; + bge[1].binding = 1; + bge[1].textureView = input_view; + WGPUBindGroupDescriptor bgd = { + .layout = bgl, .entryCount = 2, .entries = bge}; bind_group_ = wgpuDeviceCreateBindGroup(device_, &bgd); } // --- MovingEllipseEffect --- -MovingEllipseEffect::MovingEllipseEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); +MovingEllipseEffect::MovingEllipseEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); ResourceBinding bindings[] = {{uniforms_, WGPUBufferBindingType_Uniform}}; - pass_ = gpu_create_render_pass(device, format, ellipse_shader_wgsl, bindings, 1); + pass_ = + gpu_create_render_pass(device, format, ellipse_shader_wgsl, bindings, 1); pass_.vertex_count = 3; } -void MovingEllipseEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float t, b, i, a; } u = {t, b, i, a}; +void MovingEllipseEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { + struct { + float t, b, i, a; + } u = {t, b, i, a}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); wgpuRenderPassEncoderSetPipeline(pass, pass_.pipeline); wgpuRenderPassEncoderSetBindGroup(pass, 0, pass_.bind_group, 0, nullptr); @@ -313,86 +357,162 @@ void MovingEllipseEffect::render(WGPURenderPassEncoder pass, float t, float b, f } // --- ParticleSprayEffect --- -ParticleSprayEffect::ParticleSprayEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); - std::vector init_p(NUM_PARTICLES); for (auto &p : init_p) p.pos[3] = 0.0f; - particles_buffer_ = gpu_create_buffer(device, sizeof(Particle) * NUM_PARTICLES, WGPUBufferUsage_Storage | WGPUBufferUsage_Vertex, init_p.data()); - ResourceBinding cb[] = {{particles_buffer_, WGPUBufferBindingType_Storage}, {uniforms_, WGPUBufferBindingType_Uniform}}; - compute_pass_ = gpu_create_compute_pass(device, particle_spray_compute_wgsl, cb, 2); +ParticleSprayEffect::ParticleSprayEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); + std::vector init_p(NUM_PARTICLES); + for (auto &p : init_p) + p.pos[3] = 0.0f; + particles_buffer_ = gpu_create_buffer( + device, sizeof(Particle) * NUM_PARTICLES, + WGPUBufferUsage_Storage | WGPUBufferUsage_Vertex, init_p.data()); + ResourceBinding cb[] = {{particles_buffer_, WGPUBufferBindingType_Storage}, + {uniforms_, WGPUBufferBindingType_Uniform}}; + compute_pass_ = + gpu_create_compute_pass(device, particle_spray_compute_wgsl, cb, 2); compute_pass_.workgroup_size_x = (NUM_PARTICLES + 63) / 64; - ResourceBinding rb[] = {{particles_buffer_, WGPUBufferBindingType_ReadOnlyStorage}, {uniforms_, WGPUBufferBindingType_Uniform}}; - render_pass_ = gpu_create_render_pass(device, format, particle_render_wgsl, rb, 2); - render_pass_.vertex_count = 6; render_pass_.instance_count = NUM_PARTICLES; + ResourceBinding rb[] = { + {particles_buffer_, WGPUBufferBindingType_ReadOnlyStorage}, + {uniforms_, WGPUBufferBindingType_Uniform}}; + render_pass_ = + gpu_create_render_pass(device, format, particle_render_wgsl, rb, 2); + render_pass_.vertex_count = 6; + render_pass_.instance_count = NUM_PARTICLES; } -void ParticleSprayEffect::compute(WGPUCommandEncoder e, float t, float b, float i, float a) { - struct { float i, a, t, b; } u = {i, a, t, b}; +void ParticleSprayEffect::compute(WGPUCommandEncoder e, float t, float b, + float i, float a) { + struct { + float i, a, t, b; + } u = {i, a, t, b}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); WGPUComputePassEncoder pass = wgpuCommandEncoderBeginComputePass(e, nullptr); wgpuComputePassEncoderSetPipeline(pass, compute_pass_.pipeline); - wgpuComputePassEncoderSetBindGroup(pass, 0, compute_pass_.bind_group, 0, nullptr); - wgpuComputePassEncoderDispatchWorkgroups(pass, compute_pass_.workgroup_size_x, 1, 1); + wgpuComputePassEncoderSetBindGroup(pass, 0, compute_pass_.bind_group, 0, + nullptr); + wgpuComputePassEncoderDispatchWorkgroups(pass, compute_pass_.workgroup_size_x, + 1, 1); wgpuComputePassEncoderEnd(pass); } -void ParticleSprayEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { +void ParticleSprayEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { wgpuRenderPassEncoderSetPipeline(pass, render_pass_.pipeline); - wgpuRenderPassEncoderSetBindGroup(pass, 0, render_pass_.bind_group, 0, nullptr); + wgpuRenderPassEncoderSetBindGroup(pass, 0, render_pass_.bind_group, 0, + nullptr); wgpuRenderPassEncoderDraw(pass, 6, NUM_PARTICLES, 0, 0); } // --- PostProcess Implementation Helper --- -static void pp_update_bind_group(WGPUDevice device, WGPURenderPipeline pipeline, WGPUBindGroup *bind_group, WGPUTextureView input_view, GpuBuffer uniforms) { - if (*bind_group) wgpuBindGroupRelease(*bind_group); +static void pp_update_bind_group(WGPUDevice device, WGPURenderPipeline pipeline, + WGPUBindGroup *bind_group, + WGPUTextureView input_view, + GpuBuffer uniforms) { + if (*bind_group) + wgpuBindGroupRelease(*bind_group); WGPUBindGroupLayout bgl = wgpuRenderPipelineGetBindGroupLayout(pipeline, 0); - WGPUSamplerDescriptor sd = {}; sd.magFilter = WGPUFilterMode_Linear; sd.minFilter = WGPUFilterMode_Linear; + WGPUSamplerDescriptor sd = {}; + sd.magFilter = WGPUFilterMode_Linear; + sd.minFilter = WGPUFilterMode_Linear; WGPUSampler sampler = wgpuDeviceCreateSampler(device, &sd); WGPUBindGroupEntry bge[3] = {}; - bge[0].binding = 0; bge[0].sampler = sampler; - bge[1].binding = 1; bge[1].textureView = input_view; - bge[2].binding = 2; bge[2].buffer = uniforms.buffer; bge[2].size = uniforms.size; - WGPUBindGroupDescriptor bgd = {.layout = bgl, .entryCount = 3, .entries = bge}; + bge[0].binding = 0; + bge[0].sampler = sampler; + bge[1].binding = 1; + bge[1].textureView = input_view; + bge[2].binding = 2; + bge[2].buffer = uniforms.buffer; + bge[2].size = uniforms.size; + WGPUBindGroupDescriptor bgd = { + .layout = bgl, .entryCount = 3, .entries = bge}; *bind_group = wgpuDeviceCreateBindGroup(device, &bgd); } // --- GaussianBlurEffect --- -GaussianBlurEffect::GaussianBlurEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : device_(device), queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); - pipeline_ = create_post_process_pipeline(device, format, gaussian_blur_shader_wgsl); +GaussianBlurEffect::GaussianBlurEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : device_(device), queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); + pipeline_ = + create_post_process_pipeline(device, format, gaussian_blur_shader_wgsl); } -void GaussianBlurEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float t, b, i, a; } u = {t, b, i, a}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); +void GaussianBlurEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { + struct { + float t, b, i, a; + } u = {t, b, i, a}; + wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); PostProcessEffect::render(pass, t, b, i, a); } -void GaussianBlurEffect::update_bind_group(WGPUTextureView v) { pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); } +void GaussianBlurEffect::update_bind_group(WGPUTextureView v) { + pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); +} // --- SolarizeEffect --- -SolarizeEffect::SolarizeEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : device_(device), queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); - pipeline_ = create_post_process_pipeline(device, format, solarize_shader_wgsl); +SolarizeEffect::SolarizeEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : device_(device), queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); + pipeline_ = + create_post_process_pipeline(device, format, solarize_shader_wgsl); } -void SolarizeEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float t, b, i, a; } u = {t, b, i, a}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); +void SolarizeEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { + struct { + float t, b, i, a; + } u = {t, b, i, a}; + wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); PostProcessEffect::render(pass, t, b, i, a); } -void SolarizeEffect::update_bind_group(WGPUTextureView v) { pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); } +void SolarizeEffect::update_bind_group(WGPUTextureView v) { + pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); +} // --- DistortEffect --- -DistortEffect::DistortEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : device_(device), queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); +DistortEffect::DistortEffect(WGPUDevice device, WGPUQueue queue, + WGPUTextureFormat format) + : device_(device), queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); pipeline_ = create_post_process_pipeline(device, format, distort_shader_wgsl); } -void DistortEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float t, b, i, a; } u = {t, b, i, a}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); +void DistortEffect::render(WGPURenderPassEncoder pass, float t, float b, + float i, float a) { + struct { + float t, b, i, a; + } u = {t, b, i, a}; + wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); PostProcessEffect::render(pass, t, b, i, a); } -void DistortEffect::update_bind_group(WGPUTextureView v) { pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); } +void DistortEffect::update_bind_group(WGPUTextureView v) { + pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); +} // --- ChromaAberrationEffect --- -ChromaAberrationEffect::ChromaAberrationEffect(WGPUDevice device, WGPUQueue queue, WGPUTextureFormat format) : device_(device), queue_(queue) { - uniforms_ = gpu_create_buffer(device, sizeof(float) * 4, WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); - pipeline_ = create_post_process_pipeline(device, format, chroma_aberration_shader_wgsl); +ChromaAberrationEffect::ChromaAberrationEffect(WGPUDevice device, + WGPUQueue queue, + WGPUTextureFormat format) + : device_(device), queue_(queue) { + uniforms_ = + gpu_create_buffer(device, sizeof(float) * 4, + WGPUBufferUsage_Uniform | WGPUBufferUsage_CopyDst); + pipeline_ = create_post_process_pipeline(device, format, + chroma_aberration_shader_wgsl); } -void ChromaAberrationEffect::render(WGPURenderPassEncoder pass, float t, float b, float i, float a) { - struct { float t, b, i, a; } u = {t, b, i, a}; wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); +void ChromaAberrationEffect::render(WGPURenderPassEncoder pass, float t, + float b, float i, float a) { + struct { + float t, b, i, a; + } u = {t, b, i, a}; + wgpuQueueWriteBuffer(queue_, uniforms_.buffer, 0, &u, sizeof(u)); PostProcessEffect::render(pass, t, b, i, a); } -void ChromaAberrationEffect::update_bind_group(WGPUTextureView v) { pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); } +void ChromaAberrationEffect::update_bind_group(WGPUTextureView v) { + pp_update_bind_group(device_, pipeline_, &bind_group_, v, uniforms_); +} diff --git a/src/gpu/effect.cc b/src/gpu/effect.cc index 0ab476b..c3bd99a 100644 --- a/src/gpu/effect.cc +++ b/src/gpu/effect.cc @@ -188,11 +188,12 @@ void MainSequence::render_frame(float global_time, float beat, float peak, WGPUTextureView final_view = wgpuTextureCreateView(st.texture, nullptr); passthrough_effect_->update_bind_group(framebuffer_view_a_); - WGPURenderPassColorAttachment final_attachment = { - .view = final_view, .loadOp = WGPULoadOp_Load, .storeOp = WGPUStoreOp_Store}; - WGPURenderPassDescriptor final_desc = {.colorAttachmentCount = 1, - .colorAttachments = - &final_attachment}; + WGPURenderPassColorAttachment final_attachment = {.view = final_view, + .loadOp = WGPULoadOp_Load, + .storeOp = + WGPUStoreOp_Store}; + WGPURenderPassDescriptor final_desc = { + .colorAttachmentCount = 1, .colorAttachments = &final_attachment}; WGPURenderPassEncoder final_pass = wgpuCommandEncoderBeginRenderPass(encoder, &final_desc); passthrough_effect_->render(final_pass, 0, 0, 0, aspect_ratio); @@ -210,16 +211,19 @@ void MainSequence::render_frame(float global_time, float beat, float peak, wgpuSurfaceGetCurrentTexture(surface, &st); WGPUTextureView current_output = - is_last ? wgpuTextureCreateView(st.texture, nullptr) - : (current_input == framebuffer_view_a_ ? framebuffer_view_b_ - : framebuffer_view_a_); + is_last + ? wgpuTextureCreateView(st.texture, nullptr) + : (current_input == framebuffer_view_a_ ? framebuffer_view_b_ + : framebuffer_view_a_); PostProcessEffect *pp = static_cast(post_effects[i]->effect.get()); pp->update_bind_group(current_input); - WGPURenderPassColorAttachment pp_attachment = { - .view = current_output, .loadOp = WGPULoadOp_Load, .storeOp = WGPUStoreOp_Store}; + WGPURenderPassColorAttachment pp_attachment = {.view = current_output, + .loadOp = WGPULoadOp_Load, + .storeOp = + WGPUStoreOp_Store}; WGPURenderPassDescriptor pp_desc = {.colorAttachmentCount = 1, .colorAttachments = &pp_attachment}; WGPURenderPassEncoder pp_pass = @@ -242,10 +246,14 @@ void MainSequence::render_frame(float global_time, float beat, float peak, } void MainSequence::shutdown() { - if (framebuffer_view_a_) wgpuTextureViewRelease(framebuffer_view_a_); - if (framebuffer_a_) wgpuTextureRelease(framebuffer_a_); - if (framebuffer_view_b_) wgpuTextureViewRelease(framebuffer_view_b_); - if (framebuffer_b_) wgpuTextureRelease(framebuffer_b_); + if (framebuffer_view_a_) + wgpuTextureViewRelease(framebuffer_view_a_); + if (framebuffer_a_) + wgpuTextureRelease(framebuffer_a_); + if (framebuffer_view_b_) + wgpuTextureViewRelease(framebuffer_view_b_); + if (framebuffer_b_) + wgpuTextureRelease(framebuffer_b_); for (auto &entry : sequences_) { entry.seq->reset(); } @@ -256,7 +264,8 @@ void MainSequence::simulate_until(float target_time, float step_rate) { const float bpm = 128.0f; const float aspect_ratio = 16.0f / 9.0f; for (float t = 0.0f; t < target_time; t += step_rate) { - WGPUCommandEncoder encoder = wgpuDeviceCreateCommandEncoder(device, nullptr); + WGPUCommandEncoder encoder = + wgpuDeviceCreateCommandEncoder(device, nullptr); float beat = fmodf(t * bpm / 60.0f, 1.0f); std::vector scene_effects, post_effects; for (auto &entry : sequences_) { @@ -266,7 +275,8 @@ void MainSequence::simulate_until(float target_time, float step_rate) { } } for (const auto &item : scene_effects) { - item->effect->compute(encoder, t - item->start_time, beat, 0.0f, aspect_ratio); + item->effect->compute(encoder, t - item->start_time, beat, 0.0f, + aspect_ratio); } WGPUCommandBuffer commands = wgpuCommandEncoderFinish(encoder, nullptr); wgpuQueueSubmit(queue, 1, &commands); diff --git a/src/gpu/effect.h b/src/gpu/effect.h index 5f49041..ba569c2 100644 --- a/src/gpu/effect.h +++ b/src/gpu/effect.h @@ -22,10 +22,13 @@ public: virtual ~Effect() = default; // One-time setup (load assets, create buffers). - virtual void init(MainSequence *demo) { (void)demo; } + virtual void init(MainSequence *demo) { + (void)demo; + } // Called when the effect starts playing in a sequence segment. - virtual void start() {} + virtual void start() { + } // Dispatch compute shaders. virtual void compute(WGPUCommandEncoder encoder, float time, float beat, @@ -42,19 +45,25 @@ public: float intensity, float aspect_ratio) = 0; // Called when the effect finishes in a sequence segment. - virtual void end() {} + virtual void end() { + } bool is_initialized = false; - virtual bool is_post_process() const { return false; } + virtual bool is_post_process() const { + return false; + } }; // Base class for all post-processing effects class PostProcessEffect : public Effect { public: - bool is_post_process() const override { return true; } + bool is_post_process() const override { + return true; + } // Post-process effects don't have a compute phase by default - void compute(WGPUCommandEncoder, float, float, float, float) override {} + void compute(WGPUCommandEncoder, float, float, float, float) override { + } // Fullscreen quad render void render(WGPURenderPassEncoder pass, float time, float beat, diff --git a/src/gpu/gpu.cc b/src/gpu/gpu.cc index db79b9d..b9545bf 100644 --- a/src/gpu/gpu.cc +++ b/src/gpu/gpu.cc @@ -3,9 +3,9 @@ // Driven by audio peaks for synchronized visual effects. #include "gpu.h" -#include "platform.h" #include "demo_effects.h" #include "effect.h" +#include "platform.h" #include #include @@ -23,19 +23,21 @@ // --- WebGPU Headers & Compatibility --- #if defined(DEMO_CROSS_COMPILE_WIN32) // Renamed Types/Enums -#define WGPUSType_ShaderSourceWGSL WGPUSType_ShaderModuleWGSLDescriptor -using WGPUShaderSourceWGSL = WGPUShaderModuleWGSLDescriptor; -#define WGPUSurfaceGetCurrentTextureStatus_SuccessOptimal WGPUSurfaceGetCurrentTextureStatus_Success -#define WGPUSurfaceGetCurrentTextureStatus_SuccessSuboptimal WGPUSurfaceGetCurrentTextureStatus_Success +#define WGPUSurfaceGetCurrentTextureStatus_SuccessOptimal \ + WGPUSurfaceGetCurrentTextureStatus_Success +#define WGPUSurfaceGetCurrentTextureStatus_SuccessSuboptimal \ + WGPUSurfaceGetCurrentTextureStatus_Success #define WGPUCallbackMode_WaitAnyOnly 0 -static void wgpuInstanceWaitAny(WGPUInstance instance, size_t, void *, uint64_t) { +static void wgpuInstanceWaitAny(WGPUInstance instance, size_t, void *, + uint64_t) { wgpuInstanceProcessEvents(instance); } static void set_error_callback(WGPUDevice device, WGPUErrorCallback callback) { wgpuDeviceSetUncapturedErrorCallback(device, callback, nullptr); } #else -static void set_error_callback(WGPUDevice device, WGPUUncapturedErrorCallback callback) { +static void set_error_callback(WGPUDevice device, + WGPUUncapturedErrorCallback callback) { // Handled in descriptor for new API. } #endif diff --git a/src/gpu/gpu.h b/src/gpu/gpu.h index dd4fbd7..8aa290a 100644 --- a/src/gpu/gpu.h +++ b/src/gpu/gpu.h @@ -13,19 +13,27 @@ #include #include using WGPUStringView = const char *; -static inline const char *str_view(const char *str) { return str; } -static inline const char *label_view(const char *str) { return str; } +static inline const char *str_view(const char *str) { + return str; +} +static inline const char *label_view(const char *str) { + return str; +} +#define WGPUSType_ShaderSourceWGSL WGPUSType_ShaderModuleWGSLDescriptor +using WGPUShaderSourceWGSL = WGPUShaderModuleWGSLDescriptor; #else // Native (macOS/Linux) using newer wgpu-native #include #include static inline WGPUStringView str_view(const char *str) { - if (!str) return {nullptr, 0}; + if (!str) + return {nullptr, 0}; return {str, strlen(str)}; } static inline WGPUStringView label_view(const char *str) { #ifndef STRIP_ALL - if (!str) return {nullptr, 0}; + if (!str) + return {nullptr, 0}; return {str, strlen(str)}; #else (void)str; @@ -78,7 +86,8 @@ GpuBuffer gpu_create_buffer(WGPUDevice device, size_t size, uint32_t usage, ComputePass gpu_create_compute_pass(WGPUDevice device, const char *shader_code, ResourceBinding *bindings, int num_bindings); -RenderPass gpu_create_render_pass(WGPUDevice device, - WGPUTextureFormat format, // Needed for render pipeline - const char *shader_code, - ResourceBinding *bindings, int num_bindings); +RenderPass +gpu_create_render_pass(WGPUDevice device, + WGPUTextureFormat format, // Needed for render pipeline + const char *shader_code, ResourceBinding *bindings, + int num_bindings); -- cgit v1.2.3