repose_core/
view.rs

1use crate::{Color, Modifier, Rect, Transform};
2use std::rc::Rc;
3
4pub type ViewId = u64;
5
6pub type Callback = Rc<dyn Fn()>;
7pub type ScrollCallback = Rc<dyn Fn(f32) -> f32>;
8
9#[derive(Clone)]
10pub enum ViewKind {
11    Surface,
12    Box,
13    Row,
14    Column,
15    Stack,
16    ScrollV {
17        on_scroll: Option<ScrollCallback>,
18        set_viewport_height: Option<Rc<dyn Fn(f32)>>,
19        get_scroll_offset: Option<Rc<dyn Fn() -> f32>>,
20    },
21    Text {
22        text: String,
23        color: Color,
24        font_size: f32,
25    },
26    Button {
27        text: String,
28        on_click: Option<Callback>,
29    },
30    TextField {
31        state_key: ViewId,
32        hint: String,
33        on_change: Option<Rc<dyn Fn(String)>>,
34    },
35    Checkbox {
36        checked: bool,
37        label: String,
38        on_change: Option<Rc<dyn Fn(bool)>>,
39    },
40    RadioButton {
41        selected: bool,
42        label: String,
43        on_select: Option<Callback>,
44    },
45    Switch {
46        checked: bool,
47        label: String,
48        on_change: Option<Rc<dyn Fn(bool)>>,
49    },
50    Slider {
51        value: f32,
52        min: f32,
53        max: f32,
54        step: Option<f32>,
55        label: String,
56        on_change: Option<CallbackF32>,
57    },
58    RangeSlider {
59        start: f32,
60        end: f32,
61        min: f32,
62        max: f32,
63        step: Option<f32>,
64        label: String,
65        on_change: Option<CallbackRange>,
66    },
67    ProgressBar {
68        value: f32,
69        min: f32,
70        max: f32,
71        label: String,
72        circular: bool,
73    },
74}
75
76impl std::fmt::Debug for ViewKind {
77    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
78        match self {
79            ViewKind::Checkbox { checked, label, .. } => f
80                .debug_struct("Checkbox")
81                .field("checked", checked)
82                .field("label", label)
83                .finish(),
84            ViewKind::RadioButton {
85                selected, label, ..
86            } => f
87                .debug_struct("RadioButton")
88                .field("selected", selected)
89                .field("label", label)
90                .finish(),
91            ViewKind::Switch { checked, label, .. } => f
92                .debug_struct("Switch")
93                .field("checked", checked)
94                .field("label", label)
95                .finish(),
96            ViewKind::Surface => write!(f, "Surface"),
97            ViewKind::Box => write!(f, "Box"),
98            ViewKind::Row => write!(f, "Row"),
99            ViewKind::Column => write!(f, "Column"),
100            ViewKind::Stack => write!(f, "Stack"),
101            ViewKind::ScrollV { .. } => write!(f, "ScrollV"),
102            ViewKind::Text {
103                text,
104                color,
105                font_size,
106            } => f
107                .debug_struct("Text")
108                .field("text", text)
109                .field("color", color)
110                .field("font_size", font_size)
111                .finish(),
112            ViewKind::Button { text, .. } => f
113                .debug_struct("Button")
114                .field("text", text)
115                .field("on_click", &"<callback>")
116                .finish(),
117            ViewKind::TextField {
118                state_key,
119                hint,
120                on_change,
121            } => f
122                .debug_struct("TextField")
123                .field("state_key", state_key)
124                .field("hint", hint)
125                .finish(),
126            ViewKind::Slider {
127                value,
128                min,
129                max,
130                step,
131                label,
132                ..
133            } => f
134                .debug_struct("Slider")
135                .field("value", value)
136                .field("min", min)
137                .field("max", max)
138                .field("step", step)
139                .field("label", label)
140                .finish(),
141            ViewKind::RangeSlider {
142                start,
143                end,
144                min,
145                max,
146                step,
147                label,
148                ..
149            } => f
150                .debug_struct("RangeSlider")
151                .field("start", start)
152                .field("end", end)
153                .field("min", min)
154                .field("max", max)
155                .field("step", step)
156                .field("label", label)
157                .finish(),
158            ViewKind::ProgressBar {
159                value,
160                min,
161                max,
162                label,
163                circular,
164            } => f
165                .debug_struct("ProgressBar")
166                .field("value", value)
167                .field("min", min)
168                .field("max", max)
169                .field("label", label)
170                .field("circular", circular)
171                .finish(),
172        }
173    }
174}
175
176#[derive(Clone, Debug)]
177pub struct View {
178    pub id: ViewId,
179    pub kind: ViewKind,
180    pub modifier: Modifier,
181    pub children: Vec<View>,
182    pub semantics: Option<crate::semantics::Semantics>,
183}
184
185impl View {
186    pub fn new(id: ViewId, kind: ViewKind) -> Self {
187        View {
188            id,
189            kind,
190            modifier: Modifier::default(),
191            children: vec![],
192            semantics: None,
193        }
194    }
195    pub fn modifier(mut self, m: Modifier) -> Self {
196        self.modifier = m;
197        self
198    }
199    pub fn with_children(mut self, kids: Vec<View>) -> Self {
200        self.children = kids;
201        self
202    }
203    pub fn semantics(mut self, s: crate::semantics::Semantics) -> Self {
204        self.semantics = Some(s);
205        self
206    }
207}
208
209/// Renderable scene
210#[derive(Clone, Debug, Default)]
211pub struct Scene {
212    pub clear_color: Color,
213    pub nodes: Vec<SceneNode>,
214}
215
216#[derive(Clone, Debug)]
217pub enum SceneNode {
218    Rect {
219        rect: Rect,
220        color: Color,
221        radius: f32,
222    },
223    Border {
224        rect: Rect,
225        color: Color,
226        width: f32,
227        radius: f32,
228    },
229    Text {
230        rect: Rect,
231        text: String,
232        color: Color,
233        size: f32,
234    },
235    PushClip {
236        rect: Rect,
237        radius: f32,
238    },
239    PopClip,
240    PushTransform {
241        transform: Transform,
242    },
243    PopTransform,
244}
245
246pub type CallbackF32 = Rc<dyn Fn(f32)>;
247pub type CallbackRange = Rc<dyn Fn(f32, f32)>;