-
Notifications
You must be signed in to change notification settings - Fork 21
/
state.rs
128 lines (108 loc) · 3.95 KB
/
state.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
use crate::context;
use crate::dom::Dom;
use crate::event::{Event, EventResponse};
use crate::geometry::{Rect, Vec2};
use crate::id::ManagedTextureId;
use crate::input::InputState;
use crate::layout::LayoutDom;
use crate::paint::{PaintDom, PaintLimits, Texture};
/// The entrypoint for yakui.
#[derive(Debug)]
pub struct Yakui {
dom: Dom,
layout: LayoutDom,
paint: PaintDom,
input: InputState,
}
impl Yakui {
/// Creates a new yakui State.
#[allow(clippy::new_without_default)]
pub fn new() -> Self {
Self {
dom: Dom::new(),
layout: LayoutDom::new(),
paint: PaintDom::new(),
input: InputState::new(),
}
}
/// Handles the given event. Returns `true` if the event was sunk by yakui
/// and should not be processed by the application.
pub fn handle_event(&mut self, event: Event) -> bool {
log::debug!("State::handle_event({event:?})");
context::bind_dom(&self.dom);
let response = self.input.handle_event(&self.dom, &self.layout, &event);
if let Event::ViewportChanged(viewport) = event {
self.layout.set_unscaled_viewport(viewport);
}
context::unbind_dom();
response == EventResponse::Sink
}
/// Creates a texture for use within yakui.
pub fn add_texture(&mut self, texture: Texture) -> ManagedTextureId {
self.paint.add_texture(texture)
}
/// Returns an iterator of all textures managed by yakui.
pub fn textures(&self) -> impl Iterator<Item = (ManagedTextureId, &Texture)> {
self.paint.textures()
}
/// Set the size of the surface the yakui is being rendered onto.
pub fn set_surface_size(&mut self, size: Vec2) {
self.paint.set_surface_size(size);
}
/// Set the size and position of the viewport in physical units.
pub fn set_unscaled_viewport(&mut self, view: Rect) {
self.layout.set_unscaled_viewport(view);
self.paint.set_unscaled_viewport(view);
}
/// Manually sets the scale factor used for laying out widgets.
///
/// Platform integrations will usually do this automatically. If you'd like
/// to override that value, like to enable the user to set their own UI
/// scale, this is the method to use.
pub fn set_scale_factor(&mut self, factor: f32) {
self.layout.set_scale_factor(factor);
self.paint.set_scale_factor(factor);
}
/// Starts building the DOM on this thread.
///
/// Once this method is called, widgets can be created on this thread and
/// they will automatically be linked to this State.
///
/// When finished, call [`Dom::finish`].
pub fn start(&mut self) {
self.dom.start();
self.input.start(&self.dom, &self.layout);
self.paint.start();
context::bind_dom(&self.dom);
}
/// Finishes building the DOM. Must be called on a thread that previously
/// called [`Dom::start`].
///
/// This method will finalize the DOM for this frame and compute layouts.
pub fn finish(&mut self) {
context::unbind_dom();
self.dom.finish(&self.input);
self.layout.sync_removals(&self.dom.removed_nodes());
self.layout.calculate_all(&self.dom, &self.input);
self.input.finish();
}
/// Calculates the geometry needed to render the current state and gives
/// access to the [`PaintDom`], which holds information about how to paint
/// widgets.
pub fn paint(&mut self) -> &PaintDom {
self.paint.paint_all(&self.dom, &self.layout);
&self.paint
}
/// Returns access to the state's DOM.
pub fn dom(&self) -> &Dom {
&self.dom
}
/// Returns access to the state's Layout DOM.
pub fn layout_dom(&self) -> &LayoutDom {
&self.layout
}
/// Sets the paint limits, should be called once by rendering backends.
pub fn set_paint_limit(&mut self, limits: PaintLimits) {
self.paint.set_limit(limits)
}
}