1use glam::Vec2;
9use wisp::application::Application;
10use wisp::math::Rect;
11use wisp::render::Renderer;
12use wisp::{Color, DimOutside, DimStrength, Fill, Graphics, RenderTexture, Sprite, Stage, Texture};
13
14use crate::story::Story;
15
16pub fn story() -> Story {
17 Story {
18 id: "dim-outside",
19 category: "Mask",
20 title: "Dim outside (variants)",
21 milestone: "M-MASK.7 / AUT-29",
22 writeup: include_str!("writeups/dim_outside.md"),
23 build,
24 tick: None,
25 }
26}
27
28fn build(app: &Application, stage: &mut Stage) {
29 let format = wgpu::TextureFormat::Rgba8Unorm;
30 let renderer = Renderer::new(app, format).expect("renderer");
31
32 let base_rt = render_capture_with_target(&renderer, app, format);
33
34 let strengths = [
35 (DimStrength::Light, Vec2::new(-0.62, 0.0)),
36 (DimStrength::Medium, Vec2::new(0.0, 0.0)),
37 (DimStrength::Heavy, Vec2::new(0.62, 0.0)),
38 ];
39
40 let focus = Rect::new(-0.5, -0.55, 1.0, 0.7);
41
42 for (strength, pos) in strengths {
43 let dim = DimOutside::rounded_rect(focus, 0.08).with_strength(strength);
44 let out_rt = RenderTexture::with_format(app, 192, 192, format);
45 renderer.apply_dim_outside_data(app, &dim, &base_rt, &out_rt);
46 let bytes = out_rt.read_pixels(app);
47 let tex = Texture::from_rgba(app, 192, 192, &bytes);
48 let mut sprite = Sprite::from_texture(tex).with_anchor(Vec2::splat(0.5));
49 sprite.container.transform.position = pos;
50 sprite.container.transform.scale = Vec2::splat(0.28);
51 let _ = stage.add_child(stage.root(), sprite);
52 }
53
54 let label_y = -0.3;
56 let label_w = 0.32;
57 let label_h = 0.05;
58 let labels = [
59 (
60 Vec2::new(-0.62, label_y),
61 Color::rgba_u8(170, 200, 240, 230),
62 ),
63 (Vec2::new(0.0, label_y), Color::rgba_u8(220, 220, 130, 230)),
64 (Vec2::new(0.62, label_y), Color::rgba_u8(60, 60, 70, 240)),
65 ];
66 for (pos, color) in labels {
67 let mut bar = Graphics::new();
68 bar.fill(Fill::Solid(color));
69 bar.draw_rounded_rect(
70 Rect::new(
71 pos.x - label_w * 0.5,
72 pos.y - label_h * 0.5,
73 label_w,
74 label_h,
75 ),
76 0.012,
77 );
78 let _ = stage.add_child(stage.root(), bar);
79 }
80}
81
82fn render_capture_with_target(
83 renderer: &Renderer,
84 app: &Application,
85 format: wgpu::TextureFormat,
86) -> RenderTexture {
87 let mut s = Stage::new();
88 let mut bg = Graphics::new();
89 bg.fill(Fill::LinearGradient {
90 start: Vec2::new(-1.0, 1.0),
91 end: Vec2::new(1.0, -1.0),
92 color_a: Color::rgba_u8(80, 130, 210, 255),
93 color_b: Color::rgba_u8(220, 110, 80, 255),
94 });
95 bg.draw_rect(Rect::new(-1.0, -1.0, 2.0, 2.0));
96 let _ = s.add_child(s.root(), bg);
97 for i in -4i16..=4 {
98 let x = f32::from(i) * 0.2;
99 let mut line = Graphics::new();
100 line.fill(Fill::Solid(Color::rgba_u8(255, 255, 255, 200)));
101 line.draw_rect(Rect::new(x - 0.005, -1.0, 0.01, 2.0));
102 let _ = s.add_child(s.root(), line);
103 }
104 for j in -4i16..=4 {
105 let y = f32::from(j) * 0.2;
106 let mut line = Graphics::new();
107 line.fill(Fill::Solid(Color::rgba_u8(255, 255, 255, 200)));
108 line.draw_rect(Rect::new(-1.0, y - 0.005, 2.0, 0.01));
109 let _ = s.add_child(s.root(), line);
110 }
111 let rt = RenderTexture::with_format(app, 192, 192, format);
112 let _ = renderer.render_stage(app, rt.view(), Color::BLACK, &s);
113 rt
114}