diff options
Diffstat (limited to 'Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp')
-rw-r--r-- | Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp | 319 |
1 files changed, 179 insertions, 140 deletions
diff --git a/Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp b/Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp index f98d1b8816..2c4120c6ee 100644 --- a/Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp +++ b/Userland/Libraries/LibWeb/Layout/FlexFormattingContext.cpp @@ -17,6 +17,11 @@ namespace Web::Layout { +static float get_pixel_size(Box const& box, CSS::Length const& length) +{ + return length.resolved(CSS::Length::make_px(0), box, box.containing_block()->width()).to_px(box); +} + FlexFormattingContext::FlexFormattingContext(Box& flex_container, FormattingContext* parent) : FormattingContext(flex_container, parent) , m_flex_direction(flex_container.computed_values().flex_direction()) @@ -69,9 +74,6 @@ void FlexFormattingContext::run(Box& flex_container, LayoutMode) // Determine main/cross direction auto main_size_is_infinite = false; - auto get_pixel_size = [](Box& box, const CSS::Length& length) { - return length.resolved(CSS::Length::make_px(0), box, box.containing_block()->width()).to_px(box); - }; auto layout_for_maximum_main_size = [&](Box& box) { bool main_constrained = false; if (is_row) { @@ -118,113 +120,6 @@ void FlexFormattingContext::run(Box& flex_container, LayoutMode) return NumericLimits<float>::max(); } }; - auto has_definite_main_size = [&is_row](Box& box) { - return is_row ? box.has_definite_width() : box.has_definite_height(); - }; - Function<bool(NodeWithStyle&)> cross_size_is_absolute_or_resolved_nicely = [&](NodeWithStyle& box) { - auto length = is_row ? box.computed_values().height() : box.computed_values().width(); - - if (length.is_absolute() || length.is_relative()) - return true; - if (length.is_undefined_or_auto()) - return false; - - if (!box.parent()) - return false; - if (length.is_percentage() && cross_size_is_absolute_or_resolved_nicely(*box.parent())) - return true; - return false; - }; - auto has_definite_cross_size = [&is_row, &cross_size_is_absolute_or_resolved_nicely](Box& box) { - return (is_row ? box.has_definite_height() : box.has_definite_width()) && cross_size_is_absolute_or_resolved_nicely(box); - }; - auto specified_main_size = [&is_row](Box& box) { - return is_row - ? box.width() - : box.height(); - }; - auto specified_main_size_of_child_box = [&is_row, &specified_main_size](Box& box, Box& child_box) { - auto main_size_of_parent = specified_main_size(box); - if (is_row) { - return child_box.computed_values().width().resolved_or_zero(child_box, main_size_of_parent).to_px(child_box); - } else { - return child_box.computed_values().height().resolved_or_zero(child_box, main_size_of_parent).to_px(child_box); - } - }; - auto specified_cross_size = [&is_row](Box& box) { - return is_row - ? box.height() - : box.width(); - }; - auto has_main_min_size = [&is_row](Box& box) { - return is_row - ? !box.computed_values().min_width().is_undefined_or_auto() - : !box.computed_values().min_height().is_undefined_or_auto(); - }; - auto has_cross_min_size = [&is_row](Box& box) { - return is_row - ? !box.computed_values().min_height().is_undefined_or_auto() - : !box.computed_values().min_width().is_undefined_or_auto(); - }; - auto specified_main_min_size = [&is_row, &get_pixel_size](Box& box) { - return is_row - ? get_pixel_size(box, box.computed_values().min_width()) - : get_pixel_size(box, box.computed_values().min_height()); - }; - auto specified_cross_min_size = [&is_row, &get_pixel_size](Box& box) { - return is_row - ? get_pixel_size(box, box.computed_values().min_height()) - : get_pixel_size(box, box.computed_values().min_width()); - }; - auto has_main_max_size = [&is_row](Box& box) { - return is_row - ? !box.computed_values().max_width().is_undefined_or_auto() - : !box.computed_values().max_height().is_undefined_or_auto(); - }; - auto has_cross_max_size = [&is_row](Box& box) { - return is_row - ? !box.computed_values().max_height().is_undefined_or_auto() - : !box.computed_values().max_width().is_undefined_or_auto(); - }; - auto specified_main_max_size = [&is_row, &get_pixel_size](Box& box) { - return is_row - ? get_pixel_size(box, box.computed_values().max_width()) - : get_pixel_size(box, box.computed_values().max_height()); - }; - auto specified_cross_max_size = [&is_row, &get_pixel_size](Box& box) { - return is_row - ? get_pixel_size(box, box.computed_values().max_height()) - : get_pixel_size(box, box.computed_values().max_width()); - }; - auto calculated_main_size = [&is_row](Box& box) { - return is_row ? box.width() : box.height(); - }; - auto is_cross_auto = [&is_row](Box& box) { - return is_row ? box.computed_values().height().is_auto() : box.computed_values().width().is_auto(); - }; - auto is_main_axis_margin_first_auto = [&is_row](Box& box) { - return is_row ? box.computed_values().margin().left.is_auto() : box.computed_values().margin().top.is_auto(); - }; - auto is_main_axis_margin_second_auto = [&is_row](Box& box) { - return is_row ? box.computed_values().margin().right.is_auto() : box.computed_values().margin().bottom.is_auto(); - }; - auto sum_of_margin_padding_border_in_main_axis = [&is_row](Box& box) { - if (is_row) { - return box.box_model().margin.left - + box.box_model().margin.right - + box.box_model().padding.left - + box.box_model().padding.right - + box.box_model().border.left - + box.box_model().border.right; - } else { - return box.box_model().margin.top - + box.box_model().margin.bottom - + box.box_model().padding.top - + box.box_model().padding.bottom - + box.box_model().border.top - + box.box_model().border.bottom; - } - }; auto calculate_hypothetical_cross_size = [&is_row, this](Box& box) { bool cross_constrained = false; if (is_row) { @@ -256,36 +151,6 @@ void FlexFormattingContext::run(Box& flex_container, LayoutMode) return box.width(); } }; - auto set_main_size = [&is_row](Box& box, float size) { - if (is_row) - box.set_width(size); - else - box.set_height(size); - }; - auto set_cross_size = [&is_row](Box& box, float size) { - if (is_row) - box.set_height(size); - else - box.set_width(size); - }; - auto set_offset = [&is_row](Box& box, float main_offset, float cross_offset) { - if (is_row) - box.set_offset(main_offset, cross_offset); - else - box.set_offset(cross_offset, main_offset); - }; - auto set_main_axis_first_margin = [&is_row](Box& box, float margin) { - if (is_row) - box.box_model().margin.left = margin; - else - box.box_model().margin.top = margin; - }; - auto set_main_axis_second_margin = [&is_row](Box& box, float margin) { - if (is_row) - box.box_model().margin.right = margin; - else - box.box_model().margin.bottom = margin; - }; Vector<FlexItem> flex_items; @@ -859,4 +724,178 @@ void FlexFormattingContext::generate_anonymous_flex_items(Box& flex_container, V }); } +bool FlexFormattingContext::has_definite_main_size(Box const& box) const +{ + return is_row_layout() ? box.has_definite_width() : box.has_definite_height(); +} + +float FlexFormattingContext::specified_main_size(Box const& box) const +{ + return is_row_layout() ? box.width() : box.height(); +} + +float FlexFormattingContext::specified_cross_size(Box const& box) const +{ + return is_row_layout() ? box.height() : box.width(); +} + +bool FlexFormattingContext::has_main_min_size(Box const& box) const +{ + auto value = is_row_layout() ? box.computed_values().min_width() : box.computed_values().min_height(); + return !value.is_undefined_or_auto(); +} + +bool FlexFormattingContext::has_cross_min_size(Box const& box) const +{ + auto value = is_row_layout() ? box.computed_values().min_height() : box.computed_values().min_width(); + return !value.is_undefined_or_auto(); +} + +bool FlexFormattingContext::has_definite_cross_size(Box const& box) const +{ + return (is_row_layout() ? box.has_definite_height() : box.has_definite_width()) && cross_size_is_absolute_or_resolved_nicely(box); +} + +bool FlexFormattingContext::cross_size_is_absolute_or_resolved_nicely(NodeWithStyle const& box) const +{ + auto length = is_row_layout() ? box.computed_values().height() : box.computed_values().width(); + + if (length.is_absolute() || length.is_relative()) + return true; + if (length.is_undefined_or_auto()) + return false; + + if (!box.parent()) + return false; + if (length.is_percentage() && cross_size_is_absolute_or_resolved_nicely(*box.parent())) + return true; + return false; +} + +float FlexFormattingContext::specified_main_size_of_child_box(Box const& flex_container, Box const& child_box) const +{ + auto main_size_of_parent = specified_main_size(flex_container); + auto value = is_row_layout() ? child_box.computed_values().width() : child_box.computed_values().height(); + return value.resolved_or_zero(child_box, main_size_of_parent).to_px(child_box); +} + +float FlexFormattingContext::specified_main_min_size(Box const& box) const +{ + return is_row_layout() + ? get_pixel_size(box, box.computed_values().min_width()) + : get_pixel_size(box, box.computed_values().min_height()); +} + +float FlexFormattingContext::specified_cross_min_size(Box const& box) const +{ + return is_row_layout() + ? get_pixel_size(box, box.computed_values().min_height()) + : get_pixel_size(box, box.computed_values().min_width()); +} + +bool FlexFormattingContext::has_main_max_size(Box const& box) const +{ + return is_row_layout() + ? !box.computed_values().max_width().is_undefined_or_auto() + : !box.computed_values().max_height().is_undefined_or_auto(); +} + +bool FlexFormattingContext::has_cross_max_size(Box const& box) const +{ + return is_row_layout() + ? !box.computed_values().max_height().is_undefined_or_auto() + : !box.computed_values().max_width().is_undefined_or_auto(); +} + +float FlexFormattingContext::specified_main_max_size(Box const& box) const +{ + return is_row_layout() + ? get_pixel_size(box, box.computed_values().max_width()) + : get_pixel_size(box, box.computed_values().max_height()); +} + +float FlexFormattingContext::specified_cross_max_size(Box const& box) const +{ + return is_row_layout() + ? get_pixel_size(box, box.computed_values().max_height()) + : get_pixel_size(box, box.computed_values().max_width()); +} + +float FlexFormattingContext::calculated_main_size(Box const& box) const +{ + return is_row_layout() ? box.width() : box.height(); +} + +bool FlexFormattingContext::is_cross_auto(Box const& box) const +{ + return is_row_layout() ? box.computed_values().height().is_auto() : box.computed_values().width().is_auto(); +} + +bool FlexFormattingContext::is_main_axis_margin_first_auto(Box const& box) const +{ + return is_row_layout() ? box.computed_values().margin().left.is_auto() : box.computed_values().margin().top.is_auto(); +} + +bool FlexFormattingContext::is_main_axis_margin_second_auto(Box const& box) const +{ + return is_row_layout() ? box.computed_values().margin().right.is_auto() : box.computed_values().margin().bottom.is_auto(); +} + +void FlexFormattingContext::set_main_size(Box& box, float size) +{ + if (is_row_layout()) + box.set_width(size); + else + box.set_height(size); +} + +void FlexFormattingContext::set_cross_size(Box& box, float size) +{ + if (is_row_layout()) + box.set_height(size); + else + box.set_width(size); +} + +void FlexFormattingContext::set_offset(Box& box, float main_offset, float cross_offset) +{ + if (is_row_layout()) + box.set_offset(main_offset, cross_offset); + else + box.set_offset(cross_offset, main_offset); +} + +void FlexFormattingContext::set_main_axis_first_margin(Box& box, float margin) +{ + if (is_row_layout()) + box.box_model().margin.left = margin; + else + box.box_model().margin.top = margin; +} + +void FlexFormattingContext::set_main_axis_second_margin(Box& box, float margin) +{ + if (is_row_layout()) + box.box_model().margin.right = margin; + else + box.box_model().margin.bottom = margin; +} + +float FlexFormattingContext::sum_of_margin_padding_border_in_main_axis(Box const& box) const +{ + auto& margin = box.box_model().margin; + auto& padding = box.box_model().padding; + auto& border = box.box_model().border; + + if (is_row_layout()) { + return margin.left + margin.right + + padding.left + padding.right + + border.left + border.right; + } else { + return margin.top + margin.bottom + + padding.top + padding.bottom + + border.top + border.bottom; + } +} + } |