1use super::{ShaderGraph, ShaderParameter, ParameterValue};
7use super::nodes::NodeType;
8use crate::math::MathFunction;
9
10pub struct ShaderPreset;
11
12impl ShaderPreset {
13 pub fn void_protocol() -> ShaderGraph {
18 let mut g = ShaderGraph::new("void_protocol");
19
20 let uv = g.add_node_at(NodeType::UvCoord, 0.0, 0.0);
22 let time = g.add_node_at(NodeType::Time, 0.0, 80.0);
23
24 let time_scale = g.add_node_at(NodeType::ConstFloat(0.3), 200.0, 80.0);
26 let t_scaled = g.add_node_at(NodeType::Multiply, 400.0, 80.0);
27 let _ = g.connect(time, 0, t_scaled, 0);
28 let _ = g.connect(time_scale, 0, t_scaled, 1);
29
30 let uv_offset = g.add_node_at(NodeType::CombineVec2, 300.0, 0.0);
32 let sin_t = g.add_node_at(NodeType::Sin, 500.0, 40.0);
33 let _ = g.connect(t_scaled, 0, sin_t, 0);
34 let lorenz = g.add_node_at(NodeType::LorenzAttractor, 600.0, 0.0);
38 let _ = g.connect(uv, 0, lorenz, 0);
39 let _ = g.connect(t_scaled,0, lorenz, 1);
40
41 let mandel = g.add_node_at(NodeType::Mandelbrot, 600.0, 150.0);
43 let zoom = g.add_node_at(NodeType::Uniform("u_void_zoom".to_string(), super::nodes::SocketType::Float), 400.0, 200.0);
44 let _ = g.connect(uv, 0, mandel, 0);
45 let _ = g.connect(zoom, 0, mandel, 2);
46
47 let mix_lm = g.add_node_at(NodeType::Mix, 800.0, 75.0);
49 let mix_t = g.add_node_at(NodeType::ConstFloat(0.4), 600.0, 300.0);
50 let _ = g.connect(lorenz, 0, mix_lm, 0);
51 let _ = g.connect(mandel, 0, mix_lm, 1);
52 let _ = g.connect(mix_t, 0, mix_lm, 2);
53
54 let hsv_h = g.add_node_at(NodeType::Remap, 1000.0, 0.0);
56 let h_min = g.add_node_at(NodeType::ConstFloat(0.65), 800.0, -80.0);
57 let h_max = g.add_node_at(NodeType::ConstFloat(0.85), 800.0, -160.0);
58 let _ = g.connect(mix_lm, 0, hsv_h, 0);
59 let _ = g.connect(h_min, 0, hsv_h, 3);
60 let _ = g.connect(h_max, 0, hsv_h, 4);
61
62 let sat = g.add_node_at(NodeType::ConstFloat(0.9), 1000.0, 80.0);
63 let val = g.add_node_at(NodeType::ConstFloat(0.8), 1000.0, 160.0);
64 let hsv_rgb = g.add_node_at(NodeType::CombineVec3, 1200.0, 80.0);
65 let _ = g.connect(hsv_h, 0, hsv_rgb, 0);
66 let _ = g.connect(sat, 0, hsv_rgb, 1);
67 let _ = g.connect(val, 0, hsv_rgb, 2);
68 let to_rgb = g.add_node_at(NodeType::HsvToRgb, 1400.0, 80.0);
69 let _ = g.connect(hsv_rgb, 0, to_rgb, 0);
70
71 let vig = g.add_node_at(NodeType::Vignette, 1200.0, 250.0);
73 let vig_str = g.add_node_at(NodeType::ConstFloat(0.6), 1000.0, 320.0);
74 let _ = g.connect(uv, 0, vig, 0);
75 let _ = g.connect(vig_str, 0, vig, 1);
76
77 let mul_vig = g.add_node_at(NodeType::Multiply, 1600.0, 80.0);
79 let _ = g.connect(to_rgb, 0, mul_vig, 0);
80 let _ = g.connect(vig, 0, mul_vig, 1);
81
82 let alpha = g.add_node_at(NodeType::ConstFloat(1.0), 1600.0, 250.0);
84 let combine = g.add_node_at(NodeType::CombineVec4, 1800.0, 150.0);
85 let _ = g.connect(mul_vig, 0, combine, 0);
86 let _ = g.connect(alpha, 0, combine, 1);
87
88 let out = g.add_node_at(NodeType::OutputColor, 2000.0, 150.0);
89 g.set_output(out);
90 let _ = g.connect(combine, 0, out, 0);
91
92 g.add_parameter(ShaderParameter {
93 name: "void_zoom".to_string(),
94 glsl_name: "u_void_zoom".to_string(),
95 value: ParameterValue::Float(1.0),
96 driver: Some(MathFunction::Sine { amplitude: 0.3, frequency: 0.5, phase: 0.0 }),
97 min: 0.1,
98 max: 3.0,
99 });
100
101 g
102 }
103
104 pub fn blood_pact() -> ShaderGraph {
106 let mut g = ShaderGraph::new("blood_pact");
107 let uv = g.add_node(NodeType::UvCoord);
108 let time = g.add_node(NodeType::Time);
109
110 let fbm = g.add_node(NodeType::Fbm);
112 let oct = g.add_node(NodeType::ConstFloat(5.0));
113 let lac = g.add_node(NodeType::ConstFloat(2.0));
114 let gain = g.add_node(NodeType::ConstFloat(0.5));
115 let _ = g.connect(uv, 0, fbm, 0);
116 let _ = g.connect(oct, 0, fbm, 1);
117 let _ = g.connect(lac, 0, fbm, 2);
118 let _ = g.connect(gain, 0, fbm, 3);
119
120 let t_slow = g.add_node(NodeType::Multiply);
122 let t_sc = g.add_node(NodeType::ConstFloat(0.15));
123 let _ = g.connect(time, 0, t_slow, 0);
124 let _ = g.connect(t_sc, 0, t_slow, 1);
125
126 let hue_base = g.add_node(NodeType::ConstFloat(0.0)); let hue = g.add_node(NodeType::Add);
130 let hue_var = g.add_node(NodeType::ConstFloat(0.03));
131 let _ = g.connect(hue_base, 0, hue, 0);
132 let _ = g.connect(hue_var, 0, hue, 1);
133
134 let sat_v = g.add_node(NodeType::ConstFloat(0.95));
135 let val_v = g.add_node(NodeType::Multiply);
136 let bright= g.add_node(NodeType::ConstFloat(0.8));
137 let _ = g.connect(fbm, 0, val_v, 0);
138 let _ = g.connect(bright,0, val_v, 1);
139
140 let hsv = g.add_node(NodeType::CombineVec3);
141 let _ = g.connect(hue, 0, hsv, 0);
142 let _ = g.connect(sat_v, 0, hsv, 1);
143 let _ = g.connect(val_v, 0, hsv, 2);
144
145 let rgb = g.add_node(NodeType::HsvToRgb);
146 let _ = g.connect(hsv, 0, rgb, 0);
147
148 let grain = g.add_node(NodeType::FilmGrain);
150 let grain_str = g.add_node(NodeType::ConstFloat(0.03));
151 let _ = g.connect(uv, 0, grain, 0);
152 let _ = g.connect(time, 0, grain, 1);
153 let _ = g.connect(grain_str, 0, grain, 2);
154
155 let rgb_grain = g.add_node(NodeType::CombineVec3);
156 let grain_v3 = g.add_node(NodeType::CombineVec3);
157 let add_grain = g.add_node(NodeType::Add);
159 let _ = g.connect(rgb, 0, add_grain, 0);
160 let _ = g.connect(grain, 0, add_grain, 1);
161
162 let alpha = g.add_node(NodeType::ConstFloat(1.0));
163 let out4 = g.add_node(NodeType::CombineVec4);
164 let _ = g.connect(add_grain, 0, out4, 0);
165 let _ = g.connect(alpha, 0, out4, 1);
166
167 let out = g.add_node(NodeType::OutputColor);
168 g.set_output(out);
169 let _ = g.connect(out4, 0, out, 0);
170
171 let _ = (rgb_grain, grain_v3, t_slow); g
173 }
174
175 pub fn emerald_engine() -> ShaderGraph {
177 let mut g = ShaderGraph::new("emerald_engine");
178 let uv = g.add_node(NodeType::UvCoord);
179 let time = g.add_node(NodeType::Time);
180
181 let grid_scale = g.add_node(NodeType::ConstFloat(15.0));
183 let grid = g.add_node(NodeType::Grid);
184 let _ = g.connect(uv, 0, grid, 0);
185 let _ = g.connect(grid_scale, 0, grid, 1);
186
187 let vor_scale = g.add_node(NodeType::ConstFloat(8.0));
188 let voronoi = g.add_node(NodeType::Voronoi);
189 let vor_jit = g.add_node(NodeType::ConstFloat(0.7));
190 let _ = g.connect(uv, 0, voronoi, 0);
191 let _ = g.connect(vor_scale, 0, voronoi, 1);
192 let _ = g.connect(vor_jit, 0, voronoi, 2);
193
194 let grid_mix = g.add_node(NodeType::Add);
196 let mix_w = g.add_node(NodeType::ConstFloat(0.5));
197 let _ = g.connect(grid, 0, grid_mix, 0);
198 let _ = g.connect(voronoi, 0, grid_mix, 1);
199
200 let em_low = g.add_node(NodeType::ConstVec3(0.0, 0.2, 0.05));
202 let em_high = g.add_node(NodeType::ConstVec3(0.1, 0.9, 0.3));
203 let em_mix = g.add_node(NodeType::Mix);
204 let _ = g.connect(em_low, 0, em_mix, 0);
205 let _ = g.connect(em_high, 0, em_mix, 1);
206 let _ = g.connect(grid_mix,0, em_mix, 2);
207
208 let t_fast = g.add_node(NodeType::Multiply);
210 let t_scale = g.add_node(NodeType::ConstFloat(2.0));
211 let _ = g.connect(time, 0, t_fast, 0);
212 let _ = g.connect(t_scale, 0, t_fast, 1);
213 let pulse = g.add_node(NodeType::Sin);
214 let _ = g.connect(t_fast, 0, pulse, 0);
215 let p_half = g.add_node(NodeType::Multiply);
216 let ph_c = g.add_node(NodeType::ConstFloat(0.1));
217 let _ = g.connect(pulse, 0, p_half, 0);
218 let _ = g.connect(ph_c, 0, p_half, 1);
219
220 let bright = g.add_node(NodeType::Add);
222 let _ = g.connect(em_mix, 0, bright, 0);
223 let _ = g.connect(p_half, 0, bright, 1);
224
225 let alpha = g.add_node(NodeType::ConstFloat(1.0));
226 let out4 = g.add_node(NodeType::CombineVec4);
227 let _ = g.connect(bright, 0, out4, 0);
228 let _ = g.connect(alpha, 0, out4, 1);
229
230 let out = g.add_node(NodeType::OutputColor);
231 g.set_output(out);
232 let _ = g.connect(out4, 0, out, 0);
233
234 let _ = mix_w;
235 g
236 }
237
238 pub fn corruption_high() -> ShaderGraph {
240 let mut g = ShaderGraph::new("corruption_high");
241 let uv = g.add_node(NodeType::UvCoord);
242 let time = g.add_node(NodeType::Time);
243
244 let julia = g.add_node(NodeType::Julia);
246 let maxitr = g.add_node(NodeType::ConstFloat(120.0));
247 let zoom = g.add_node(NodeType::ConstFloat(1.5));
248 let cx = g.add_node(NodeType::Uniform("u_corrupt_cx".to_string(), super::nodes::SocketType::Float));
249 let cy = g.add_node(NodeType::Uniform("u_corrupt_cy".to_string(), super::nodes::SocketType::Float));
250 let _ = g.connect(uv, 0, julia, 0);
251 let _ = g.connect(maxitr, 0, julia, 1);
252 let _ = g.connect(zoom, 0, julia, 2);
253 let _ = g.connect(cx, 0, julia, 3);
254 let _ = g.connect(cy, 0, julia, 4);
255
256 let hue_base = g.add_node(NodeType::ConstFloat(0.75)); let hue = g.add_node(NodeType::Add);
259 let hue_var = g.add_node(NodeType::Multiply);
260 let julia_scaled = g.add_node(NodeType::Multiply);
261 let j_scale = g.add_node(NodeType::ConstFloat(0.1));
262 let _ = g.connect(julia, 0, julia_scaled, 0);
263 let _ = g.connect(j_scale,0, julia_scaled, 1);
264 let _ = g.connect(hue_base, 0, hue, 0);
265 let _ = g.connect(julia_scaled, 0, hue, 1);
266 let _ = (hue_var,);
267
268 let sat = g.add_node(NodeType::ConstFloat(0.85));
269 let val = g.add_node(NodeType::Clamp);
270 let jv = g.add_node(NodeType::Multiply);
271 let jvc = g.add_node(NodeType::ConstFloat(0.9));
272 let _ = g.connect(julia, 0, jv, 0);
273 let _ = g.connect(jvc, 0, jv, 1);
274 let vmin = g.add_node(NodeType::ConstFloat(0.0));
275 let vmax = g.add_node(NodeType::ConstFloat(1.0));
276 let _ = g.connect(jv, 0, val, 0);
277 let _ = g.connect(vmin, 0, val, 1);
278 let _ = g.connect(vmax, 0, val, 2);
279
280 let hsv = g.add_node(NodeType::CombineVec3);
281 let _ = g.connect(hue, 0, hsv, 0);
282 let _ = g.connect(sat, 0, hsv, 1);
283 let _ = g.connect(val, 0, hsv, 2);
284 let rgb = g.add_node(NodeType::HsvToRgb);
285 let _ = g.connect(hsv, 0, rgb, 0);
286
287 let glitch = g.add_node(NodeType::GlitchOffset);
289 let gstr = g.add_node(NodeType::ConstFloat(0.4));
290 let _ = g.connect(uv, 0, glitch, 0);
291 let _ = g.connect(time, 0, glitch, 1);
292 let _ = g.connect(gstr, 0, glitch, 2);
293
294 let alpha = g.add_node(NodeType::ConstFloat(1.0));
295 let out4 = g.add_node(NodeType::CombineVec4);
296 let _ = g.connect(rgb, 0, out4, 0);
297 let _ = g.connect(alpha,0, out4, 1);
298
299 let out = g.add_node(NodeType::OutputColor);
300 g.set_output(out);
301 let _ = g.connect(out4, 0, out, 0);
302
303 g.add_parameter(ShaderParameter {
304 name: "corrupt_cx".to_string(),
305 glsl_name: "u_corrupt_cx".to_string(),
306 value: ParameterValue::Float(-0.7),
307 driver: Some(MathFunction::Sine { amplitude: 0.4, frequency: 0.2, phase: 0.0 }),
308 min: -2.0,
309 max: 2.0,
310 });
311 g.add_parameter(ShaderParameter {
312 name: "corrupt_cy".to_string(),
313 glsl_name: "u_corrupt_cy".to_string(),
314 value: ParameterValue::Float(0.27),
315 driver: Some(MathFunction::Cosine { amplitude: 0.3, frequency: 0.17, phase: 1.57 }),
316 min: -2.0,
317 max: 2.0,
318 });
319 g
320 }
321
322 pub fn null_fight() -> ShaderGraph {
324 let mut g = ShaderGraph::new("null_fight");
325 let uv = g.add_node(NodeType::UvCoord);
326 let time = g.add_node(NodeType::Time);
327
328 let star = g.add_node(NodeType::StarBurst);
330 let arms = g.add_node(NodeType::ConstFloat(12.0));
331 let sharp = g.add_node(NodeType::ConstFloat(0.8));
332 let _ = g.connect(uv, 0, star, 0);
333 let _ = g.connect(arms, 0, star, 1);
334 let _ = g.connect(sharp,0, star, 2);
335
336 let rings = g.add_node(NodeType::Rings);
338 let rcount= g.add_node(NodeType::ConstFloat(8.0));
339 let rwidth= g.add_node(NodeType::ConstFloat(0.3));
340 let _ = g.connect(uv, 0, rings, 0);
341 let _ = g.connect(rcount,0, rings, 1);
342 let _ = g.connect(rwidth,0, rings, 2);
343
344 let combined = g.add_node(NodeType::Max);
346 let _ = g.connect(star, 0, combined, 0);
347 let _ = g.connect(rings, 0, combined, 1);
348
349 let t_pulse = g.add_node(NodeType::Sin);
351 let _ = g.connect(time, 0, t_pulse, 0);
352 let t_remap = g.add_node(NodeType::Remap);
353 let rm1 = g.add_node(NodeType::ConstFloat(-1.0));
354 let rm2 = g.add_node(NodeType::ConstFloat(1.0));
355 let rm3 = g.add_node(NodeType::ConstFloat(0.7));
356 let rm4 = g.add_node(NodeType::ConstFloat(1.0));
357 let _ = g.connect(t_pulse, 0, t_remap, 0);
358 let _ = g.connect(rm1, 0, t_remap, 1);
359 let _ = g.connect(rm2, 0, t_remap, 2);
360 let _ = g.connect(rm3, 0, t_remap, 3);
361 let _ = g.connect(rm4, 0, t_remap, 4);
362
363 let brightness = g.add_node(NodeType::Multiply);
364 let _ = g.connect(combined, 0, brightness, 0);
365 let _ = g.connect(t_remap, 0, brightness, 1);
366
367 let white = g.add_node(NodeType::ConstVec3(1.0, 1.0, 1.0));
369 let color = g.add_node(NodeType::Multiply);
370 let _ = g.connect(white, 0, color, 0);
371 let _ = g.connect(brightness,0, color, 1);
372
373 let alpha = g.add_node(NodeType::ConstFloat(1.0));
374 let out4 = g.add_node(NodeType::CombineVec4);
375 let _ = g.connect(color, 0, out4, 0);
376 let _ = g.connect(alpha, 0, out4, 1);
377
378 let out = g.add_node(NodeType::OutputColor);
379 g.set_output(out);
380 let _ = g.connect(out4, 0, out, 0);
381 g
382 }
383
384 pub fn paradox_invert() -> ShaderGraph {
386 let mut g = ShaderGraph::new("paradox_invert");
387 let uv = g.add_node(NodeType::UvCoord);
388 let time = g.add_node(NodeType::Time);
389
390 let chroma = g.add_node(NodeType::ChromaticAberration);
392 let c_str = g.add_node(NodeType::ConstFloat(0.015));
393 let _ = g.connect(uv, 0, chroma, 0);
394 let _ = g.connect(c_str, 0, chroma, 1);
395
396 let barrel = g.add_node(NodeType::BarrelDistort);
398 let b_str = g.add_node(NodeType::ConstFloat(-0.3));
399 let _ = g.connect(chroma, 0, barrel, 0);
400 let _ = g.connect(b_str, 0, barrel, 1);
401
402 let fbm = g.add_node(NodeType::Fbm);
404 let oct = g.add_node(NodeType::ConstFloat(3.0));
405 let lac = g.add_node(NodeType::ConstFloat(2.0));
406 let gain = g.add_node(NodeType::ConstFloat(0.6));
407 let _ = g.connect(barrel, 0, fbm, 0);
408 let _ = g.connect(oct, 0, fbm, 1);
409 let _ = g.connect(lac, 0, fbm, 2);
410 let _ = g.connect(gain, 0, fbm, 3);
411
412 let inv = g.add_node(NodeType::OneMinus);
414 let _ = g.connect(fbm, 0, inv, 0);
415
416 let hue_rot = g.add_node(NodeType::HueRotate);
418 let base_col= g.add_node(NodeType::ConstVec3(0.5, 0.2, 0.8));
419 let time_deg= g.add_node(NodeType::Multiply);
420 let deg_c = g.add_node(NodeType::ConstFloat(90.0));
421 let _ = g.connect(time, 0, time_deg, 0);
422 let _ = g.connect(deg_c, 0, time_deg, 1);
423 let _ = g.connect(base_col, 0, hue_rot, 0);
424 let _ = g.connect(time_deg, 0, hue_rot, 1);
425
426 let final_col = g.add_node(NodeType::Multiply);
428 let _ = g.connect(hue_rot, 0, final_col, 0);
429 let _ = g.connect(inv, 0, final_col, 1);
430
431 let alpha = g.add_node(NodeType::ConstFloat(1.0));
432 let out4 = g.add_node(NodeType::CombineVec4);
433 let _ = g.connect(final_col, 0, out4, 0);
434 let _ = g.connect(alpha, 0, out4, 1);
435
436 let out = g.add_node(NodeType::OutputColor);
437 g.set_output(out);
438 let _ = g.connect(out4, 0, out, 0);
439 g
440 }
441
442 pub fn fire_elemental() -> ShaderGraph {
444 let mut g = ShaderGraph::new("fire_elemental");
445 let uv = g.add_node(NodeType::UvCoord);
446 let time = g.add_node(NodeType::Time);
447
448 let haze = g.add_node(NodeType::HeatHaze);
450 let hz_str= g.add_node(NodeType::ConstFloat(0.03));
451 let hz_spd= g.add_node(NodeType::ConstFloat(2.0));
452 let _ = g.connect(uv, 0, haze, 0);
453 let _ = g.connect(time, 0, haze, 1);
454 let _ = g.connect(hz_str,0, haze, 2);
455 let _ = g.connect(hz_spd,0, haze, 3);
456
457 let fbm = g.add_node(NodeType::Fbm);
459 let oct = g.add_node(NodeType::ConstFloat(4.0));
460 let lac = g.add_node(NodeType::ConstFloat(2.2));
461 let gn = g.add_node(NodeType::ConstFloat(0.5));
462 let _ = g.connect(haze, 0, fbm, 0);
463 let _ = g.connect(oct, 0, fbm, 1);
464 let _ = g.connect(lac, 0, fbm, 2);
465 let _ = g.connect(gn, 0, fbm, 3);
466
467 let fire_low = g.add_node(NodeType::ConstVec3(0.8, 0.1, 0.0));
469 let fire_high = g.add_node(NodeType::ConstVec3(1.0, 0.9, 0.1));
470 let fire_mix = g.add_node(NodeType::Mix);
471 let _ = g.connect(fire_low, 0, fire_mix, 0);
472 let _ = g.connect(fire_high, 0, fire_mix, 1);
473 let _ = g.connect(fbm, 0, fire_mix, 2);
474
475 let glow = g.add_node(NodeType::Multiply);
477 let glow_c = g.add_node(NodeType::ConstFloat(1.8));
478 let _ = g.connect(fire_mix, 0, glow, 0);
479 let _ = g.connect(glow_c, 0, glow, 1);
480
481 let alpha = g.add_node(NodeType::ConstFloat(1.0));
482 let out4 = g.add_node(NodeType::CombineVec4);
483 let _ = g.connect(glow, 0, out4, 0);
484 let _ = g.connect(alpha, 0, out4, 1);
485
486 let out = g.add_node(NodeType::OutputColor);
487 g.set_output(out);
488 let _ = g.connect(out4, 0, out, 0);
489 g
490 }
491
492 pub fn ice_elemental() -> ShaderGraph {
494 let mut g = ShaderGraph::new("ice_elemental");
495 let uv = g.add_node(NodeType::UvCoord);
496 let time = g.add_node(NodeType::Time);
497
498 let vor = g.add_node(NodeType::Voronoi);
500 let v_sc = g.add_node(NodeType::ConstFloat(12.0));
501 let v_jit = g.add_node(NodeType::ConstFloat(0.5));
502 let _ = g.connect(uv, 0, vor, 0);
503 let _ = g.connect(v_sc, 0, vor, 1);
504 let _ = g.connect(v_jit,0, vor, 2);
505
506 let rings = g.add_node(NodeType::Rings);
508 let r_cnt = g.add_node(NodeType::ConstFloat(6.0));
509 let r_wid = g.add_node(NodeType::ConstFloat(0.4));
510 let _ = g.connect(uv, 0, rings, 0);
511 let _ = g.connect(r_cnt,0, rings, 1);
512 let _ = g.connect(r_wid,0, rings, 2);
513
514 let combined = g.add_node(NodeType::Add);
516 let _ = g.connect(vor, 0, combined, 0);
517 let _ = g.connect(rings,0, combined, 1);
518
519 let shimmer = g.add_node(NodeType::Sin);
521 let t_fast = g.add_node(NodeType::Multiply);
522 let t_sc = g.add_node(NodeType::ConstFloat(3.0));
523 let _ = g.connect(time, 0, t_fast, 0);
524 let _ = g.connect(t_sc, 0, t_fast, 1);
525 let _ = g.connect(t_fast, 0, shimmer, 0);
526
527 let shim_m = g.add_node(NodeType::Multiply);
528 let shim_c = g.add_node(NodeType::ConstFloat(0.1));
529 let _ = g.connect(shimmer, 0, shim_m, 0);
530 let _ = g.connect(shim_c, 0, shim_m, 1);
531 let with_shim = g.add_node(NodeType::Add);
532 let _ = g.connect(combined, 0, with_shim, 0);
533 let _ = g.connect(shim_m, 0, with_shim, 1);
534
535 let ice_dark = g.add_node(NodeType::ConstVec3(0.05, 0.2, 0.5));
537 let ice_light = g.add_node(NodeType::ConstVec3(0.8, 0.95, 1.0));
538 let ice_mix = g.add_node(NodeType::Mix);
539 let _ = g.connect(ice_dark, 0, ice_mix, 0);
540 let _ = g.connect(ice_light, 0, ice_mix, 1);
541 let _ = g.connect(with_shim, 0, ice_mix, 2);
542
543 let alpha = g.add_node(NodeType::ConstFloat(1.0));
544 let out4 = g.add_node(NodeType::CombineVec4);
545 let _ = g.connect(ice_mix, 0, out4, 0);
546 let _ = g.connect(alpha, 0, out4, 1);
547
548 let out = g.add_node(NodeType::OutputColor);
549 g.set_output(out);
550 let _ = g.connect(out4, 0, out, 0);
551 g
552 }
553
554 pub fn aurora() -> ShaderGraph {
556 let mut g = ShaderGraph::new("aurora");
557 let uv = g.add_node(NodeType::UvCoord);
558 let time = g.add_node(NodeType::Time);
559
560 let t_slow = g.add_node(NodeType::Multiply);
562 let ts_c = g.add_node(NodeType::ConstFloat(0.2));
563 let _ = g.connect(time, 0, t_slow, 0);
564 let _ = g.connect(ts_c, 0, t_slow, 1);
565
566 let fbm = g.add_node(NodeType::Fbm);
568 let oct = g.add_node(NodeType::ConstFloat(4.0));
569 let lac = g.add_node(NodeType::ConstFloat(2.0));
570 let gn = g.add_node(NodeType::ConstFloat(0.5));
571 let _ = g.connect(uv, 0, fbm, 0);
572 let _ = g.connect(oct, 0, fbm, 1);
573 let _ = g.connect(lac, 0, fbm, 2);
574 let _ = g.connect(gn, 0, fbm, 3);
575
576 let band_sin = g.add_node(NodeType::Sin);
578 let band_mul = g.add_node(NodeType::Multiply);
579 let band_c = g.add_node(NodeType::ConstFloat(8.0));
580 let _ = g.connect(fbm, 0, band_mul, 0);
581 let _ = g.connect(band_c, 0, band_mul, 1);
582 let _ = g.connect(band_mul, 0, band_sin, 0);
583
584 let hue = g.add_node(NodeType::Remap);
586 let h_min = g.add_node(NodeType::ConstFloat(0.3));
587 let h_max = g.add_node(NodeType::ConstFloat(0.8));
588 let _ = g.connect(band_sin, 0, hue, 0);
589 let _ = g.connect(h_min, 0, hue, 3);
590 let _ = g.connect(h_max, 0, hue, 4);
591
592 let sat = g.add_node(NodeType::ConstFloat(0.7));
593 let val = g.add_node(NodeType::ConstFloat(0.9));
594 let hsv = g.add_node(NodeType::CombineVec3);
595 let _ = g.connect(hue, 0, hsv, 0);
596 let _ = g.connect(sat, 0, hsv, 1);
597 let _ = g.connect(val, 0, hsv, 2);
598 let rgb = g.add_node(NodeType::HsvToRgb);
599 let _ = g.connect(hsv, 0, rgb, 0);
600
601 let alpha = g.add_node(NodeType::ConstFloat(1.0));
602 let out4 = g.add_node(NodeType::CombineVec4);
603 let _ = g.connect(rgb, 0, out4, 0);
604 let _ = g.connect(alpha, 0, out4, 1);
605
606 let out = g.add_node(NodeType::OutputColor);
607 g.set_output(out);
608 let _ = g.connect(out4, 0, out, 0);
609
610 let _ = t_slow;
611 g
612 }
613
614 pub fn static_noise() -> ShaderGraph {
616 let mut g = ShaderGraph::new("static_noise");
617 let uv = g.add_node(NodeType::UvCoord);
618 let time = g.add_node(NodeType::Time);
619
620 let grain = g.add_node(NodeType::FilmGrain);
621 let grain_str = g.add_node(NodeType::ConstFloat(2.0));
622 let _ = g.connect(uv, 0, grain, 0);
623 let _ = g.connect(time, 0, grain, 1);
624 let _ = g.connect(grain_str, 0, grain, 2);
625
626 let scanlines = g.add_node(NodeType::Scanlines);
627 let scan_int = g.add_node(NodeType::ConstFloat(0.4));
628 let scan_cnt = g.add_node(NodeType::ConstFloat(400.0));
629 let _ = g.connect(uv, 0, scanlines, 0);
630 let _ = g.connect(scan_int, 0, scanlines, 1);
631 let _ = g.connect(scan_cnt, 0, scanlines, 2);
632
633 let combined = g.add_node(NodeType::Multiply);
634 let _ = g.connect(grain, 0, combined, 0);
635 let _ = g.connect(scanlines,0, combined, 1);
636
637 let sat_node = g.add_node(NodeType::Saturate);
638 let _ = g.connect(combined, 0, sat_node, 0);
639
640 let gray = g.add_node(NodeType::CombineVec3);
642 let _ = g.connect(sat_node, 0, gray, 0);
643 let _ = g.connect(sat_node, 0, gray, 1);
644 let _ = g.connect(sat_node, 0, gray, 2);
645
646 let alpha = g.add_node(NodeType::ConstFloat(1.0));
647 let out4 = g.add_node(NodeType::CombineVec4);
648 let _ = g.connect(gray, 0, out4, 0);
649 let _ = g.connect(alpha, 0, out4, 1);
650
651 let out = g.add_node(NodeType::OutputColor);
652 g.set_output(out);
653 let _ = g.connect(out4, 0, out, 0);
654 g
655 }
656
657 pub fn all_names() -> Vec<&'static str> {
659 vec![
660 "void_protocol",
661 "blood_pact",
662 "emerald_engine",
663 "corruption_high",
664 "null_fight",
665 "paradox_invert",
666 "fire_elemental",
667 "ice_elemental",
668 "aurora",
669 "static_noise",
670 ]
671 }
672
673 pub fn by_name(name: &str) -> Option<ShaderGraph> {
675 match name {
676 "void_protocol" => Some(Self::void_protocol()),
677 "blood_pact" => Some(Self::blood_pact()),
678 "emerald_engine" => Some(Self::emerald_engine()),
679 "corruption_high" => Some(Self::corruption_high()),
680 "null_fight" => Some(Self::null_fight()),
681 "paradox_invert" => Some(Self::paradox_invert()),
682 "fire_elemental" => Some(Self::fire_elemental()),
683 "ice_elemental" => Some(Self::ice_elemental()),
684 "aurora" => Some(Self::aurora()),
685 "static_noise" => Some(Self::static_noise()),
686 _ => None,
687 }
688 }
689}
690
691#[cfg(test)]
694mod tests {
695 use super::*;
696
697 #[test]
698 fn test_all_presets_compile_without_panic() {
699 for name in ShaderPreset::all_names() {
700 let graph = ShaderPreset::by_name(name).unwrap();
701 assert!(!graph.name.is_empty());
702 assert!(graph.output_node.is_some(), "Preset {} has no output node", name);
703 let s = graph.stats();
705 assert!(s.node_count > 3, "Preset {} has too few nodes", name);
706 }
707 }
708
709 #[test]
710 fn test_void_protocol_has_parameters() {
711 let g = ShaderPreset::void_protocol();
712 assert!(!g.parameters.is_empty());
713 assert!(g.parameters.iter().any(|p| p.name == "void_zoom"));
714 }
715
716 #[test]
717 fn test_corruption_high_parameters() {
718 let g = ShaderPreset::corruption_high();
719 assert!(g.parameters.iter().any(|p| p.name == "corrupt_cx"));
720 assert!(g.parameters.iter().any(|p| p.name == "corrupt_cy"));
721 }
722
723 #[test]
724 fn test_by_name_unknown_returns_none() {
725 assert!(ShaderPreset::by_name("does_not_exist").is_none());
726 }
727
728 #[test]
729 fn test_all_names_count() {
730 assert_eq!(ShaderPreset::all_names().len(), 10);
731 }
732
733 #[test]
734 fn test_preset_topological_order() {
735 for name in ShaderPreset::all_names() {
736 let graph = ShaderPreset::by_name(name).unwrap();
737 let order = graph.topological_order();
738 assert!(order.is_ok(), "Preset {} has cycles or invalid graph", name);
739 }
740 }
741}