git.lucas.co / cce-ui
GPU-accelerated UI toolkit (Vulkan)
git clone https://git.lucas.co/cce-ui.git

src/vk/glyph.wgsl (1.6K)

 1 // Glyph-atlas pipeline for the ash text stage. Mask glyphs are stored as
 2 // white-with-alpha texels, color (emoji) glyphs as-is with a white vertex
 3 // color — one multiply covers both.
 4 
 5 @group(0) @binding(0) var t_atlas: texture_2d<f32>;
 6 @group(0) @binding(1) var s_atlas: sampler;
 7 
 8 struct VertexOutput {
 9     @builtin(position) clip_position: vec4f,
10     @location(0) uv: vec2f,
11     @location(1) color: vec4f,
12     @location(2) clip_circle: vec3f,
13     @location(3) clip_extents: vec2f,
14 }
15 
16 @vertex
17 fn vs_main(
18     @location(0) position: vec2f,
19     @location(1) uv: vec2f,
20     @location(2) color: vec4f,
21     @location(3) clip_circle: vec3f,
22     @location(4) clip_extents: vec2f,
23 ) -> VertexOutput {
24     var out: VertexOutput;
25     out.clip_position = vec4f(position, 0.0, 1.0);
26     out.uv = uv;
27     out.color = color;
28     out.clip_circle = clip_circle;
29     out.clip_extents = clip_extents;
30     return out;
31 }
32 
33 @fragment
34 fn fs_main(in: VertexOutput) -> @location(0) vec4f {
35     // Rounded-rect SDF clip in framebuffer px: center clip_circle.xy, corner radius
36     // clip_circle.z, inner-box half-size clip_extents. Zero extents degenerate to the
37     // plain circle clip (the circular network pane's curved rim labels); a non-zero
38     // box clips plate children at the plate's rounded corners.
39     if (in.clip_circle.z > 0.0) {
40         let q = abs(in.clip_position.xy - in.clip_circle.xy) - in.clip_extents;
41         let d = length(max(q, vec2f(0.0))) - in.clip_circle.z;
42         if (d > 0.0) {
43             discard;
44         }
45     }
46     return in.color * textureSample(t_atlas, s_atlas, in.uv);
47 }