Rename `RenderRoot::state` to `global_state` (#691)

This commit is contained in:
Olivier FAURE 2024-10-20 16:46:46 +02:00 committed by GitHub
parent 2832766eff
commit ef5d9afec3
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
11 changed files with 102 additions and 73 deletions

View File

@ -629,7 +629,7 @@ impl MasonryState<'_> {
}
MasonryUserEvent::Action(action, widget) => self
.render_root
.state
.global_state
.signal_queue
.push_back(render_root::RenderRootSignal::Action(action, widget)),
}

View File

@ -139,7 +139,11 @@ pub(crate) fn run_accessibility_pass(
let mut tree_update = TreeUpdate {
nodes: vec![],
tree: None,
focus: root.state.focused_widget.unwrap_or(root.root.id()).into(),
focus: root
.global_state
.focused_widget
.unwrap_or(root.root.id())
.into(),
};
let (root_widget, root_state) = {
@ -162,7 +166,7 @@ pub(crate) fn run_accessibility_pass(
}
build_accessibility_tree(
&mut root.state,
&mut root.global_state,
&mut tree_update,
root_widget,
root_state,

View File

@ -55,7 +55,7 @@ pub(crate) fn run_update_anim_pass(root: &mut RenderRoot, elapsed_ns: u64) {
let (root_widget, mut root_state) = root.widget_arena.get_pair_mut(root.root.id());
update_anim_for_widget(
&mut root.state,
&mut root.global_state,
root_widget,
root_state.reborrow_mut(),
elapsed_ns,

View File

@ -76,5 +76,11 @@ pub(crate) fn run_compose_pass(root: &mut RenderRoot) {
let _span = info_span!("compose").entered();
let (root_widget, root_state) = root.widget_arena.get_pair_mut(root.root.id());
compose_widget(&mut root.state, root_widget, root_state, false, Vec2::ZERO);
compose_widget(
&mut root.global_state,
root_widget,
root_state,
false,
Vec2::ZERO,
);
}

View File

@ -15,7 +15,7 @@ fn get_target_widget(
root: &RenderRoot,
pointer_pos: Option<LogicalPosition<f64>>,
) -> Option<WidgetId> {
if let Some(capture_target) = root.state.pointer_capture_target {
if let Some(capture_target) = root.global_state.pointer_capture_target {
return Some(capture_target);
}
@ -48,7 +48,7 @@ fn run_event_pass<E>(
let (widget_mut, state_mut) = root.widget_arena.get_pair_mut(widget_id);
let mut ctx = EventCtx {
global_state: &mut root.state,
global_state: &mut root.global_state,
widget_state: state_mut.item,
widget_state_children: state_mut.children,
widget_children: widget_mut.children,
@ -104,12 +104,12 @@ pub(crate) fn run_on_pointer_event_pass(root: &mut RenderRoot, event: &PointerEv
// Automatically release the pointer on pointer up or leave. If a widget holds the capture,
// it is notified of the pointer event before the capture is released, so it knows it is
// about to lose the pointer.
root.state.pointer_capture_target = None;
root.global_state.pointer_capture_target = None;
}
if !event.is_high_density() {
debug!(
focused_widget = root.state.focused_widget.map(|id| id.0),
focused_widget = root.global_state.focused_widget.map(|id| id.0),
handled = handled.is_handled(),
"ON_POINTER_EVENT finished",
);
@ -130,7 +130,7 @@ pub(crate) fn run_on_text_event_pass(root: &mut RenderRoot, event: &TextEvent) -
debug!("Running ON_TEXT_EVENT pass with {}", event.short_name());
}
let target = root.state.focused_widget;
let target = root.global_state.focused_widget;
let mut handled = run_event_pass(root, target, event, false, |widget, ctx, event| {
widget.on_text_event(ctx, event);
@ -143,9 +143,9 @@ pub(crate) fn run_on_text_event_pass(root: &mut RenderRoot, event: &TextEvent) -
&& handled == Handled::No
{
if !mods.shift_key() {
root.state.next_focused_widget = root.widget_from_focus_chain(true);
root.global_state.next_focused_widget = root.widget_from_focus_chain(true);
} else {
root.state.next_focused_widget = root.widget_from_focus_chain(false);
root.global_state.next_focused_widget = root.widget_from_focus_chain(false);
}
handled = Handled::Yes;
}
@ -153,7 +153,7 @@ pub(crate) fn run_on_text_event_pass(root: &mut RenderRoot, event: &TextEvent) -
if !event.is_high_density() {
debug!(
focused_widget = root.state.focused_widget.map(|id| id.0),
focused_widget = root.global_state.focused_widget.map(|id| id.0),
handled = handled.is_handled(),
"ON_TEXT_EVENT finished",
);
@ -179,13 +179,13 @@ pub(crate) fn run_on_access_event_pass(
match event.action {
accesskit::Action::Focus if !handled.is_handled() => {
if root.is_still_interactive(target) {
root.state.next_focused_widget = Some(target);
root.global_state.next_focused_widget = Some(target);
handled = Handled::Yes;
}
}
accesskit::Action::Blur if !handled.is_handled() => {
if root.state.next_focused_widget == Some(target) {
root.state.next_focused_widget = None;
if root.global_state.next_focused_widget == Some(target) {
root.global_state.next_focused_widget = None;
handled = Handled::Yes;
}
}
@ -193,7 +193,7 @@ pub(crate) fn run_on_access_event_pass(
}
debug!(
focused_widget = root.state.focused_widget.map(|id| id.0),
focused_widget = root.global_state.focused_widget.map(|id| id.0),
handled = handled.is_handled(),
"ON_ACCESS_EVENT finished",
);

View File

@ -222,7 +222,7 @@ pub(crate) fn run_layout_pass(root: &mut RenderRoot) {
let root_state_token = root.widget_arena.widget_states.root_token_mut();
let root_widget_token = root.widget_arena.widgets.root_token_mut();
let mut ctx = LayoutCtx {
global_state: &mut root.state,
global_state: &mut root.global_state,
widget_state: &mut dummy_state,
widget_state_children: root_state_token,
widget_children: root_widget_token,
@ -235,7 +235,8 @@ pub(crate) fn run_layout_pass(root: &mut RenderRoot) {
let new_size = LogicalSize::new(size.width, size.height).to_physical(root.scale_factor);
if root.size != new_size {
root.size = new_size;
root.state.emit_signal(RenderRootSignal::SetSize(new_size));
root.global_state
.emit_signal(RenderRootSignal::SetSize(new_size));
}
}
}

View File

@ -20,7 +20,7 @@ pub(crate) fn mutate_widget<R>(
// state up to the root.
let root_widget = WidgetMut {
ctx: MutateCtx {
global_state: &mut root.state,
global_state: &mut root.global_state,
parent_widget_state: None,
widget_state: state_mut.item,
widget_state_children: state_mut.children,
@ -45,7 +45,7 @@ pub(crate) fn mutate_widget<R>(
// TODO - Add link to mutate pass documentation
/// Apply any deferred mutations (created using [`...Ctx::mutate_later`](crate::LayoutCtx::mutate_later)).
pub(crate) fn run_mutate_pass(root: &mut RenderRoot) {
let callbacks = std::mem::take(&mut root.state.mutate_callbacks);
let callbacks = std::mem::take(&mut root.global_state.mutate_callbacks);
for callback in callbacks {
mutate_widget(root, callback.id, callback.callback);
}

View File

@ -126,17 +126,17 @@ pub(crate) fn run_paint_pass(root: &mut RenderRoot) -> Scene {
// TODO - This is a bit of a hack until we refactor widget tree mutation.
// This should be removed once remove_child is exclusive to MutateCtx.
let mut scenes = std::mem::take(&mut root.state.scenes);
let mut scenes = std::mem::take(&mut root.global_state.scenes);
paint_widget(
&mut root.state,
&mut root.global_state,
&mut complete_scene,
&mut scenes,
root_widget,
root_state,
debug_paint,
);
root.state.scenes = scenes;
root.global_state.scenes = scenes;
complete_scene
}

View File

@ -39,7 +39,7 @@ fn run_targeted_update_pass(
let (widget_mut, state_mut) = root.widget_arena.get_pair_mut(widget_id);
let mut ctx = UpdateCtx {
global_state: &mut root.state,
global_state: &mut root.global_state,
widget_state: state_mut.item,
widget_state_children: state_mut.children,
widget_children: widget_mut.children,
@ -60,7 +60,7 @@ fn run_single_update_pass(
let (widget_mut, state_mut) = root.widget_arena.get_pair_mut(widget_id);
let mut ctx = UpdateCtx {
global_state: &mut root.state,
global_state: &mut root.global_state,
widget_state: state_mut.item,
widget_state_children: state_mut.children,
widget_children: widget_mut.children,
@ -177,7 +177,11 @@ pub(crate) fn run_update_widget_tree_pass(root: &mut RenderRoot) {
}
let (root_widget, mut root_state) = root.widget_arena.get_pair_mut(root.root.id());
update_widget_tree(&mut root.state, root_widget, root_state.reborrow_mut());
update_widget_tree(
&mut root.global_state,
root_widget,
root_state.reborrow_mut(),
);
}
// ----------------
@ -229,7 +233,7 @@ pub(crate) fn run_update_disabled_pass(root: &mut RenderRoot) {
let _span = info_span!("update_disabled").entered();
let (root_widget, root_state) = root.widget_arena.get_pair_mut(root.root.id());
update_disabled_for_widget(&mut root.state, root_widget, root_state, false);
update_disabled_for_widget(&mut root.global_state, root_widget, root_state, false);
}
// ----------------
@ -297,7 +301,7 @@ pub(crate) fn run_update_stashed_pass(root: &mut RenderRoot) {
let _span = info_span!("update_stashed").entered();
let (root_widget, root_state) = root.widget_arena.get_pair_mut(root.root.id());
update_stashed_for_widget(&mut root.state, root_widget, root_state, false);
update_stashed_for_widget(&mut root.global_state, root_widget, root_state, false);
}
// ----------------
@ -369,7 +373,7 @@ pub(crate) fn run_update_focus_chain_pass(root: &mut RenderRoot) {
let (root_widget, mut root_state) = root.widget_arena.get_pair_mut(root.root.id());
update_focus_chain_for_widget(
&mut root.state,
&mut root.global_state,
root_widget,
root_state.reborrow_mut(),
&mut dummy_focus_chain,
@ -382,17 +386,17 @@ pub(crate) fn run_update_focus_chain_pass(root: &mut RenderRoot) {
pub(crate) fn run_update_focus_pass(root: &mut RenderRoot) {
// If the focused widget is disabled, stashed or removed, we set
// the focused id to None
if let Some(id) = root.state.next_focused_widget {
if let Some(id) = root.global_state.next_focused_widget {
if !root.is_still_interactive(id) {
root.state.next_focused_widget = None;
root.global_state.next_focused_widget = None;
}
}
let prev_focused = root.state.focused_widget;
let next_focused = root.state.next_focused_widget;
let prev_focused = root.global_state.focused_widget;
let next_focused = root.global_state.next_focused_widget;
// "Focused path" means the focused widget, and all its parents.
let prev_focused_path = std::mem::take(&mut root.state.focused_path);
let prev_focused_path = std::mem::take(&mut root.global_state.focused_path);
let next_focused_path = get_id_path(root, next_focused);
let mut focused_set = HashSet::new();
@ -442,13 +446,13 @@ pub(crate) fn run_update_focus_pass(root: &mut RenderRoot) {
}
if prev_focused != next_focused {
let was_ime_active = root.state.is_ime_active;
let was_ime_active = root.global_state.is_ime_active;
let is_ime_active = if let Some(id) = next_focused {
root.widget_arena.get_state(id).item.accepts_text_input
} else {
false
};
root.state.is_ime_active = is_ime_active;
root.global_state.is_ime_active = is_ime_active;
run_single_update_pass(root, prev_focused, |widget, ctx| {
widget.on_status_change(ctx, &StatusChange::FocusChanged(false));
@ -458,21 +462,21 @@ pub(crate) fn run_update_focus_pass(root: &mut RenderRoot) {
});
if prev_focused.is_some() && was_ime_active {
root.state.emit_signal(RenderRootSignal::EndIme);
root.global_state.emit_signal(RenderRootSignal::EndIme);
}
if next_focused.is_some() && is_ime_active {
root.state.emit_signal(RenderRootSignal::StartIme);
root.global_state.emit_signal(RenderRootSignal::StartIme);
}
if let Some(id) = next_focused {
let ime_area = root.widget_arena.get_state(id).item.get_ime_area();
root.state
root.global_state
.emit_signal(RenderRootSignal::new_ime_moved_signal(ime_area));
}
}
root.state.focused_widget = root.state.next_focused_widget;
root.state.focused_path = next_focused_path;
root.global_state.focused_widget = root.global_state.next_focused_widget;
root.global_state.focused_path = next_focused_path;
}
// ----------------
@ -486,7 +490,7 @@ pub(crate) fn run_update_focus_pass(root: &mut RenderRoot) {
pub(crate) fn run_update_scroll_pass(root: &mut RenderRoot) {
let _span = info_span!("update_scroll").entered();
let scroll_request_targets = std::mem::take(&mut root.state.scroll_request_targets);
let scroll_request_targets = std::mem::take(&mut root.global_state.scroll_request_targets);
for (target, rect) in scroll_request_targets {
let mut target_rect = rect;
@ -511,9 +515,9 @@ pub(crate) fn run_update_pointer_pass(root: &mut RenderRoot) {
let pointer_pos = root.last_mouse_pos.map(|pos| (pos.x, pos.y).into());
// Release pointer capture if target can no longer hold it.
if let Some(id) = root.state.pointer_capture_target {
if let Some(id) = root.global_state.pointer_capture_target {
if !root.is_still_interactive(id) {
root.state.pointer_capture_target = None;
root.global_state.pointer_capture_target = None;
run_on_pointer_event_pass(root, &PointerEvent::new_pointer_leave());
}
}
@ -528,14 +532,14 @@ pub(crate) fn run_update_pointer_pass(root: &mut RenderRoot) {
None
};
// If the pointer is captured, it can either hover its capture target or nothing.
if let Some(capture_target) = root.state.pointer_capture_target {
if let Some(capture_target) = root.global_state.pointer_capture_target {
if next_hovered_widget != Some(capture_target) {
next_hovered_widget = None;
}
}
// "Hovered path" means the widget which is considered hovered, and all its parents.
let prev_hovered_path = std::mem::take(&mut root.state.hovered_path);
let prev_hovered_path = std::mem::take(&mut root.global_state.hovered_path);
let next_hovered_path = get_id_path(root, next_hovered_widget);
let mut hovered_set = HashSet::new();
@ -591,7 +595,10 @@ pub(crate) fn run_update_pointer_pass(root: &mut RenderRoot) {
// If the pointer is captured, its cursor always reflects the
// capture target, even when not hovered.
let cursor_source = root.state.pointer_capture_target.or(next_hovered_widget);
let cursor_source = root
.global_state
.pointer_capture_target
.or(next_hovered_widget);
let new_cursor = if let Some(cursor_source) = cursor_source {
let (widget, state) = root.widget_arena.get_pair(cursor_source);
@ -600,11 +607,11 @@ pub(crate) fn run_update_pointer_pass(root: &mut RenderRoot) {
CursorIcon::Default
};
if root.state.cursor_icon != new_cursor {
root.state
if root.global_state.cursor_icon != new_cursor {
root.global_state
.emit_signal(RenderRootSignal::SetCursor(new_cursor));
}
root.state.cursor_icon = new_cursor;
root.state.hovered_path = next_hovered_path;
root.global_state.cursor_icon = new_cursor;
root.global_state.hovered_path = next_hovered_path;
}

View File

@ -52,7 +52,7 @@ pub struct RenderRoot {
pub(crate) last_anim: Option<Instant>,
pub(crate) last_mouse_pos: Option<LogicalPosition<f64>>,
pub(crate) cursor_icon: CursorIcon,
pub(crate) state: RenderRootState,
pub(crate) global_state: RenderRootState,
// TODO - Add "access_tree_active" to detect when you don't need to update the
// access tree
pub(crate) rebuild_access_tree: bool,
@ -141,7 +141,7 @@ impl RenderRoot {
last_anim: None,
last_mouse_pos: None,
cursor_icon: CursorIcon::Default,
state: RenderRootState {
global_state: RenderRootState {
debug_logger: DebugLogger::new(false),
signal_queue: VecDeque::new(),
focused_widget: None,
@ -174,7 +174,7 @@ impl RenderRoot {
let families = root.register_fonts(test_font_data);
// Make sure that all of these fonts are in the fallback chain for the Latin script.
// <https://en.wikipedia.org/wiki/Script_(Unicode)#Latn>
root.state
root.global_state
.font_context
.collection
.append_fallbacks(*b"Latn", families.iter().map(|(family, _)| *family));
@ -231,7 +231,8 @@ impl RenderRoot {
}
WindowEvent::RebuildAccessTree => {
self.rebuild_access_tree = true;
self.state.emit_signal(RenderRootSignal::RequestRedraw);
self.global_state
.emit_signal(RenderRootSignal::RequestRedraw);
Handled::Yes
}
}
@ -254,7 +255,10 @@ impl RenderRoot {
&mut self,
data: Vec<u8>,
) -> Vec<(fontique::FamilyId, Vec<fontique::FontInfo>)> {
self.state.font_context.collection.register_fonts(data)
self.global_state
.font_context
.collection
.register_fonts(data)
}
pub fn redraw(&mut self) -> (Scene, TreeUpdate) {
@ -264,7 +268,8 @@ impl RenderRoot {
}
if self.root_state().needs_layout {
warn!("Widget requested layout during layout pass");
self.state.emit_signal(RenderRootSignal::RequestRedraw);
self.global_state
.emit_signal(RenderRootSignal::RequestRedraw);
}
// TODO - Handle invalidation regions
@ -273,15 +278,15 @@ impl RenderRoot {
}
pub fn pop_signal(&mut self) -> Option<RenderRootSignal> {
self.state.signal_queue.pop_front()
self.global_state.signal_queue.pop_front()
}
pub fn pop_signal_matching(
&mut self,
predicate: impl Fn(&RenderRootSignal) -> bool,
) -> Option<RenderRootSignal> {
let idx = self.state.signal_queue.iter().position(predicate)?;
self.state.signal_queue.remove(idx)
let idx = self.global_state.signal_queue.iter().position(predicate)?;
self.global_state.signal_queue.remove(idx)
}
pub fn cursor_icon(&self) -> CursorIcon {
@ -310,7 +315,7 @@ impl RenderRoot {
.unwrap();
let ctx = QueryCtx {
global_state: &self.state,
global_state: &self.global_state,
widget_state_children: state_ref.children,
widget_children: widget_ref.children,
widget_state: state_ref.item,
@ -335,7 +340,7 @@ impl RenderRoot {
let widget = widget_ref.item;
let widget: &dyn Widget = &**widget;
let ctx = QueryCtx {
global_state: &self.state,
global_state: &self.global_state,
widget_state_children: state_ref.children,
widget_children: widget_ref.children,
widget_state: state_ref.item,
@ -480,7 +485,8 @@ impl RenderRoot {
run_update_pointer_pass(self);
if self.root_state().needs_anim {
self.state.emit_signal(RenderRootSignal::RequestAnimFrame);
self.global_state
.emit_signal(RenderRootSignal::RequestAnimFrame);
}
// We request a redraw if either the render tree or the accessibility
@ -491,7 +497,8 @@ impl RenderRoot {
|| self.root_state().needs_accessibility
|| self.root_state().needs_layout
{
self.state.emit_signal(RenderRootSignal::RequestRedraw);
self.global_state
.emit_signal(RenderRootSignal::RequestRedraw);
}
}
@ -518,7 +525,8 @@ impl RenderRoot {
let (root_widget, mut root_state) = self.widget_arena.get_pair_mut(self.root.id());
request_render_all_in(root_widget, root_state.reborrow_mut());
self.state.emit_signal(RenderRootSignal::RequestRedraw);
self.global_state
.emit_signal(RenderRootSignal::RequestRedraw);
}
// Checks whether the given id points to a widget that is "interactive".
@ -533,7 +541,7 @@ impl RenderRoot {
}
pub(crate) fn widget_from_focus_chain(&mut self, forward: bool) -> Option<WidgetId> {
let focused_widget = self.state.focused_widget;
let focused_widget = self.global_state.focused_widget;
let focused_idx = focused_widget.and_then(|focused_widget| {
self.focus_chain()
.iter()
@ -569,7 +577,7 @@ impl RenderRoot {
#[allow(dead_code)]
pub(crate) fn needs_rewrite_passes(&mut self) -> bool {
self.root_state().needs_rewrite_passes() || self.state.focus_changed()
self.root_state().needs_rewrite_passes() || self.global_state.focus_changed()
}
}

View File

@ -449,7 +449,7 @@ impl TestHarness {
}
pub fn focus_on(&mut self, id: Option<WidgetId>) {
self.render_root.state.next_focused_widget = id;
self.render_root.global_state.next_focused_widget = id;
self.render_root.run_rewrite_passes();
}
@ -511,18 +511,18 @@ impl TestHarness {
/// Return the widget that receives keyboard events.
pub fn focused_widget(&self) -> Option<WidgetRef<'_, dyn Widget>> {
self.root_widget()
.find_widget_by_id(self.render_root.state.focused_widget?)
.find_widget_by_id(self.render_root.global_state.focused_widget?)
}
// TODO - Multiple pointers
pub fn pointer_capture_target(&self) -> Option<WidgetRef<'_, dyn Widget>> {
self.render_root
.get_widget(self.render_root.state.pointer_capture_target?)
.get_widget(self.render_root.global_state.pointer_capture_target?)
}
// TODO - This is kinda redundant with the above
pub fn pointer_capture_target_id(&self) -> Option<WidgetId> {
self.render_root.state.pointer_capture_target
self.render_root.global_state.pointer_capture_target
}
/// Call the provided visitor on every widget in the widget tree.
@ -660,6 +660,9 @@ impl TestHarness {
// ex: harness.write_debug_logs("test_log.json");
#[allow(missing_docs)]
pub fn write_debug_logs(&mut self, path: &str) {
self.render_root.state.debug_logger.write_to_file(path);
self.render_root
.global_state
.debug_logger
.write_to_file(path);
}
}