mirror of
https://github.com/slint-ui/slint.git
synced 2025-10-01 14:21:16 +00:00
New runtime implementation for the box layout
Currently only horizontal layout is supported
This commit is contained in:
parent
211fa69ef5
commit
aeade826fe
6 changed files with 332 additions and 60 deletions
|
@ -187,10 +187,7 @@ pub mod re_exports {
|
|||
};
|
||||
pub use sixtyfps_corelib::items::*;
|
||||
pub use sixtyfps_corelib::layout::LayoutInfo;
|
||||
pub use sixtyfps_corelib::layout::{
|
||||
grid_layout_info, solve_grid_layout, solve_path_layout, GridLayoutCellData, GridLayoutData,
|
||||
Padding, PathLayoutData, PathLayoutItemData,
|
||||
};
|
||||
pub use sixtyfps_corelib::layout::*;
|
||||
pub use sixtyfps_corelib::model::*;
|
||||
pub use sixtyfps_corelib::properties::{Property, PropertyTracker};
|
||||
pub use sixtyfps_corelib::signals::Signal;
|
||||
|
|
|
@ -1497,6 +1497,61 @@ impl crate::layout::gen::Language for CppLanguageLayoutGen {
|
|||
cell_ref_variable,
|
||||
}
|
||||
}
|
||||
|
||||
fn box_layout_tree_item<'a, 'b>(
|
||||
layout_tree: &'b mut Vec<crate::layout::gen::LayoutTreeItem<'a, Self>>,
|
||||
box_layout: &'a crate::layout::BoxLayout,
|
||||
component: &Rc<Component>,
|
||||
) -> crate::layout::gen::LayoutTreeItem<'a, Self> {
|
||||
let cells: Vec<_> = box_layout
|
||||
.elems
|
||||
.iter()
|
||||
.map(|cell| {
|
||||
let layout_info =
|
||||
get_layout_info_ref(&cell.item, &cell.constraints, layout_tree, component);
|
||||
let lay_rect = cell.item.rect();
|
||||
let get_property_ref = |p: &Option<NamedReference>| match p {
|
||||
Some(nr) => format!("&{}", access_named_reference(nr, component, "self")),
|
||||
None => "nullptr".to_owned(),
|
||||
};
|
||||
format!(
|
||||
" {{ {li}, {x}, {y}, {w}, {h} }},",
|
||||
li = layout_info,
|
||||
x = get_property_ref(&lay_rect.x_reference),
|
||||
y = get_property_ref(&lay_rect.y_reference),
|
||||
w = get_property_ref(&lay_rect.width_reference),
|
||||
h = get_property_ref(&lay_rect.height_reference)
|
||||
)
|
||||
})
|
||||
.collect();
|
||||
|
||||
let cell_ref_variable = format!("cells_{}", layout_tree.len()).to_owned();
|
||||
let mut creation_code = cells;
|
||||
creation_code.insert(
|
||||
0,
|
||||
format!(" sixtyfps::GridLayoutCellData {}_data[] = {{", cell_ref_variable,),
|
||||
);
|
||||
creation_code.push(" };".to_owned());
|
||||
creation_code.push(format!(
|
||||
" const sixtyfps::Slice<sixtyfps::GridLayoutCellData> {cv}{{{cv}_data, std::size({cv}_data)}};",
|
||||
cv = cell_ref_variable
|
||||
));
|
||||
|
||||
let (padding, spacing) = generate_layout_padding_and_spacing(
|
||||
&mut creation_code,
|
||||
&box_layout.geometry,
|
||||
&layout_tree,
|
||||
component,
|
||||
);
|
||||
|
||||
LayoutTreeItem::BoxLayout {
|
||||
geometry: &box_layout.geometry,
|
||||
spacing,
|
||||
padding,
|
||||
var_creation_code: creation_code.join("\n"),
|
||||
cell_ref_variable,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
type LayoutTreeItem<'a> = crate::layout::gen::LayoutTreeItem<'a, CppLanguageLayoutGen>;
|
||||
|
@ -1515,6 +1570,10 @@ fn get_layout_info_ref<'a, 'b>(
|
|||
"sixtyfps::grid_layout_info(&{}, {}, &{})",
|
||||
cell_ref_variable, spacing, padding
|
||||
),
|
||||
LayoutTreeItem::BoxLayout { spacing, cell_ref_variable, padding, .. } => format!(
|
||||
"sixtyfps::box_layout_info(&{}, {}, &{})",
|
||||
cell_ref_variable, spacing, padding
|
||||
),
|
||||
LayoutTreeItem::PathLayout(_) => todo!(),
|
||||
}
|
||||
});
|
||||
|
@ -1623,11 +1682,28 @@ impl<'a> LayoutTreeItem<'a> {
|
|||
s = spacing,
|
||||
p = padding,
|
||||
));
|
||||
code_stream.push(format!(" {cv}", cv = cell_ref_variable).to_owned());
|
||||
code_stream.push(format!(" {cv}", cv = cell_ref_variable));
|
||||
code_stream.push(" };".to_owned());
|
||||
code_stream.push(" sixtyfps::solve_grid_layout(&grid);".to_owned());
|
||||
code_stream.push(" } ".into());
|
||||
}
|
||||
LayoutTreeItem::BoxLayout { geometry, spacing, cell_ref_variable, padding, .. } => {
|
||||
code_stream.push(" { ".into());
|
||||
code_stream.push(" sixtyfps::BoxLayoutData box { ".into());
|
||||
code_stream.push(format!(
|
||||
" {w}, {h}, {x}, {y}, {s}, &{p},",
|
||||
w = layout_prop(&geometry.rect.width_reference),
|
||||
h = layout_prop(&geometry.rect.height_reference),
|
||||
x = layout_prop(&geometry.rect.x_reference),
|
||||
y = layout_prop(&geometry.rect.y_reference),
|
||||
s = spacing,
|
||||
p = padding,
|
||||
));
|
||||
code_stream.push(format!(" {cv}", cv = cell_ref_variable));
|
||||
code_stream.push(" };".to_owned());
|
||||
code_stream.push(" sixtyfps::solve_box_layout(&box);".to_owned());
|
||||
code_stream.push(" } ".into());
|
||||
}
|
||||
LayoutTreeItem::PathLayout(path_layout) => {
|
||||
code_stream.push("{".to_owned());
|
||||
|
||||
|
@ -1762,6 +1838,7 @@ fn compute_layout(
|
|||
|
||||
res.extend(inverse_layout_tree.iter().filter_map(|layout| match layout {
|
||||
LayoutTreeItem::GridLayout { var_creation_code, .. } => Some(var_creation_code.clone()),
|
||||
LayoutTreeItem::BoxLayout { var_creation_code, .. } => Some(var_creation_code.clone()),
|
||||
LayoutTreeItem::PathLayout(_) => None,
|
||||
}));
|
||||
|
||||
|
|
|
@ -1371,6 +1371,54 @@ impl crate::layout::gen::Language for RustLanguageLayoutGen {
|
|||
}
|
||||
.into()
|
||||
}
|
||||
|
||||
fn box_layout_tree_item<'a, 'b>(
|
||||
layout_tree: &'b mut Vec<crate::layout::gen::LayoutTreeItem<'a, Self>>,
|
||||
box_layout: &'a crate::layout::BoxLayout,
|
||||
component: &Rc<Component>,
|
||||
) -> crate::layout::gen::LayoutTreeItem<'a, Self> {
|
||||
let cells: Vec<_> = box_layout
|
||||
.elems
|
||||
.iter()
|
||||
.map(|cell| {
|
||||
let get_property_ref = |p: &Option<NamedReference>| match p {
|
||||
Some(nr) => {
|
||||
let p = access_named_reference(nr, component, quote!(_self));
|
||||
quote!(Some(#p.get_ref()))
|
||||
}
|
||||
None => quote!(None),
|
||||
};
|
||||
let lay_rect = cell.item.rect();
|
||||
let width = get_property_ref(&lay_rect.width_reference);
|
||||
let height = get_property_ref(&lay_rect.height_reference);
|
||||
let x = get_property_ref(&lay_rect.x_reference);
|
||||
let y = get_property_ref(&lay_rect.y_reference);
|
||||
let layout_info =
|
||||
get_layout_info_ref(&cell.item, &cell.constraints, layout_tree, component);
|
||||
quote!(BoxLayoutCellData {
|
||||
x: #x,
|
||||
y: #y,
|
||||
width: #width,
|
||||
height: #height,
|
||||
constraint: #layout_info,
|
||||
})
|
||||
})
|
||||
.collect();
|
||||
let cell_ref_variable = format_ident!("cells_{}", layout_tree.len());
|
||||
let cell_creation_code = quote!(let #cell_ref_variable
|
||||
= [#( #cells ),*];);
|
||||
let (padding, spacing, spacing_creation_code) =
|
||||
generate_layout_padding_and_spacing(&layout_tree, &box_layout.geometry, component);
|
||||
|
||||
LayoutTreeItem::BoxLayout {
|
||||
geometry: &box_layout.geometry,
|
||||
var_creation_code: quote!(#cell_creation_code #spacing_creation_code),
|
||||
cell_ref_variable: quote!(#cell_ref_variable),
|
||||
spacing,
|
||||
padding,
|
||||
}
|
||||
.into()
|
||||
}
|
||||
}
|
||||
|
||||
type LayoutTreeItem<'a> = crate::layout::gen::LayoutTreeItem<'a, RustLanguageLayoutGen>;
|
||||
|
@ -1388,6 +1436,9 @@ fn get_layout_info_ref<'a, 'b>(
|
|||
LayoutTreeItem::GridLayout { cell_ref_variable, spacing, padding, .. } => {
|
||||
quote!(grid_layout_info(&Slice::from_slice(&#cell_ref_variable), #spacing, #padding))
|
||||
}
|
||||
LayoutTreeItem::BoxLayout { cell_ref_variable, spacing, padding, .. } => {
|
||||
quote!(box_layout_info(&Slice::from_slice(&#cell_ref_variable), #spacing, #padding))
|
||||
}
|
||||
LayoutTreeItem::PathLayout(_) => todo!(),
|
||||
}
|
||||
});
|
||||
|
@ -1488,6 +1539,24 @@ impl<'a> LayoutTreeItem<'a> {
|
|||
});
|
||||
});
|
||||
}
|
||||
LayoutTreeItem::BoxLayout { geometry, cell_ref_variable, spacing, padding, .. } => {
|
||||
let x_pos = layout_prop(&geometry.rect.x_reference);
|
||||
let y_pos = layout_prop(&geometry.rect.y_reference);
|
||||
let width = layout_prop(&geometry.rect.width_reference);
|
||||
let height = layout_prop(&geometry.rect.height_reference);
|
||||
|
||||
code_stream.push(quote! {
|
||||
solve_box_layout(&BoxLayoutData {
|
||||
width: #width,
|
||||
height: #height,
|
||||
x: #x_pos as _,
|
||||
y: #y_pos as _,
|
||||
cells: Slice::from_slice(&#cell_ref_variable),
|
||||
spacing: #spacing,
|
||||
padding: #padding,
|
||||
});
|
||||
});
|
||||
}
|
||||
LayoutTreeItem::PathLayout(path_layout) => {
|
||||
let path_layout_item_data =
|
||||
|elem: &ElementRc, elem_rs: TokenStream, component_rust: TokenStream| {
|
||||
|
@ -1615,6 +1684,7 @@ fn compute_layout(
|
|||
|
||||
layouts.extend(inverse_layout_tree.iter().filter_map(|layout| match layout {
|
||||
LayoutTreeItem::GridLayout { var_creation_code, .. } => Some(var_creation_code.clone()),
|
||||
LayoutTreeItem::BoxLayout { var_creation_code, .. } => Some(var_creation_code.clone()),
|
||||
LayoutTreeItem::PathLayout(_) => None,
|
||||
}));
|
||||
|
||||
|
|
|
@ -339,6 +339,12 @@ pub mod gen {
|
|||
cells: Vec<Self::CompiledCode>,
|
||||
component: &Rc<Component>,
|
||||
) -> LayoutTreeItem<'a, Self>;
|
||||
/// Returns a LayoutTree:BoxLayout
|
||||
fn box_layout_tree_item<'a, 'b>(
|
||||
layout_tree: &'b mut Vec<LayoutTreeItem<'a, Self>>,
|
||||
box_layout: &'a BoxLayout,
|
||||
component: &Rc<Component>,
|
||||
) -> LayoutTreeItem<'a, Self>;
|
||||
}
|
||||
|
||||
#[derive(derive_more::From)]
|
||||
|
@ -350,6 +356,14 @@ pub mod gen {
|
|||
var_creation_code: L::CompiledCode,
|
||||
cell_ref_variable: L::CompiledCode,
|
||||
},
|
||||
BoxLayout {
|
||||
geometry: &'a LayoutGeometry,
|
||||
spacing: L::CompiledCode,
|
||||
padding: L::CompiledCode,
|
||||
var_creation_code: L::CompiledCode,
|
||||
cell_ref_variable: L::CompiledCode,
|
||||
},
|
||||
#[from]
|
||||
PathLayout(&'a PathLayout),
|
||||
}
|
||||
|
||||
|
@ -382,27 +396,7 @@ pub mod gen {
|
|||
layout_tree.push(i);
|
||||
}
|
||||
Layout::BoxLayout(box_layout) => {
|
||||
let cells: Vec<_> = box_layout
|
||||
.elems
|
||||
.iter()
|
||||
.enumerate()
|
||||
.map(|(idx, cell)| {
|
||||
let (c, r) = if box_layout.is_horizontal { (idx, 0) } else { (0, idx) };
|
||||
L::make_grid_layout_cell_data(
|
||||
&cell.item,
|
||||
&cell.constraints,
|
||||
c as u16,
|
||||
r as u16,
|
||||
1,
|
||||
1,
|
||||
layout_tree,
|
||||
component,
|
||||
)
|
||||
})
|
||||
.collect();
|
||||
|
||||
let i =
|
||||
L::grid_layout_tree_item(layout_tree, &box_layout.geometry, cells, component);
|
||||
let i = L::box_layout_tree_item(layout_tree, box_layout, component);
|
||||
layout_tree.push(i);
|
||||
}
|
||||
Layout::PathLayout(layout) => layout_tree.push(layout.into()),
|
||||
|
|
|
@ -47,7 +47,7 @@ impl LayoutInfo {
|
|||
}
|
||||
}
|
||||
|
||||
mod internal {
|
||||
mod grid_internal {
|
||||
use super::*;
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
|
@ -226,8 +226,8 @@ pub extern "C" fn solve_grid_layout(data: &GridLayoutData) {
|
|||
return;
|
||||
}
|
||||
|
||||
let mut row_layout_data = vec![internal::LayoutData::default(); num_row as usize];
|
||||
let mut col_layout_data = vec![internal::LayoutData::default(); num_col as usize];
|
||||
let mut row_layout_data = vec![grid_internal::LayoutData::default(); num_row as usize];
|
||||
let mut col_layout_data = vec![grid_internal::LayoutData::default(); num_col as usize];
|
||||
for cell in data.cells.iter() {
|
||||
let row_max = cell.constraint.max_height / (cell.rowspan as f32);
|
||||
let row_min = cell.constraint.min_height / (cell.rowspan as f32);
|
||||
|
@ -252,13 +252,13 @@ pub extern "C" fn solve_grid_layout(data: &GridLayoutData) {
|
|||
}
|
||||
}
|
||||
|
||||
internal::layout_items(
|
||||
grid_internal::layout_items(
|
||||
&mut row_layout_data,
|
||||
data.y + data.padding.top,
|
||||
data.height - (data.padding.top + data.padding.bottom),
|
||||
data.spacing,
|
||||
);
|
||||
internal::layout_items(
|
||||
grid_internal::layout_items(
|
||||
&mut col_layout_data,
|
||||
data.x + data.padding.left,
|
||||
data.width - (data.padding.left + data.padding.right),
|
||||
|
@ -302,8 +302,8 @@ pub extern "C" fn grid_layout_info<'a>(
|
|||
return LayoutInfo { min_width: 0., max_width: 0., min_height: 0., max_height: 0. };
|
||||
};
|
||||
|
||||
let mut row_layout_data = vec![internal::LayoutData::default(); num_row as usize];
|
||||
let mut col_layout_data = vec![internal::LayoutData::default(); num_col as usize];
|
||||
let mut row_layout_data = vec![grid_internal::LayoutData::default(); num_row as usize];
|
||||
let mut col_layout_data = vec![grid_internal::LayoutData::default(); num_col as usize];
|
||||
for cell in cells.iter() {
|
||||
let rdata = &mut row_layout_data[cell.row as usize];
|
||||
let cdata = &mut col_layout_data[cell.col as usize];
|
||||
|
@ -320,8 +320,8 @@ pub extern "C" fn grid_layout_info<'a>(
|
|||
|
||||
let min_height = row_layout_data.iter().map(|data| data.min).sum::<Coord>()
|
||||
+ spacing_h
|
||||
+ padding.left
|
||||
+ padding.right;
|
||||
+ padding.top
|
||||
+ padding.bottom;
|
||||
let max_height = row_layout_data.iter().map(|data| data.max).sum::<Coord>()
|
||||
+ spacing_h
|
||||
+ padding.top
|
||||
|
@ -332,9 +332,135 @@ pub extern "C" fn grid_layout_info<'a>(
|
|||
+ padding.right;
|
||||
let max_width = col_layout_data.iter().map(|data| data.max).sum::<Coord>()
|
||||
+ spacing_w
|
||||
+ padding.left
|
||||
+ padding.right;
|
||||
|
||||
LayoutInfo { min_width, max_width, min_height, max_height }
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
#[derive(Debug)]
|
||||
/// The BoxLayoutData is used to represent both a Horizontal and Vertical layout.
|
||||
/// The width/height x/y corrspond to that of a horizontal layout.
|
||||
/// For vertical layout, they are inverted
|
||||
pub struct BoxLayoutData<'a> {
|
||||
pub width: Coord,
|
||||
pub height: Coord,
|
||||
pub x: Coord,
|
||||
pub y: Coord,
|
||||
pub spacing: Coord,
|
||||
pub padding: &'a Padding,
|
||||
pub cells: Slice<'a, BoxLayoutCellData<'a>>,
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
#[derive(Default, Debug)]
|
||||
pub struct BoxLayoutCellData<'a> {
|
||||
pub constraint: LayoutInfo,
|
||||
pub x: Option<&'a Property<Coord>>,
|
||||
pub y: Option<&'a Property<Coord>>,
|
||||
pub width: Option<&'a Property<Coord>>,
|
||||
pub height: Option<&'a Property<Coord>>,
|
||||
}
|
||||
|
||||
/// Solve the horizontal BoxLayout
|
||||
#[no_mangle]
|
||||
pub extern "C" fn solve_box_layout(data: &BoxLayoutData) {
|
||||
use stretch::geometry::*;
|
||||
use stretch::number::*;
|
||||
use stretch::style::*;
|
||||
|
||||
let mut stretch = stretch::Stretch::new();
|
||||
|
||||
let box_style = stretch::style::Style {
|
||||
size: Size { width: Dimension::Percent(1.), height: Dimension::Percent(1.) },
|
||||
flex_grow: 1.,
|
||||
display: Display::Flex,
|
||||
flex_direction: FlexDirection::Row,
|
||||
flex_basis: Dimension::Percent(1.),
|
||||
..Default::default()
|
||||
};
|
||||
|
||||
let flex_box = stretch.new_node(box_style, vec![]).unwrap();
|
||||
|
||||
for (index, cell) in data.cells.iter().enumerate() {
|
||||
let min = if cell.constraint.min_width == 0.0 {
|
||||
Dimension::Undefined
|
||||
} else {
|
||||
Dimension::Points(cell.constraint.min_height)
|
||||
};
|
||||
let max = if cell.constraint.max_width == f32::MAX {
|
||||
Dimension::Undefined
|
||||
} else {
|
||||
Dimension::Points(cell.constraint.max_width)
|
||||
};
|
||||
let mut margin = Rect::default();
|
||||
if index != 0 {
|
||||
margin.start = Dimension::Points(data.spacing / 2.);
|
||||
}
|
||||
if index != data.cells.len() - 1 {
|
||||
margin.end = Dimension::Points(data.spacing / 2.);
|
||||
}
|
||||
|
||||
let cell_style = Style {
|
||||
min_size: Size { width: min, height: Dimension::Auto },
|
||||
max_size: Size { width: max, height: Dimension::Auto },
|
||||
size: Size { width: min, height: Dimension::Auto },
|
||||
flex_grow: 1.,
|
||||
margin,
|
||||
..Default::default()
|
||||
};
|
||||
|
||||
let cell_item = stretch.new_node(cell_style, vec![]).unwrap();
|
||||
stretch.add_child(flex_box, cell_item).unwrap();
|
||||
}
|
||||
|
||||
stretch
|
||||
.compute_layout(
|
||||
flex_box,
|
||||
Size {
|
||||
width: Number::Defined(data.width - (data.padding.left + data.padding.right)),
|
||||
height: Number::Undefined,
|
||||
},
|
||||
)
|
||||
.unwrap();
|
||||
|
||||
let start_pos = data.x + data.padding.left;
|
||||
|
||||
for (cell, layout) in data.cells.iter().zip(
|
||||
stretch.children(flex_box).unwrap().iter().map(|child| stretch.layout(*child).unwrap()),
|
||||
) {
|
||||
cell.x.map(|p| p.set(start_pos + layout.location.x));
|
||||
cell.y.map(|p| p.set(data.y + data.padding.top));
|
||||
cell.width.map(|p| p.set(layout.size.width));
|
||||
cell.height.map(|p| p.set(data.height - (data.padding.top + data.padding.bottom)));
|
||||
}
|
||||
}
|
||||
|
||||
#[no_mangle]
|
||||
/// Return the LayoutInfo for a Horizontal BoxLayout with the given cells.
|
||||
/// Transpose everything for vertical
|
||||
pub extern "C" fn box_layout_info<'a>(
|
||||
cells: &Slice<'a, BoxLayoutCellData<'a>>,
|
||||
spacing: Coord,
|
||||
padding: &Padding,
|
||||
) -> LayoutInfo {
|
||||
let count = cells.len();
|
||||
if count < 1 {
|
||||
return LayoutInfo { min_width: 0., max_width: 0., min_height: 0., max_height: 0. };
|
||||
};
|
||||
|
||||
let extra_w = padding.left + padding.right + spacing * (count - 1) as Coord;
|
||||
let order_float = |a: &Coord, b: &Coord| a.partial_cmp(b).unwrap_or(core::cmp::Ordering::Equal);
|
||||
|
||||
let min_height = cells.iter().map(|c| c.constraint.min_height).max_by(order_float).unwrap()
|
||||
+ padding.top
|
||||
+ padding.bottom;
|
||||
|
||||
let max_height = cells.iter().map(|c| c.constraint.max_height).min_by(order_float).unwrap()
|
||||
+ padding.top
|
||||
+ padding.bottom;
|
||||
let min_width = cells.iter().map(|c| c.constraint.min_width).sum::<Coord>() + extra_w;
|
||||
let max_width = cells.iter().map(|c| c.constraint.max_width).sum::<Coord>() + extra_w;
|
||||
LayoutInfo { min_width, max_width, min_height, max_height }
|
||||
}
|
||||
|
||||
|
|
|
@ -919,16 +919,17 @@ fn get_property_ptr(nr: &NamedReference, instance: InstanceRef) -> *const () {
|
|||
|
||||
use sixtyfps_corelib::layout::*;
|
||||
|
||||
pub struct GridLayoutWithCells<'a> {
|
||||
pub struct LayoutWithCells<'a, C> {
|
||||
geometry: &'a sixtyfps_compilerlib::layout::LayoutGeometry,
|
||||
cells: Vec<GridLayoutCellData<'a>>,
|
||||
cells: Vec<C>,
|
||||
spacing: f32,
|
||||
padding: Padding,
|
||||
}
|
||||
|
||||
#[derive(derive_more::From)]
|
||||
enum LayoutTreeItem<'a> {
|
||||
GridLayout(GridLayoutWithCells<'a>),
|
||||
GridLayout(LayoutWithCells<'a, GridLayoutCellData<'a>>),
|
||||
BoxLayout(LayoutWithCells<'a, BoxLayoutCellData<'a>>),
|
||||
PathLayout(&'a PathLayout),
|
||||
}
|
||||
|
||||
|
@ -940,6 +941,11 @@ impl<'a> LayoutTreeItem<'a> {
|
|||
grid_layout.spacing,
|
||||
&grid_layout.padding,
|
||||
),
|
||||
LayoutTreeItem::BoxLayout(box_layout) => box_layout_info(
|
||||
&Slice::from(box_layout.cells.as_slice()),
|
||||
box_layout.spacing,
|
||||
&box_layout.padding,
|
||||
),
|
||||
LayoutTreeItem::PathLayout(_) => todo!(),
|
||||
}
|
||||
}
|
||||
|
@ -1034,32 +1040,24 @@ fn collect_layouts_recursively<'a, 'b>(
|
|||
bottom: grid_layout.geometry.padding.bottom.as_ref().map_or(0., expr_eval),
|
||||
};
|
||||
layout_tree.push(
|
||||
GridLayoutWithCells { geometry: &grid_layout.geometry, cells, spacing, padding }
|
||||
.into(),
|
||||
LayoutWithCells { geometry: &grid_layout.geometry, cells, spacing, padding }.into(),
|
||||
);
|
||||
}
|
||||
Layout::BoxLayout(box_layout) => {
|
||||
let cells = box_layout
|
||||
.elems
|
||||
.iter()
|
||||
.enumerate()
|
||||
.map(|(idx, cell)| {
|
||||
.map(|cell| {
|
||||
let mut layout_info =
|
||||
get_layout_info(&cell.item, component, layout_tree, window);
|
||||
fill_layout_info_constraints(&mut layout_info, &cell.constraints, &expr_eval);
|
||||
let (col, row) =
|
||||
if box_layout.is_horizontal { (idx as u16, 0) } else { (0, idx as u16) };
|
||||
let rect = cell.item.rect();
|
||||
|
||||
GridLayoutCellData {
|
||||
BoxLayoutCellData {
|
||||
x: assume_property_f32(&rect.x_reference),
|
||||
y: assume_property_f32(&rect.y_reference),
|
||||
width: assume_property_f32(&rect.width_reference),
|
||||
height: assume_property_f32(&rect.height_reference),
|
||||
col,
|
||||
row,
|
||||
colspan: 1,
|
||||
rowspan: 1,
|
||||
constraint: layout_info,
|
||||
}
|
||||
})
|
||||
|
@ -1072,8 +1070,7 @@ fn collect_layouts_recursively<'a, 'b>(
|
|||
bottom: box_layout.geometry.padding.bottom.as_ref().map_or(0., expr_eval),
|
||||
};
|
||||
layout_tree.push(
|
||||
GridLayoutWithCells { geometry: &box_layout.geometry, cells, spacing, padding }
|
||||
.into(),
|
||||
LayoutWithCells { geometry: &box_layout.geometry, cells, spacing, padding }.into(),
|
||||
);
|
||||
}
|
||||
Layout::PathLayout(layout) => layout_tree.push(layout.into()),
|
||||
|
@ -1104,6 +1101,17 @@ impl<'a> LayoutTreeItem<'a> {
|
|||
cells: Slice::from(grid_layout.cells.as_slice()),
|
||||
});
|
||||
}
|
||||
Self::BoxLayout(box_layout) => {
|
||||
solve_box_layout(&BoxLayoutData {
|
||||
width: resolve_prop_ref(&box_layout.geometry.rect.width_reference),
|
||||
height: resolve_prop_ref(&box_layout.geometry.rect.height_reference),
|
||||
x: resolve_prop_ref(&box_layout.geometry.rect.x_reference),
|
||||
y: resolve_prop_ref(&box_layout.geometry.rect.y_reference),
|
||||
spacing: box_layout.spacing,
|
||||
padding: &box_layout.padding,
|
||||
cells: Slice::from(box_layout.cells.as_slice()),
|
||||
});
|
||||
}
|
||||
Self::PathLayout(path_layout) => {
|
||||
use sixtyfps_corelib::layout::*;
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue