tawasuyu/llimphi
Sovereign retained-mode GPU UI framework in Rust (wgpu+vello+taffy+parley), Elm loop, 40+ widgets.
chore: refresco desde el monorepo — vello 0.9 / wgpu 29, 120 miembros
1//! Showcase de `llimphi-widget-splitter`: dos splits anidados
2//! draggables (Row con Column adentro).
3//!
4//! Corre con: `cargo run -p llimphi-widget-splitter --example showcase --release`.
5//!
6//! Prueba: agarrá el divisor vertical y arrástralo izquierda/derecha
7//! para resizar el pane izquierdo; agarrá el divisor horizontal de la
8//! derecha para resizar el pane superior derecho.
9
10use llimphi_ui::llimphi_layout::taffy::{
11 prelude::{percent, Size, Style},
12 AlignItems, JustifyContent,
13};
14use llimphi_ui::llimphi_raster::peniko::Color;
15use llimphi_ui::llimphi_text::Alignment;
16use llimphi_ui::{App, DragPhase, Handle, View};
17use llimphi_widget_splitter::{splitter_two, Direction, PaneSize, SplitterPalette};
18
19#[derive(Clone)]
20enum Msg {
21 ResizeOuter(f32),
22 ResizeInner(f32),
23}
24
25struct Model {
26 left_w: f32,
27 top_h: f32,
28}
29
30struct Showcase;
31
32impl App for Showcase {
33 type Model = Model;
34 type Msg = Msg;
35
36 fn title() -> &'static str {
37 "llimphi · splitter showcase"
38 }
39
40 fn initial_size() -> (u32, u32) {
41 (1100, 720)
42 }
43
44 fn init(_: &Handle<Msg>) -> Model {
45 Model {
46 left_w: 320.0,
47 top_h: 240.0,
48 }
49 }
50
51 fn update(model: Model, msg: Msg, _: &Handle<Msg>) -> Model {
52 let mut m = model;
53 match msg {
54 Msg::ResizeOuter(dx) => {
55 m.left_w = (m.left_w + dx).clamp(120.0, 800.0);
56 }
57 Msg::ResizeInner(dy) => {
58 m.top_h = (m.top_h + dy).clamp(80.0, 600.0);
59 }
60 }
61 m
62 }
63
64 fn view(model: &Model) -> View<Msg> {
65 let palette = SplitterPalette::default();
66
67 let left = pane("izquierdo", Color::from_rgba8(28, 36, 50, 255));
68 let top_right = pane(
69 &format!("arriba · {:.0} px", model.top_h),
70 Color::from_rgba8(38, 50, 70, 255),
71 );
72 let bottom_right = pane(
73 "abajo · flex",
74 Color::from_rgba8(48, 36, 60, 255),
75 );
76
77 let right = splitter_two(
78 Direction::Column,
79 top_right,
80 PaneSize::Fixed(model.top_h),
81 bottom_right,
82 PaneSize::Flex,
83 |phase, dy| match phase {
84 DragPhase::Move => Some(Msg::ResizeInner(dy)),
85 DragPhase::End => None,
86 },
87 &palette,
88 );
89
90 splitter_two(
91 Direction::Row,
92 left,
93 PaneSize::Fixed(model.left_w),
94 right,
95 PaneSize::Flex,
96 |phase, dx| match phase {
97 DragPhase::Move => Some(Msg::ResizeOuter(dx)),
98 DragPhase::End => None,
99 },
100 &palette,
101 )
102 }
103}
104
105fn pane(label: &str, bg: Color) -> View<Msg> {
106 View::new(Style {
107 size: Size {
108 width: percent(1.0_f32),
109 height: percent(1.0_f32),
110 },
111 align_items: Some(AlignItems::CENTER),
112 justify_content: Some(JustifyContent::CENTER),
113 ..Default::default()
114 })
115 .fill(bg)
116 .text_aligned(
117 label.to_string(),
118 18.0,
119 Color::from_rgba8(220, 230, 240, 255),
120 Alignment::Center,
121 )
122}
123
124fn main() {
125 llimphi_ui::run::<Showcase>();
126}