mirror of
https://github.com/slint-ui/slint.git
synced 2025-09-27 12:29:41 +00:00
Traverse item front to back for input events
This commit is contained in:
parent
d9c776eb57
commit
36243ccdf7
12 changed files with 97 additions and 47 deletions
|
@ -31,6 +31,7 @@ using internal::ComponentVTable;
|
||||||
using ItemTreeNode = internal::ItemTreeNode<uint8_t>;
|
using ItemTreeNode = internal::ItemTreeNode<uint8_t>;
|
||||||
using ComponentRef = VRef<ComponentVTable>;
|
using ComponentRef = VRef<ComponentVTable>;
|
||||||
using ItemVisitorRefMut = VRefMut<internal::ItemVisitorVTable>;
|
using ItemVisitorRefMut = VRefMut<internal::ItemVisitorVTable>;
|
||||||
|
using internal::TraversalOrder;
|
||||||
using internal::EasingCurve;
|
using internal::EasingCurve;
|
||||||
using internal::TextHorizontalAlignment;
|
using internal::TextHorizontalAlignment;
|
||||||
using internal::TextVerticalAlignment;
|
using internal::TextVerticalAlignment;
|
||||||
|
@ -177,12 +178,13 @@ struct Repeater
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
intptr_t visit(ItemVisitorRefMut visitor) const
|
intptr_t visit(TraversalOrder order, ItemVisitorRefMut visitor) const
|
||||||
{
|
{
|
||||||
for (std::size_t i = 0; i < data.size(); ++i) {
|
for (std::size_t i = 0; i < data.size(); ++i) {
|
||||||
VRef<ComponentVTable> ref = item_at(i);
|
int index = order == TraversalOrder::BackToFront ? i : data.size() - 1 - i;
|
||||||
if (ref.vtable->visit_children_item(ref, -1, visitor) != -1) {
|
VRef<ComponentVTable> ref = item_at(index);
|
||||||
return i;
|
if (ref.vtable->visit_children_item(ref, -1, order, visitor) != -1) {
|
||||||
|
return index;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return -1;
|
return -1;
|
||||||
|
|
|
@ -87,7 +87,7 @@ pub mod re_exports {
|
||||||
};
|
};
|
||||||
pub use sixtyfps_corelib::item_tree::{
|
pub use sixtyfps_corelib::item_tree::{
|
||||||
item_offset, visit_item_tree, ItemTreeNode, ItemVisitorRefMut, ItemVisitorVTable,
|
item_offset, visit_item_tree, ItemTreeNode, ItemVisitorRefMut, ItemVisitorVTable,
|
||||||
VisitChildrenResult,
|
TraversalOrder, VisitChildrenResult,
|
||||||
};
|
};
|
||||||
pub use sixtyfps_corelib::items::*;
|
pub use sixtyfps_corelib::items::*;
|
||||||
pub use sixtyfps_corelib::layout::LayoutInfo;
|
pub use sixtyfps_corelib::layout::LayoutInfo;
|
||||||
|
|
|
@ -43,10 +43,11 @@ where
|
||||||
/// Call the visitor for each component
|
/// Call the visitor for each component
|
||||||
pub fn visit(
|
pub fn visit(
|
||||||
&self,
|
&self,
|
||||||
|
order: sixtyfps_corelib::item_tree::TraversalOrder,
|
||||||
mut visitor: sixtyfps_corelib::item_tree::ItemVisitorRefMut,
|
mut visitor: sixtyfps_corelib::item_tree::ItemVisitorRefMut,
|
||||||
) -> sixtyfps_corelib::item_tree::VisitChildrenResult {
|
) -> sixtyfps_corelib::item_tree::VisitChildrenResult {
|
||||||
for (i, c) in self.components.borrow().iter().enumerate() {
|
for (i, c) in self.components.borrow().iter().enumerate() {
|
||||||
if c.as_ref().visit_children_item(-1, visitor.borrow_mut()).has_aborted() {
|
if c.as_ref().visit_children_item(-1, order, visitor.borrow_mut()).has_aborted() {
|
||||||
return sixtyfps_corelib::item_tree::VisitChildrenResult::abort(i, 0);
|
return sixtyfps_corelib::item_tree::VisitChildrenResult::abort(i, 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -146,8 +146,6 @@ MainWindow := Rectangle {
|
||||||
clicked => {
|
clicked => {
|
||||||
if (root.active_page == 0) {
|
if (root.active_page == 0) {
|
||||||
root.active_page = idx + 1;
|
root.active_page = idx + 1;
|
||||||
} else {
|
|
||||||
root.active_page = 0;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -356,7 +356,7 @@ fn handle_repeater(
|
||||||
repeater_count: i32,
|
repeater_count: i32,
|
||||||
component_struct: &mut Struct,
|
component_struct: &mut Struct,
|
||||||
init: &mut Vec<String>,
|
init: &mut Vec<String>,
|
||||||
children_repeater_cases: &mut Vec<String>,
|
children_visitor_cases: &mut Vec<String>,
|
||||||
repeated_input_branch: &mut Vec<String>,
|
repeated_input_branch: &mut Vec<String>,
|
||||||
) {
|
) {
|
||||||
let repeater_id =
|
let repeater_id =
|
||||||
|
@ -372,8 +372,8 @@ fn handle_repeater(
|
||||||
};
|
};
|
||||||
|
|
||||||
if repeated.model.is_constant() {
|
if repeated.model.is_constant() {
|
||||||
children_repeater_cases.push(format!(
|
children_visitor_cases.push(format!(
|
||||||
"\n case {i}: return self->{id}.visit(visitor);",
|
"\n case {i}: return self->{id}.visit(order, visitor);",
|
||||||
id = repeater_id,
|
id = repeater_id,
|
||||||
i = repeater_count
|
i = repeater_count
|
||||||
));
|
));
|
||||||
|
@ -392,14 +392,14 @@ fn handle_repeater(
|
||||||
init: None,
|
init: None,
|
||||||
}),
|
}),
|
||||||
));
|
));
|
||||||
children_repeater_cases.push(format!(
|
children_visitor_cases.push(format!(
|
||||||
"\n case {i}: {{
|
"\n case {i}: {{
|
||||||
if (self->model_{i}.is_dirty()) {{
|
if (self->model_{i}.is_dirty()) {{
|
||||||
self->model_{i}.evaluate([&] {{
|
self->model_{i}.evaluate([&] {{
|
||||||
self->{id}.update_model({model}, self);
|
self->{id}.update_model({model}, self);
|
||||||
}});
|
}});
|
||||||
}}
|
}}
|
||||||
self->{id}.visit(visitor);
|
self->{id}.visit(order, visitor);
|
||||||
break;
|
break;
|
||||||
}}",
|
}}",
|
||||||
id = repeater_id,
|
id = repeater_id,
|
||||||
|
@ -667,7 +667,7 @@ fn generate_component(
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut children_visitor_case = vec![];
|
let mut children_visitor_cases = vec![];
|
||||||
let mut repeated_input_branch = vec![];
|
let mut repeated_input_branch = vec![];
|
||||||
let mut tree_array = vec![];
|
let mut tree_array = vec![];
|
||||||
let mut repeater_count = 0;
|
let mut repeater_count = 0;
|
||||||
|
@ -699,7 +699,7 @@ fn generate_component(
|
||||||
repeater_count,
|
repeater_count,
|
||||||
&mut component_struct,
|
&mut component_struct,
|
||||||
&mut init,
|
&mut init,
|
||||||
&mut children_visitor_case,
|
&mut children_visitor_cases,
|
||||||
&mut repeated_input_branch,
|
&mut repeated_input_branch,
|
||||||
);
|
);
|
||||||
repeater_count += 1;
|
repeater_count += 1;
|
||||||
|
@ -731,15 +731,14 @@ fn generate_component(
|
||||||
Access::Private,
|
Access::Private,
|
||||||
Declaration::Function(Function {
|
Declaration::Function(Function {
|
||||||
name: "visit_children".into(),
|
name: "visit_children".into(),
|
||||||
signature: "(sixtyfps::ComponentRef component, intptr_t index, sixtyfps::ItemVisitorRefMut visitor) -> intptr_t".into(),
|
signature: "(sixtyfps::ComponentRef component, intptr_t index, sixtyfps::TraversalOrder order, sixtyfps::ItemVisitorRefMut visitor) -> intptr_t".into(),
|
||||||
is_static: true,
|
is_static: true,
|
||||||
statements: Some(vec![
|
statements: Some(vec![
|
||||||
"static const auto dyn_visit = [] (const uint8_t *base, [[maybe_unused]] sixtyfps::ItemVisitorRefMut visitor, uintptr_t dyn_index) -> int64_t {".to_owned(),
|
"static const auto dyn_visit = [] (const uint8_t *base, sixtyfps::TraversalOrder order, [[maybe_unused]] sixtyfps::ItemVisitorRefMut visitor, uintptr_t dyn_index) -> int64_t {".to_owned(),
|
||||||
format!(" [[maybe_unused]] auto self = reinterpret_cast<const {}*>(base);", component_id),
|
format!(" [[maybe_unused]] auto self = reinterpret_cast<const {}*>(base);", component_id),
|
||||||
// Fixme: this is not the root component
|
format!(" switch(dyn_index) {{ {} }};", children_visitor_cases.join("")),
|
||||||
format!(" switch(dyn_index) {{ {} }};", children_visitor_case.join("")),
|
|
||||||
" return -1; //should not happen\n};".to_owned(),
|
" return -1; //should not happen\n};".to_owned(),
|
||||||
"return sixtyfps::sixtyfps_visit_item_tree(component, item_tree() , index, visitor, dyn_visit);".to_owned(),
|
"return sixtyfps::sixtyfps_visit_item_tree(component, item_tree() , index, order, visitor, dyn_visit);".to_owned(),
|
||||||
]),
|
]),
|
||||||
..Default::default()
|
..Default::default()
|
||||||
}),
|
}),
|
||||||
|
|
|
@ -230,7 +230,7 @@ fn generate_component(
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
repeated_visit_branch.push(quote!(
|
repeated_visit_branch.push(quote!(
|
||||||
#repeater_index => self_pinned.#repeater_id.visit(visitor),
|
#repeater_index => self_pinned.#repeater_id.visit(order, visitor),
|
||||||
));
|
));
|
||||||
} else {
|
} else {
|
||||||
let model_name = quote::format_ident!("model_{}", repeater_index);
|
let model_name = quote::format_ident!("model_{}", repeater_index);
|
||||||
|
@ -244,7 +244,7 @@ fn generate_component(
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
self_pinned.#repeater_id.visit(visitor)
|
self_pinned.#repeater_id.visit(order, visitor)
|
||||||
}
|
}
|
||||||
));
|
));
|
||||||
repeated_dynmodel_names.push(model_name);
|
repeated_dynmodel_names.push(model_name);
|
||||||
|
@ -438,13 +438,13 @@ fn generate_component(
|
||||||
}
|
}
|
||||||
|
|
||||||
impl sixtyfps::re_exports::Component for #component_id {
|
impl sixtyfps::re_exports::Component for #component_id {
|
||||||
fn visit_children_item(self: ::core::pin::Pin<&Self>, index: isize, visitor: sixtyfps::re_exports::ItemVisitorRefMut)
|
fn visit_children_item(self: ::core::pin::Pin<&Self>, index: isize, order: sixtyfps::re_exports::TraversalOrder, visitor: sixtyfps::re_exports::ItemVisitorRefMut)
|
||||||
-> sixtyfps::re_exports::VisitChildrenResult
|
-> sixtyfps::re_exports::VisitChildrenResult
|
||||||
{
|
{
|
||||||
use sixtyfps::re_exports::*;
|
use sixtyfps::re_exports::*;
|
||||||
return sixtyfps::re_exports::visit_item_tree(self, VRef::new_pin(self), Self::item_tree(), index, visitor, visit_dynamic);
|
return sixtyfps::re_exports::visit_item_tree(self, VRef::new_pin(self), Self::item_tree(), index, order, visitor, visit_dynamic);
|
||||||
#[allow(unused)]
|
#[allow(unused)]
|
||||||
fn visit_dynamic(self_pinned: ::core::pin::Pin<&#component_id>, visitor: ItemVisitorRefMut, dyn_index: usize) -> VisitChildrenResult {
|
fn visit_dynamic(self_pinned: ::core::pin::Pin<&#component_id>, order: sixtyfps::re_exports::TraversalOrder, visitor: ItemVisitorRefMut, dyn_index: usize) -> VisitChildrenResult {
|
||||||
match dyn_index {
|
match dyn_index {
|
||||||
#(#repeated_visit_branch)*
|
#(#repeated_visit_branch)*
|
||||||
_ => panic!("invalid dyn_index {}", dyn_index),
|
_ => panic!("invalid dyn_index {}", dyn_index),
|
||||||
|
|
|
@ -5,7 +5,7 @@ use vtable::*;
|
||||||
use crate::graphics::{HighLevelRenderingPrimitive, Rect, RenderingVariable};
|
use crate::graphics::{HighLevelRenderingPrimitive, Rect, RenderingVariable};
|
||||||
use crate::input::{InputEventResult, MouseEvent};
|
use crate::input::{InputEventResult, MouseEvent};
|
||||||
use crate::item_rendering::CachedRenderingData;
|
use crate::item_rendering::CachedRenderingData;
|
||||||
use crate::item_tree::{ItemVisitorVTable, VisitChildrenResult};
|
use crate::item_tree::{ItemVisitorVTable, TraversalOrder, VisitChildrenResult};
|
||||||
use crate::{layout::LayoutInfo, SharedArray};
|
use crate::{layout::LayoutInfo, SharedArray};
|
||||||
|
|
||||||
/// A Component is representing an unit that is allocated together
|
/// A Component is representing an unit that is allocated together
|
||||||
|
@ -18,6 +18,7 @@ pub struct ComponentVTable {
|
||||||
pub visit_children_item: extern "C" fn(
|
pub visit_children_item: extern "C" fn(
|
||||||
core::pin::Pin<VRef<ComponentVTable>>,
|
core::pin::Pin<VRef<ComponentVTable>>,
|
||||||
index: isize,
|
index: isize,
|
||||||
|
order: TraversalOrder,
|
||||||
visitor: VRefMut<ItemVisitorVTable>,
|
visitor: VRefMut<ItemVisitorVTable>,
|
||||||
) -> VisitChildrenResult,
|
) -> VisitChildrenResult,
|
||||||
|
|
||||||
|
|
|
@ -416,6 +416,7 @@ impl<Backend: GraphicsBackend> crate::eventloop::GenericWindow for GraphicsWindo
|
||||||
// Generate cached rendering data once
|
// Generate cached rendering data once
|
||||||
crate::item_tree::visit_items(
|
crate::item_tree::visit_items(
|
||||||
component,
|
component,
|
||||||
|
crate::item_tree::TraversalOrder::BackToFront,
|
||||||
|_, item, _| {
|
|_, item, _| {
|
||||||
crate::item_rendering::update_item_rendering_data(
|
crate::item_rendering::update_item_rendering_data(
|
||||||
item,
|
item,
|
||||||
|
|
|
@ -66,6 +66,7 @@ pub fn process_ungrabbed_mouse_event(
|
||||||
let mut result = InputEventResult::EventIgnored;
|
let mut result = InputEventResult::EventIgnored;
|
||||||
let item_index = crate::item_tree::visit_items(
|
let item_index = crate::item_tree::visit_items(
|
||||||
component,
|
component,
|
||||||
|
crate::item_tree::TraversalOrder::FrontToBack,
|
||||||
|_, item, offset| -> ItemVisitorResult<Vector2D<f32>> {
|
|_, item, offset| -> ItemVisitorResult<Vector2D<f32>> {
|
||||||
let geom = item.as_ref().geometry();
|
let geom = item.as_ref().geometry();
|
||||||
let geom = geom.translate(*offset);
|
let geom = geom.translate(*offset);
|
||||||
|
|
|
@ -49,6 +49,7 @@ pub(crate) fn render_component_items<Backend: GraphicsBackend>(
|
||||||
|
|
||||||
crate::item_tree::visit_items(
|
crate::item_tree::visit_items(
|
||||||
component,
|
component,
|
||||||
|
crate::item_tree::TraversalOrder::BackToFront,
|
||||||
|_, item, transform| {
|
|_, item, transform| {
|
||||||
let origin = item.as_ref().geometry().origin;
|
let origin = item.as_ref().geometry().origin;
|
||||||
let transform =
|
let transform =
|
||||||
|
|
|
@ -3,6 +3,13 @@ use crate::ComponentRefPin;
|
||||||
use core::pin::Pin;
|
use core::pin::Pin;
|
||||||
use vtable::*;
|
use vtable::*;
|
||||||
|
|
||||||
|
#[repr(u8)]
|
||||||
|
#[derive(Debug, Copy, Clone, Eq, PartialEq)]
|
||||||
|
pub enum TraversalOrder {
|
||||||
|
BackToFront,
|
||||||
|
FrontToBack,
|
||||||
|
}
|
||||||
|
|
||||||
/// The return value of the Component::visit_children_item function
|
/// The return value of the Component::visit_children_item function
|
||||||
///
|
///
|
||||||
/// Represents something like `enum { Continue, Aborted{aborted_at_item: isize} }`.
|
/// Represents something like `enum { Continue, Aborted{aborted_at_item: isize} }`.
|
||||||
|
@ -114,29 +121,31 @@ pub enum ItemVisitorResult<State> {
|
||||||
/// Returns the index of the item that cancelled, or -1 if nobody cancelled
|
/// Returns the index of the item that cancelled, or -1 if nobody cancelled
|
||||||
pub fn visit_items<State>(
|
pub fn visit_items<State>(
|
||||||
component: ComponentRefPin,
|
component: ComponentRefPin,
|
||||||
|
order: TraversalOrder,
|
||||||
mut visitor: impl FnMut(ComponentRefPin, Pin<ItemRef>, &State) -> ItemVisitorResult<State>,
|
mut visitor: impl FnMut(ComponentRefPin, Pin<ItemRef>, &State) -> ItemVisitorResult<State>,
|
||||||
state: State,
|
state: State,
|
||||||
) -> VisitChildrenResult {
|
) -> VisitChildrenResult {
|
||||||
visit_internal(component, &mut visitor, -1, &state)
|
visit_internal(component, order, &mut visitor, -1, &state)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn visit_internal<State>(
|
fn visit_internal<State>(
|
||||||
component: ComponentRefPin,
|
component: ComponentRefPin,
|
||||||
|
order: TraversalOrder,
|
||||||
visitor: &mut impl FnMut(ComponentRefPin, Pin<ItemRef>, &State) -> ItemVisitorResult<State>,
|
visitor: &mut impl FnMut(ComponentRefPin, Pin<ItemRef>, &State) -> ItemVisitorResult<State>,
|
||||||
index: isize,
|
index: isize,
|
||||||
state: &State,
|
state: &State,
|
||||||
) -> VisitChildrenResult {
|
) -> VisitChildrenResult {
|
||||||
let mut actual_visitor = |component: ComponentRefPin,
|
let mut actual_visitor =
|
||||||
index: isize,
|
|component: ComponentRefPin, index: isize, item: Pin<ItemRef>| -> VisitChildrenResult {
|
||||||
item: Pin<ItemRef>|
|
match visitor(component, item, state) {
|
||||||
-> VisitChildrenResult {
|
ItemVisitorResult::Continue(state) => {
|
||||||
match visitor(component, item, state) {
|
visit_internal(component, order, visitor, index, &state)
|
||||||
ItemVisitorResult::Continue(state) => visit_internal(component, visitor, index, &state),
|
}
|
||||||
ItemVisitorResult::Abort => VisitChildrenResult::abort(index as usize, 0),
|
ItemVisitorResult::Abort => VisitChildrenResult::abort(index as usize, 0),
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
vtable::new_vref!(let mut actual_visitor : VRefMut<ItemVisitorVTable> for ItemVisitor = &mut actual_visitor);
|
vtable::new_vref!(let mut actual_visitor : VRefMut<ItemVisitorVTable> for ItemVisitor = &mut actual_visitor);
|
||||||
component.as_ref().visit_children_item(index, actual_visitor)
|
component.as_ref().visit_children_item(index, order, actual_visitor)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Visit the children within an array of ItemTreeNode
|
/// Visit the children within an array of ItemTreeNode
|
||||||
|
@ -152,8 +161,14 @@ pub fn visit_item_tree<Base>(
|
||||||
component: ComponentRefPin,
|
component: ComponentRefPin,
|
||||||
item_tree: &[ItemTreeNode<Base>],
|
item_tree: &[ItemTreeNode<Base>],
|
||||||
index: isize,
|
index: isize,
|
||||||
|
order: TraversalOrder,
|
||||||
mut visitor: vtable::VRefMut<ItemVisitorVTable>,
|
mut visitor: vtable::VRefMut<ItemVisitorVTable>,
|
||||||
visit_dynamic: impl Fn(Pin<&Base>, vtable::VRefMut<ItemVisitorVTable>, usize) -> VisitChildrenResult,
|
visit_dynamic: impl Fn(
|
||||||
|
Pin<&Base>,
|
||||||
|
TraversalOrder,
|
||||||
|
vtable::VRefMut<ItemVisitorVTable>,
|
||||||
|
usize,
|
||||||
|
) -> VisitChildrenResult,
|
||||||
) -> VisitChildrenResult {
|
) -> VisitChildrenResult {
|
||||||
let mut visit_at_index = |idx: usize| -> VisitChildrenResult {
|
let mut visit_at_index = |idx: usize| -> VisitChildrenResult {
|
||||||
match &item_tree[idx] {
|
match &item_tree[idx] {
|
||||||
|
@ -162,7 +177,7 @@ pub fn visit_item_tree<Base>(
|
||||||
}
|
}
|
||||||
ItemTreeNode::DynamicTree { index } => {
|
ItemTreeNode::DynamicTree { index } => {
|
||||||
if let Some(sub_idx) =
|
if let Some(sub_idx) =
|
||||||
visit_dynamic(base, visitor.borrow_mut(), *index).aborted_index()
|
visit_dynamic(base, order, visitor.borrow_mut(), *index).aborted_index()
|
||||||
{
|
{
|
||||||
VisitChildrenResult::abort(idx, sub_idx)
|
VisitChildrenResult::abort(idx, sub_idx)
|
||||||
} else {
|
} else {
|
||||||
|
@ -176,8 +191,12 @@ pub fn visit_item_tree<Base>(
|
||||||
} else {
|
} else {
|
||||||
match &item_tree[index as usize] {
|
match &item_tree[index as usize] {
|
||||||
ItemTreeNode::Item { children_index, chilren_count, .. } => {
|
ItemTreeNode::Item { children_index, chilren_count, .. } => {
|
||||||
for c in *children_index..(*children_index + *chilren_count) {
|
for c in 0..*chilren_count {
|
||||||
let maybe_abort_index = visit_at_index(c as usize);
|
let idx = match order {
|
||||||
|
TraversalOrder::BackToFront => (*children_index + c),
|
||||||
|
TraversalOrder::FrontToBack => (*children_index + *chilren_count - c - 1),
|
||||||
|
} as usize;
|
||||||
|
let maybe_abort_index = visit_at_index(idx);
|
||||||
if maybe_abort_index.has_aborted() {
|
if maybe_abort_index.has_aborted() {
|
||||||
return maybe_abort_index;
|
return maybe_abort_index;
|
||||||
}
|
}
|
||||||
|
@ -228,9 +247,11 @@ pub(crate) mod ffi {
|
||||||
component: Pin<VRef<ComponentVTable>>,
|
component: Pin<VRef<ComponentVTable>>,
|
||||||
item_tree: Slice<ItemTreeNode<u8>>,
|
item_tree: Slice<ItemTreeNode<u8>>,
|
||||||
index: isize,
|
index: isize,
|
||||||
|
order: TraversalOrder,
|
||||||
visitor: VRefMut<ItemVisitorVTable>,
|
visitor: VRefMut<ItemVisitorVTable>,
|
||||||
visit_dynamic: extern "C" fn(
|
visit_dynamic: extern "C" fn(
|
||||||
base: &u8,
|
base: &u8,
|
||||||
|
order: TraversalOrder,
|
||||||
visitor: vtable::VRefMut<ItemVisitorVTable>,
|
visitor: vtable::VRefMut<ItemVisitorVTable>,
|
||||||
dyn_index: usize,
|
dyn_index: usize,
|
||||||
) -> VisitChildrenResult,
|
) -> VisitChildrenResult,
|
||||||
|
@ -240,8 +261,9 @@ pub(crate) mod ffi {
|
||||||
component,
|
component,
|
||||||
item_tree.as_slice(),
|
item_tree.as_slice(),
|
||||||
index,
|
index,
|
||||||
|
order,
|
||||||
visitor,
|
visitor,
|
||||||
|a, b, c| visit_dynamic(a.get_ref(), b, c),
|
|a, b, c, d| visit_dynamic(a.get_ref(), b, c, d),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -9,7 +9,9 @@ use sixtyfps_compilerlib::typeregister::Type;
|
||||||
use sixtyfps_compilerlib::*;
|
use sixtyfps_compilerlib::*;
|
||||||
use sixtyfps_corelib::abi::datastructures::{ComponentVTable, ItemVTable, WindowProperties};
|
use sixtyfps_corelib::abi::datastructures::{ComponentVTable, ItemVTable, WindowProperties};
|
||||||
use sixtyfps_corelib::graphics::Resource;
|
use sixtyfps_corelib::graphics::Resource;
|
||||||
use sixtyfps_corelib::item_tree::{ItemTreeNode, ItemVisitorRefMut, VisitChildrenResult};
|
use sixtyfps_corelib::item_tree::{
|
||||||
|
ItemTreeNode, ItemVisitorRefMut, TraversalOrder, VisitChildrenResult,
|
||||||
|
};
|
||||||
use sixtyfps_corelib::items::{Flickable, PropertyAnimation, Rectangle};
|
use sixtyfps_corelib::items::{Flickable, PropertyAnimation, Rectangle};
|
||||||
use sixtyfps_corelib::layout::LayoutInfo;
|
use sixtyfps_corelib::layout::LayoutInfo;
|
||||||
use sixtyfps_corelib::properties::{InterpolatedPropertyValue, PropertyListenerScope};
|
use sixtyfps_corelib::properties::{InterpolatedPropertyValue, PropertyListenerScope};
|
||||||
|
@ -157,6 +159,7 @@ pub struct ComponentDescription {
|
||||||
unsafe extern "C" fn visit_children_item(
|
unsafe extern "C" fn visit_children_item(
|
||||||
component: ComponentRefPin,
|
component: ComponentRefPin,
|
||||||
index: isize,
|
index: isize,
|
||||||
|
order: TraversalOrder,
|
||||||
v: ItemVisitorRefMut,
|
v: ItemVisitorRefMut,
|
||||||
) -> VisitChildrenResult {
|
) -> VisitChildrenResult {
|
||||||
let component_type =
|
let component_type =
|
||||||
|
@ -167,8 +170,9 @@ unsafe extern "C" fn visit_children_item(
|
||||||
component,
|
component,
|
||||||
item_tree.as_slice().into(),
|
item_tree.as_slice().into(),
|
||||||
index,
|
index,
|
||||||
|
order,
|
||||||
v,
|
v,
|
||||||
|_, mut visitor, index| {
|
|_, order, mut visitor, index| {
|
||||||
let rep_in_comp = &component_type.repeater[index];
|
let rep_in_comp = &component_type.repeater[index];
|
||||||
let vec = &mut *(component.as_ptr().add(rep_in_comp.offset) as *mut RepeaterVec);
|
let vec = &mut *(component.as_ptr().add(rep_in_comp.offset) as *mut RepeaterVec);
|
||||||
if let Some(listener_offset) = rep_in_comp.listener {
|
if let Some(listener_offset) = rep_in_comp.listener {
|
||||||
|
@ -205,11 +209,31 @@ unsafe extern "C" fn visit_children_item(
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (i, x) in vec.iter().enumerate() {
|
match order {
|
||||||
if x.borrow().as_ref().visit_children_item(-1, visitor.borrow_mut()).has_aborted() {
|
TraversalOrder::FrontToBack => {
|
||||||
return VisitChildrenResult::abort(i, 0);
|
for (i, x) in vec.iter().enumerate() {
|
||||||
|
if x.borrow()
|
||||||
|
.as_ref()
|
||||||
|
.visit_children_item(-1, order, visitor.borrow_mut())
|
||||||
|
.has_aborted()
|
||||||
|
{
|
||||||
|
return VisitChildrenResult::abort(i, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TraversalOrder::BackToFront => {
|
||||||
|
for (i, x) in vec.iter().enumerate().rev() {
|
||||||
|
if x.borrow()
|
||||||
|
.as_ref()
|
||||||
|
.visit_children_item(-1, order, visitor.borrow_mut())
|
||||||
|
.has_aborted()
|
||||||
|
{
|
||||||
|
return VisitChildrenResult::abort(i, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
VisitChildrenResult::CONTINUE
|
VisitChildrenResult::CONTINUE
|
||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue