tawasuyu

tawasuyu/taffy

A high performance rust-powered UI layout library

HTML 5544Rust 88Markdown 11TOML 91926 Definiciones

Ensure that root flexbox node sizes are floored by their padding border (#655)

* Uses the sum of border and padding if it's greater than the containers definite size

* Ensure that root flexbox node sizes are floored by their padding border

Co-authored-by: Julia Ortiz <contato@juliaortiz.com.br>

---------

Co-authored-by: Julia Ortiz <contato@juliaortiz.com.br>

c154b8aa719da0d6f8636b123765a47fa40a3306 · por Nico Burns · (hace 2 años) · padre 04e20d1de · ver el árbol en este commit

Delta semántico · 4

src/compute/flexbox.rs

tests/generated/flex/mod.rs

tests/generated/flex/padding_border_overrides_size_root.rs

tests/root_constraints.rs

6 archivos · +138 −3

diff --git a/RELEASES.md b/RELEASES.md
index 811ec88f9..c76236dda 100644
--- a/RELEASES.md
+++ b/RELEASES.md
@@ -5,6 +5,7 @@
 ### Fixes
 
 - Content alignment (`align-content`/`justify-content`) behaviour was updated to match the latest spec (and Chrome 123+) (#635)
+- Ensure that root Flexbox nodes are floored by their padding-border (#651, #655)
 
 ## 0.4.3
 
diff --git a/src/compute/flexbox.rs b/src/compute/flexbox.rs
index 592b8ec20..464cd0a91 100644
--- a/src/compute/flexbox.rs
+++ b/src/compute/flexbox.rs
@@ -161,6 +161,9 @@ pub fn compute_flexbox_layout(tree: &mut impl LayoutPartialTree, node: NodeId, i
     let aspect_ratio = style.aspect_ratio;
     let min_size = style.min_size.maybe_resolve(parent_size).maybe_apply_aspect_ratio(aspect_ratio);
     let max_size = style.max_size.maybe_resolve(parent_size).maybe_apply_aspect_ratio(aspect_ratio);
+    let padding = style.padding.resolve_or_zero(parent_size.width);
+    let border = style.border.resolve_or_zero(parent_size.width);
+    let padding_border_sum = padding.sum_axes() + border.sum_axes();
     let clamped_style_size = if inputs.sizing_mode == SizingMode::InherentSize {
         style.size.maybe_resolve(parent_size).maybe_apply_aspect_ratio(aspect_ratio).maybe_clamp(min_size, max_size)
     } else {
@@ -172,7 +175,10 @@ pub fn compute_flexbox_layout(tree: &mut impl LayoutPartialTree, node: NodeId, i
         (Some(min), Some(max)) if max <= min => Some(min),
         _ => None,
     });
-    let styled_based_known_dimensions = known_dimensions.or(min_max_definite_size).or(clamped_style_size);
+
+    // The size of the container should be floored by the padding and border
+    let styled_based_known_dimensions =
+        known_dimensions.or(min_max_definite_size.or(clamped_style_size).maybe_max(padding_border_sum));
 
     // Short-circuit layout if the container's size is fully determined by the container's size and the run mode
     // is ComputeSize (and thus the container's size is all that we're interested in)
diff --git a/test_fixtures/flex/padding_border_overrides_size_root.html b/test_fixtures/flex/padding_border_overrides_size_root.html
new file mode 100644
index 000000000..9dbcfe951
--- /dev/null
+++ b/test_fixtures/flex/padding_border_overrides_size_root.html
@@ -0,0 +1,17 @@
+<!DOCTYPE html>
+<html lang="en">
+<head>
+  <script src="../../scripts/gentest/test_helper.js"></script>
+  <link rel="stylesheet" type="text/css" href="../../scripts/gentest/test_base_style.css">
+  <title>
+    Test description
+  </title>
+</head>
+<body>
+
+<div id="test-root" style="width: 12px; height: 12px; padding: 2px 4px 6px 8px; border-width: 1px 3px 5px 7px; border-style: solid; border-color: red;">
+  <div></div>
+</div>
+
+</body>
+</html>
\ No newline at end of file
diff --git a/tests/generated/flex/mod.rs b/tests/generated/flex/mod.rs
index 6e427742d..b2f6d34c4 100644
--- a/tests/generated/flex/mod.rs
+++ b/tests/generated/flex/mod.rs
@@ -425,6 +425,7 @@ mod padding_border_overrides_min_size;
 mod padding_border_overrides_size;
 mod padding_border_overrides_size_flex_basis_0;
 mod padding_border_overrides_size_flex_basis_0_growable;
+mod padding_border_overrides_size_root;
 mod padding_center_child;
 mod padding_container_match_child;
 mod padding_flex_child;
diff --git a/tests/generated/flex/padding_border_overrides_size_root.rs b/tests/generated/flex/padding_border_overrides_size_root.rs
new file mode 100644
index 000000000..33f2844fb
--- /dev/null
+++ b/tests/generated/flex/padding_border_overrides_size_root.rs
@@ -0,0 +1,83 @@
+#[test]
+fn padding_border_overrides_size_root() {
+    #[allow(unused_imports)]
+    use taffy::{prelude::*, tree::Layout, TaffyTree};
+    let mut taffy: TaffyTree<crate::TextMeasure> = TaffyTree::new();
+    let node0 = taffy.new_leaf(taffy::style::Style { ..Default::default() }).unwrap();
+    let node = taffy
+        .new_with_children(
+            taffy::style::Style {
+                size: taffy::geometry::Size {
+                    width: taffy::style::Dimension::Length(12f32),
+                    height: taffy::style::Dimension::Length(12f32),
+                },
+                padding: taffy::geometry::Rect {
+                    left: taffy::style::LengthPercentage::Length(8f32),
+                    right: taffy::style::LengthPercentage::Length(4f32),
+                    top: taffy::style::LengthPercentage::Length(2f32),
+                    bottom: taffy::style::LengthPercentage::Length(6f32),
+                },
+                border: taffy::geometry::Rect {
+                    left: taffy::style::LengthPercentage::Length(7f32),
+                    right: taffy::style::LengthPercentage::Length(3f32),
+                    top: taffy::style::LengthPercentage::Length(1f32),
+                    bottom: taffy::style::LengthPercentage::Length(5f32),
+                },
+                ..Default::default()
+            },
+            &[node0],
+        )
+        .unwrap();
+    taffy.compute_layout_with_measure(node, taffy::geometry::Size::MAX_CONTENT, crate::test_measure_function).unwrap();
+    println!("\nComputed tree:");
+    taffy.print_tree(node);
+    println!();
+    #[cfg_attr(not(feature = "content_size"), allow(unused_variables))]
+    let layout @ Layout { size, location, .. } = taffy.layout(node).unwrap();
+    assert_eq!(size.width, 22f32, "width of node {:?}. Expected {}. Actual {}", node, 22f32, size.width);
+    assert_eq!(size.height, 14f32, "height of node {:?}. Expected {}. Actual {}", node, 14f32, size.height);
+    assert_eq!(location.x, 0f32, "x of node {:?}. Expected {}. Actual {}", node, 0f32, location.x);
+    assert_eq!(location.y, 0f32, "y of node {:?}. Expected {}. Actual {}", node, 0f32, location.y);
+    #[cfg(feature = "content_size")]
+    assert_eq!(
+        layout.scroll_width(),
+        0f32,
+        "scroll_width of node {:?}. Expected {}. Actual {}",
+        node,
+        0f32,
+        layout.scroll_width()
+    );
+    #[cfg(feature = "content_size")]
+    assert_eq!(
+        layout.scroll_height(),
+        0f32,
+        "scroll_height of node {:?}. Expected {}. Actual {}",
+        node,
+        0f32,
+        layout.scroll_height()
+    );
+    #[cfg_attr(not(feature = "content_size"), allow(unused_variables))]
+    let layout @ Layout { size, location, .. } = taffy.layout(node0).unwrap();
+    assert_eq!(size.width, 0f32, "width of node {:?}. Expected {}. Actual {}", node0, 0f32, size.width);
+    assert_eq!(size.height, 0f32, "height of node {:?}. Expected {}. Actual {}", node0, 0f32, size.height);
+    assert_eq!(location.x, 15f32, "x of node {:?}. Expected {}. Actual {}", node0, 15f32, location.x);
+    assert_eq!(location.y, 3f32, "y of node {:?}. Expected {}. Actual {}", node0, 3f32, location.y);
+    #[cfg(feature = "content_size")]
+    assert_eq!(
+        layout.scroll_width(),
+        0f32,
+        "scroll_width of node {:?}. Expected {}. Actual {}",
+        node0,
+        0f32,
+        layout.scroll_width()
+    );
+    #[cfg(feature = "content_size")]
+    assert_eq!(
+        layout.scroll_height(),
+        0f32,
+        "scroll_height of node {:?}. Expected {}. Actual {}",
+        node0,
+        0f32,
+        layout.scroll_height()
+    );
+}
diff --git a/tests/root_constraints.rs b/tests/root_constraints.rs
index 9216118d2..631751d48 100644
--- a/tests/root_constraints.rs
+++ b/tests/root_constraints.rs
@@ -1,7 +1,7 @@
 #[cfg(test)]
 mod root_constraints {
-    use taffy::style::AvailableSpace;
-    use taffy::TaffyTree;
+    use taffy::style_helpers::{length, TaffyMaxContent};
+    use taffy::{AvailableSpace, Rect, Size, Style, TaffyTree};
 
     #[test]
     fn root_with_percentage_size() {
@@ -78,4 +78,31 @@ mod root_constraints {
         assert_eq!(layout.size.width, 200.0);
         assert_eq!(layout.size.height, 200.0);
     }
+
+    #[test]
+    fn root_padding_and_border_larger_than_definite_size() {
+        let mut tree: TaffyTree<()> = TaffyTree::with_capacity(16);
+
+        let child = tree.new_leaf(Style::default()).unwrap();
+
+        let root = tree
+            .new_with_children(
+                Style {
+                    size: Size { width: length(10.0), height: length(10.0) },
+                    padding: Rect { left: length(10.0), right: length(10.0), top: length(10.0), bottom: length(10.0) },
+
+                    border: Rect { left: length(10.0), right: length(10.0), top: length(10.0), bottom: length(10.0) },
+                    ..Default::default()
+                },
+                &[child],
+            )
+            .unwrap();
+
+        tree.compute_layout(root, Size::MAX_CONTENT).unwrap();
+
+        let layout = tree.layout(root).unwrap();
+
+        assert_eq!(layout.size.width, 40.0);
+        assert_eq!(layout.size.height, 40.0);
+    }
 }