@@ -455,6 +455,20 @@ fn remap_time(parent_t: f32, start_time: f32, end_time: f32) -> f32 {
455
455
return f32:: clamp ( ( parent_t - start_time) / duration, 0.0 , 1.0 ) ;
456
456
}
457
457
458
+ /// Alpha compositing using "over" operator
459
+ fn composite_layers < const N : usize > ( overlay_colors : & [ Vec4 ; N ] ) -> Vec4 {
460
+ let mut result = Vec4 :: ZERO ;
461
+ for i in ( 0 ..overlay_colors. len ( ) ) . rev ( ) {
462
+ let color = overlay_colors[ i] ;
463
+ let alpha = color. w ;
464
+ if alpha > 0.0 {
465
+ result = result + ( color * alpha * ( 1.0 - result. w ) ) ;
466
+ result. w += alpha * ( 1.0 - result. w ) ;
467
+ }
468
+ }
469
+ return result;
470
+ }
471
+
458
472
impl Inputs {
459
473
pub fn main_image ( & self , frag_color : & mut Vec4 , frag_coord : Vec2 ) {
460
474
// Get screen dimensions as Vec2.
@@ -470,8 +484,9 @@ impl Inputs {
470
484
471
485
let aspect = screen_xy / shorter_dim;
472
486
473
- let mut combined_mask: f32 = 0.0 ;
474
- let mut combined_debug_mask: f32 = 0.0 ;
487
+ let mut black_alpha: f32 = 0.0 ;
488
+ let mut debug_red_alpha: f32 = 0.0 ;
489
+ let mut debug_blue_alpha: f32 = 0.0 ;
475
490
476
491
let center = vec2 ( 0.0 , 0.0 ) ;
477
492
let bottom_middle = vec2 ( 0.0 , -aspect. y ) ;
@@ -494,37 +509,10 @@ impl Inputs {
494
509
let t_rotation = exp_time ( t_master, 0.6 ) ;
495
510
let t_trail_delayed = remap_time ( t_master, 0.4 , 1.0 ) ;
496
511
let t_trail = exp_time ( t_trail_delayed, 0.4 ) ;
497
- let t_assist_circle_delayed = remap_time ( t_master, 0.5 , 1.0 ) ;
512
+ let t_assist_circle_delayed = remap_time ( t_master, 0.5 , 0.9 ) ;
498
513
let t_assist_circle = exp_time ( t_assist_circle_delayed, 0.4 ) ;
499
514
//let t_exp = 1.0 - (-5.0 * t).exp();
500
515
501
- let m_sausage_filled_test = sdf_sausage_filled (
502
- uv,
503
- center,
504
- 45.0 * PI / 180.0 ,
505
- 270.0 * PI / 180.0 ,
506
- target_radius,
507
- target_stroke,
508
- 90.0 * PI / 180.0 ,
509
- 0.5 ,
510
- ) ;
511
- //combined_mask = combined_mask.max((1.0 - smoothstep(0.0, aa_width, m_sausage_filled_test.x)) * f32::clamp(m_sausage_filled_test.y, 0.1, 1.0));
512
- let m_sausage_outline_test = sdf_sausage_outline (
513
- uv,
514
- center,
515
- 45.0 * PI / 180.0 ,
516
- 270.0 * PI / 180.0 ,
517
- target_radius,
518
- target_stroke / 2.0 ,
519
- target_stroke,
520
- 90.0 * PI / 180.0 ,
521
- 0.5 ,
522
- ) ;
523
- /*combined_mask = combined_mask.max(
524
- (1.0 - smoothstep(0.0, aa_width, m_sausage_outline_test.x))
525
- * f32::clamp(m_sausage_outline_test.y, 0.1, 1.0),
526
- );*/
527
-
528
516
// rotating circles
529
517
let num_circles = 12 ;
530
518
let angle_between_circles = 2.0 * PI / num_circles as f32 ;
@@ -556,18 +544,25 @@ impl Inputs {
556
544
num_circles,
557
545
3 ,
558
546
) ;
559
- let m = sdf_circle_outline (
547
+
548
+ let m_start_circle = sdf_circle_outline (
560
549
uv,
561
550
target_rotating_circle. position ,
562
551
target_radius,
563
552
target_stroke,
564
553
) ;
565
- // Combine masks using max to create a single mask.
566
- //combined_mask = combined_mask.max(m);
554
+ debug_red_alpha = debug_red_alpha. max ( m_start_circle) ;
555
+ let m_middle_circle_path = sdf_circle_outline (
556
+ uv,
557
+ middle_circle_start_position,
558
+ middle_circle_start_radius,
559
+ target_stroke / 2.0 ,
560
+ ) ;
561
+ debug_red_alpha = debug_red_alpha. max ( m_middle_circle_path) ;
567
562
568
563
for i in 0 ..num_circles {
569
564
// Compute the position of the circle based on the angle and radius.
570
- let rotating_circle_result = rotating_discrete_circle (
565
+ let outer_discrete_circle = rotating_discrete_circle (
571
566
middle_circle_position,
572
567
middle_circle_radius,
573
568
-t_rotation * 5.0 ,
@@ -576,7 +571,7 @@ impl Inputs {
576
571
) ;
577
572
let m = sdf_circle_outline (
578
573
uv,
579
- rotating_circle_result . position - vec2 ( 0.1 , 0.0 ) ,
574
+ outer_discrete_circle . position - vec2 ( 0.1 , 0.0 ) ,
580
575
outer_circle_outer_radius,
581
576
target_stroke,
582
577
) ;
@@ -588,16 +583,16 @@ impl Inputs {
588
583
let m = sdf_sausage_outline (
589
584
uv,
590
585
middle_circle_position,
591
- rotating_circle_result . angle - trail_angular_extent / 2.0 ,
592
- rotating_circle_result . angle + trail_angular_extent / 2.0 ,
586
+ outer_discrete_circle . angle - trail_angular_extent / 2.0 ,
587
+ outer_discrete_circle . angle + trail_angular_extent / 2.0 ,
593
588
middle_circle_radius,
594
589
outer_circle_inner_radius,
595
590
outer_circle_outer_radius,
596
- rotating_circle_result . angle ,
591
+ outer_discrete_circle . angle ,
597
592
outer_circle_fade,
598
593
) ;
599
- combined_mask = combined_mask
600
- . max ( ( 1.0 - smoothstep ( 0.0 , aa_width, m. x ) ) * ( m. y + t_assist_circle) . min ( 1.0 ) ) ;
594
+ black_alpha =
595
+ black_alpha . max ( ( 1.0 - smoothstep ( 0.0 , aa_width, m. x ) ) * ( m. y + t_assist_circle) . min ( 1.0 ) ) ;
601
596
// * (m.y + 6.0 / 256.0));
602
597
603
598
let m = sdf_circle_outline (
@@ -606,17 +601,17 @@ impl Inputs {
606
601
middle_circle_radius,
607
602
outer_circle_outer_radius * 2.0 ,
608
603
) ;
609
- combined_mask = combined_mask . max ( ( smoothstep ( 0.0 , aa_width, m) ) * t_assist_circle) ;
604
+ black_alpha = black_alpha . max ( ( smoothstep ( 0.0 , aa_width, m) ) * t_assist_circle) ;
610
605
}
611
606
612
- // Mix white and black based on mask.
613
- // With current mask: outside band (mask=1) is black, inside band (mask=0) is white.
614
- // This produces a white outline on a black background.
615
- let color_rgb = mix ( Vec3 :: ONE , Vec3 :: ZERO , combined_mask ) ;
607
+ let color_background = Vec4 :: ONE ;
608
+ let color_black = Vec4 :: new ( 0.0 , 0.0 , 0.0 , black_alpha ) ;
609
+ let color_red = Vec4 :: new ( 1.0 , 0.0 , 0.0 , debug_red_alpha * 0.5 ) ;
610
+ let color_blue = Vec4 :: new ( 0.0 , 0.0 , 1.0 , debug_blue_alpha * 0.5 ) ;
616
611
617
- let debug_red = mix ( Vec3 :: new ( 1.0 , 0.0 , 0.0 ) , Vec3 :: ZERO , combined_debug_mask ) ;
612
+ let color_rgb = composite_layers ( & [ color_background , color_black , color_red , color_blue ] ) ;
618
613
619
614
// Output final pixel color with alpha = 1.0.
620
- * frag_color = color_rgb. extend ( 1.0 ) ;
615
+ * frag_color = color_rgb;
621
616
}
622
617
}
0 commit comments