Enable multisampling (anti-aliasing)

Francesco Pasa 11 months ago

demo.c   M +7 -3

 8     options.clear_color.b = 0.02;
 9     AlbaWindow* window = create_window(&options);
10 
11+    float w, h;
12+    window_get_size(window, &w, &h);
13+    printf("%f %f\n", w, h);
14+
15     const float vertices[] = {
16         100, 100,
17-        100, 600,
18+        100, 400,
19         200, 100,
20         //
21-        0, 20,
22-        20, 0
23+        300, 150,
24+        150, 300
25     };
26     const float color[] = {
27         1.0, 0.0, 0.0, 1.0,

src/window.c   M +34 -5

 6 
 7 #include "GLFW/glfw3.h"
 8 #include "webgpu.h"
 9+#include "../cmake-build-debug/_deps/glfw-build/src/fractional-scale-v1-client-protocol.h"
10 
11 extern char _binary_shaders_wgsl_start[];
12 
146     // Rendering settings
147     pipleine_options.primitive.topology = WGPUPrimitiveTopology_TriangleList;
148     pipleine_options.primitive.frontFace = WGPUFrontFace_CCW; // counter clockwise
149-    pipleine_options.multisample.count = 1; // no anti-aliasing
150+    pipleine_options.multisample.count = 4;
151     pipleine_options.multisample.mask = 0xFFFFFFFF;
152 
153     // Vertex shader
206     pipleine_options.layout = configure_uniforms(window);
207 
208     window->pipeline = wgpuDeviceCreateRenderPipeline(window->device, &pipleine_options);
209+
210+    wgpuPipelineLayoutRelease(pipleine_options.layout);
211 }
212 
213 AlbaWindow* create_window(const AlbaWindowOptions* options)
288 
289 void window_release(AlbaWindow* window)
290 {
291+    wgpuBufferDestroy(window->uniforms);
292+    wgpuBufferRelease(window->uniforms);
293+
294     wgpuBufferDestroy(window->vertices);
295     wgpuBufferRelease(window->vertices);
296     float_array_release(&window->new_vertices);
303     wgpuBufferRelease(window->indices);
304     uint32_array_release(&window->new_indices);
305 
306+    wgpuBindGroupRelease(window->bind_group);
307     wgpuShaderModuleRelease(window->shaders);
308     wgpuRenderPipelineRelease(window->pipeline);
309     wgpuQueueRelease(window->queue);
399         window->dirty = 0;
400     }
401 
402+
403     WGPUSurfaceTexture frame;
404     wgpuSurfaceGetCurrentTexture(window->surface, &frame);
405     if (!frame_status_is_valid(window, frame))
414         return;
415     }
416 
417-    const WGPUTextureView view = wgpuTextureCreateView(frame.texture, NULL);
418-    if (view == NULL)
419+    WGPUTextureDescriptor texture_options = {0};
420+    texture_options.usage = WGPUTextureUsage_RenderAttachment;
421+    texture_options.format = WGPUTextureFormat_BGRA8UnormSrgb; // TODO: avoid hardcoding
422+    texture_options.dimension = WGPUTextureDimension_2D;
423+    texture_options.size.width = 800;
424+    texture_options.size.height = 600;
425+    texture_options.size.depthOrArrayLayers = 1;
426+    texture_options.sampleCount = 4;
427+    texture_options.mipLevelCount = 1;
428+    const WGPUTexture texture = wgpuDeviceCreateTexture(window->device, &texture_options);
429+
430+    const WGPUTextureView frame_view = wgpuTextureCreateView(frame.texture, NULL);
431+    if (frame_view == NULL)
432     {
433         printf("warning: could not get frame view, dropping frame (%d)\n", frame.status);
434         return;
435     }
436 
437+    const WGPUTextureView texture_view = wgpuTextureCreateView(texture, NULL);
438+    if (texture_view == NULL)
439+    {
440+        printf("warning: could not get texture view, dropping frame\n");
441+        return;
442+    }
443+
444     const WGPUCommandEncoder encoder = wgpuDeviceCreateCommandEncoder(window->device, NULL);
445 
446     // Configures rendering
447     WGPURenderPassColorAttachment render_pass_attachment_options = {0};
448-    render_pass_attachment_options.view = view;
449+    render_pass_attachment_options.view = texture_view;
450     render_pass_attachment_options.loadOp = WGPULoadOp_Clear;
451     render_pass_attachment_options.storeOp = WGPUStoreOp_Store;
452+    render_pass_attachment_options.resolveTarget = frame_view;
453     copy_color(window->options.clear_color, &render_pass_attachment_options.clearValue);
454 
455     WGPURenderPassDescriptor render_pass_options = {0};
483     wgpuCommandBufferRelease(command);
484     wgpuRenderPassEncoderRelease(render_pass);
485     wgpuCommandEncoderRelease(encoder);
486-    wgpuTextureViewRelease(view);
487+    wgpuTextureViewRelease(texture_view);
488+    wgpuTextureViewRelease(frame_view);
489+    wgpuTextureRelease(texture);
490     wgpuTextureRelease(frame.texture);
491 }
492