stevenkhan commited on
Commit
37cfbbb
·
verified ·
1 Parent(s): 81568be

Upload spectral-render/src/shaders.rs

Browse files
Files changed (1) hide show
  1. spectral-render/src/shaders.rs +146 -0
spectral-render/src/shaders.rs ADDED
@@ -0,0 +1,146 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ pub const BG_VERTEX: &str = r#"
2
+ struct BgInstance {
3
+ col: u32, row: u32,
4
+ bg_r: u32, bg_g: u32, bg_b: u32, bg_a: u32,
5
+ };
6
+ @group(0) @binding(0)
7
+ var<storage, read> instances: array<BgInstance>;
8
+
9
+ struct Uniforms {
10
+ cell_width: f32, cell_height: f32,
11
+ screen_cols: u32, screen_rows: u32,
12
+ };
13
+ @group(0) @binding(1)
14
+ var<uniform> uniforms: Uniforms;
15
+
16
+ struct VertexOutput {
17
+ @builtin(position) position: vec4<f32>,
18
+ @location(0) color: vec4<f32>,
19
+ };
20
+
21
+ @vertex
22
+ fn main(@builtin(vertex_index) vertex_idx: u32, @builtin(instance_index) instance_idx: u32) -> VertexOutput {
23
+ let cell = instances[instance_idx];
24
+ var corners = array<vec2<f32>, 6>(
25
+ vec2<f32>(0.0, 0.0), vec2<f32>(1.0, 0.0), vec2<f32>(0.0, 1.0),
26
+ vec2<f32>(0.0, 1.0), vec2<f32>(1.0, 0.0), vec2<f32>(1.0, 1.0),
27
+ );
28
+ let corner = corners[vertex_idx];
29
+ let x = (f32(cell.col) + corner.x) * uniforms.cell_width;
30
+ let y = (f32(cell.row) + corner.y) * uniforms.cell_height;
31
+ let screen_w = f32(uniforms.screen_cols) * uniforms.cell_width;
32
+ let screen_h = f32(uniforms.screen_rows) * uniforms.cell_height;
33
+ let ndc_x = (x / screen_w) * 2.0 - 1.0;
34
+ let ndc_y = -((y / screen_h) * 2.0 - 1.0);
35
+ var out: VertexOutput;
36
+ out.position = vec4<f32>(ndc_x, ndc_y, 0.0, 1.0);
37
+ out.color = vec4<f32>(f32(cell.bg_r) / 255.0, f32(cell.bg_g) / 255.0, f32(cell.bg_b) / 255.0, f32(cell.bg_a) / 255.0);
38
+ return out;
39
+ }
40
+ "#;
41
+
42
+ pub const BG_FRAGMENT: &str = r#"
43
+ struct VertexOutput {
44
+ @builtin(position) position: vec4<f32>,
45
+ @location(0) color: vec4<f32>,
46
+ };
47
+ @fragment
48
+ fn main(in: VertexOutput) -> @location(0) vec4<f32> {
49
+ return in.color;
50
+ }
51
+ "#;
52
+
53
+ pub const TEXT_VERTEX: &str = r#"
54
+ struct TextInstance {
55
+ col: f32, row: f32,
56
+ bearing_x: f32, bearing_y: f32,
57
+ glyph_w: f32, glyph_h: f32,
58
+ atlas_x: f32, atlas_y: f32,
59
+ atlas_w: f32, atlas_h: f32,
60
+ fg_r: u32, fg_g: u32, fg_b: u32,
61
+ flags: u32, thickening: f32,
62
+ };
63
+ @group(0) @binding(0)
64
+ var<storage, read> instances: array<TextInstance>;
65
+
66
+ struct Uniforms {
67
+ cell_width: f32, cell_height: f32,
68
+ atlas_size: f32,
69
+ screen_cols: u32, screen_rows: u32,
70
+ };
71
+ @group(0) @binding(1)
72
+ var<uniform> uniforms: Uniforms;
73
+
74
+ struct VertexOutput {
75
+ @builtin(position) position: vec4<f32>,
76
+ @location(0) uv: vec2<f32>,
77
+ @location(1) fg_color: vec4<f32>,
78
+ @location(2) atlas_uv: vec4<f32>,
79
+ @location(3) thickening: f32,
80
+ @location(4) flags: u32,
81
+ };
82
+
83
+ @vertex
84
+ fn main(@builtin(vertex_index) vertex_idx: u32, @builtin(instance_index) instance_idx: u32) -> VertexOutput {
85
+ let cell = instances[instance_idx];
86
+ var corners = array<vec2<f32>, 6>(
87
+ vec2<f32>(0.0, 0.0), vec2<f32>(1.0, 0.0), vec2<f32>(0.0, 1.0),
88
+ vec2<f32>(0.0, 1.0), vec2<f32>(1.0, 0.0), vec2<f32>(1.0, 1.0),
89
+ );
90
+ let corner = corners[vertex_idx];
91
+ let x = (cell.col * uniforms.cell_width) + cell.bearing_x + corner.x * cell.glyph_w;
92
+ let y = (cell.row * uniforms.cell_height) + cell.bearing_y + corner.y * cell.glyph_h;
93
+ let screen_w = f32(uniforms.screen_cols) * uniforms.cell_width;
94
+ let screen_h = f32(uniforms.screen_rows) * uniforms.cell_height;
95
+ let ndc_x = (x / screen_w) * 2.0 - 1.0;
96
+ let ndc_y = -((y / screen_h) * 2.0 - 1.0);
97
+ var out: VertexOutput;
98
+ out.position = vec4<f32>(ndc_x, ndc_y, 0.0, 1.0);
99
+ out.uv = corner;
100
+ out.fg_color = vec4<f32>(f32(cell.fg_r) / 255.0, f32(cell.fg_g) / 255.0, f32(cell.fg_b) / 255.0, 1.0);
101
+ let norm = uniforms.atlas_size;
102
+ out.atlas_uv = vec4<f32>(cell.atlas_x / norm, cell.atlas_y / norm, cell.atlas_w / norm, cell.atlas_h / norm);
103
+ out.thickening = cell.thickening;
104
+ out.flags = cell.flags;
105
+ return out;
106
+ }
107
+ "#;
108
+
109
+ pub const TEXT_FRAGMENT: &str = r#"
110
+ @group(0) @binding(2)
111
+ var atlas_sampler: sampler;
112
+ @group(0) @binding(3)
113
+ var atlas_texture: texture_2d<f32>;
114
+
115
+ struct VertexOutput {
116
+ @builtin(position) position: vec4<f32>,
117
+ @location(0) uv: vec2<f32>,
118
+ @location(1) fg_color: vec4<f32>,
119
+ @location(2) atlas_uv: vec4<f32>,
120
+ @location(3) thickening: f32,
121
+ @location(4) flags: u32,
122
+ };
123
+
124
+ fn median(r: f32, g: f32, b: f32) -> f32 {
125
+ return max(min(r, g), min(max(r, g), b));
126
+ }
127
+
128
+ @fragment
129
+ fn main(in: VertexOutput) -> @location(0) vec4<f32> {
130
+ let atlas_pos = vec2<f32>(
131
+ in.atlas_uv.x + in.uv.x * in.atlas_uv.z,
132
+ in.atlas_uv.y + in.uv.y * in.atlas_uv.w,
133
+ );
134
+ let sample = textureSample(atlas_texture, atlas_sampler, atlas_pos);
135
+ let sig_dist = median(sample.r, sample.g, sample.b);
136
+ let threshold = 0.5 - in.thickening * 0.15;
137
+ let smoothing = 0.05;
138
+ let opacity = smoothstep(threshold - smoothing, threshold + smoothing, sig_dist);
139
+ let is_colored = (in.flags & 0x0040u) != 0u;
140
+ if is_colored {
141
+ return vec4<f32>(sample.rgb, opacity);
142
+ } else {
143
+ return vec4<f32>(in.fg_color.rgb, opacity);
144
+ }
145
+ }
146
+ "#;