These methods were doing virtually the same thing. So this patch moves
the common logic into a new `FlexItemBox::to_flex_item()`, which is then
called by `FlexItem::new()` and `FlexItemBox::main_content_size_info()`.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
`Size::resolve_for_min()` had an `Au` parameter, representing the value
to be used for an automatic minimum size. However, this amount isn't
trivial to compute in flexbox, so this patch changes the parameter to a
function that can be called lazily.
Note flexbox isn't currently using `Size::resolve_for_min()`, but it
will in #35961.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* Migrate to 2024 edition
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Allow unsafe_op_in_unsafe_fn lint
This lint warns by default in the 2024
edition, but is *way* too noisy for servo.
We might enable it in the future, but not now.
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Compile using the 2024 edition
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
---------
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
We were already not compiling it and not running tests on it by default.
So it's simpler to just completely remove it.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
In particular:
- `z-index` will now work on unpositioned grid items.
- `will-change: z-index` will only establish a stacking context if
`z-index` applies, i.e. if the box is positioned or a flex/grid item.
- The conditions in `establishes_stacking_context()` are reordered,
so that the most likely ones are checked first.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
When computing the intrinsic block size of a replaced element with a
computed preferred inline size of `auto`, instead of transferring the
final inline size through the aspect ratio, we were only transferring
the min and max constraints.
We did this to match other browsers, but Ian Kilpatrick agreed that this
is a bug and plans to change Blink.
CSSWG issue: https://github.com/w3c/csswg-drafts/issues/11236
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
The CSSWG resolved that `block-size: stretch` on a block-level box
stretches the margin box to fill the parent. However, if the parent
doesn't have padding nor border, and doesn't establish an independent
formatting context, then we assume that the margins will collapse.
Therefore, we treat the margins as zero when resolving the stretch size,
regardless of whether they will actually end up collapsing.
https://github.com/w3c/csswg-drafts/issues/11044#issuecomment-2599101601https://drafts.csswg.org/css-sizing-4/#stretch-fit-sizing
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
One of the callers was only used for an assert, and it was passing an
inline size argument to a parameter expecting a block size, so it wasn't
making much sense anyways.
Just inline the code into the other caller, and for consistency remove
the assert for replaced elements too.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
Adds support for min-content, max-content, fit-content and stretch on
the min and max cross size properties of a flex item.
With one exception: when resolving the main sizes, transferred cross
minimums and maximums will still ignore keywords.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
We were ignoring `table-layout: fixed` both for `inline-size: auto` and
`inline-size: max-content`. However, the CSSWG resolved that fixed table
layout should be triggered except when `inline-size` is `auto`.
https://github.com/w3c/csswg-drafts/issues/10937#issuecomment-2669150397
Blink has already adopted this change, and they modified the WPT
`/css/css-tables/fixed-layout-2.html` accordingly. Here I'm doing some
further cosmetic cleanups to the test.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* support CSS `will-change`
* update wpt-test result
* Enable css-will-change test
* Update css-will-change test results
* Check transformable before will-change; update wpt-results
* Solve merge conflict
* Update Cargo.toml and Cargo.lock
* Mark new failing test-cases
---------
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: Fix behavior of `transform-style: preserve-3d`
This makes `transform-style: preserve-3d` establish a containing block
for all descendants, as specified here:
<https://drafts.csswg.org/css-transforms-2/#transform-style-property>
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
* layout: Check for transformable elements
Adds a new `is_transformable` helper method and use this in several other
methods, including the methods for whether the fragment establishes a
new stacking context or a containing block for all descendants.
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
* Use generic green square reference for reftest.
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
* layout: Fix stacking context & containing block checks.
Only the computed value of `transform-style` should be used to determine
whether the element establishes a stacking context and/or a containing
block, not the used value.
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
* Update clip-no-stacking-context test expectation to pass.
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
---------
Signed-off-by: Daniel Hast <hast.daniel@protonmail.com>
This function showed up as a top producer of allocations
(around 10% of all allocations).
Allocating the vector once upfront and using
`collect_into_vec` removes any intermediate allocations.
This approach is also recommended by the rayon documentation:
https://docs.rs/rayon/1.10.0/rayon/iter/trait.ParallelIterator.html#method.collect
Signed-off-by: Jonathan Schwender <schwenderjonathan@gmail.com>
This changes `FlexItem::content_cross_size` into `Size<Au>` to preserve
keyword sizes. The calculation of the hypothetical cross size still
ignores them though, that will be addressed in a follow-up.
Also, browsers don't follow the spec and treat a stretch size different
than a stretch alignment: the former stretches to the containing block,
while the latter stretches to the line. This aligns Servo with that
behavior (following the spec would require bigger refactorings), so
`stretches()` is renamed to `stretches_to_line()` for clarity.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* Use 2024 style edition
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Reformat all code
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
---------
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
Instead of keeping a per-FontGroup cache of the previously used fallback
font, cache this value in the caller of `FontGroup::find_by_codepoint`.
The problem with caching this value in the `FontGroup` is that it can
make one layout different from the next.
Still, it is important to cache the value somewhere so that, for
instance, Chinese character don't have to continuously walk through the
entire fallback list when laying out. The heuristic here is to try to
last used font first if the `Script`s match. At the very least this
should make one layout consistent with the next.
Fixes#35704.
Fixes#35697.
Fixes#35689.
Fixes#35679.
Signed-off-by: Martin Robinson <mrobinson@igalia.com>
* Squash and don't explicitly use noto-cjk in tests
Signed-off-by: Xiaocheng Hu <xiaochengh.work@gmail.com>
* Mark quotes-034.html.ini failure
Signed-off-by: Xiaocheng Hu <xiaochengh.work@gmail.com>
* Address review comments
Signed-off-by: Xiaocheng Hu <xiaochengh.work@gmail.com>
---------
Signed-off-by: Xiaocheng Hu <xiaochengh.work@gmail.com>
An intrinsic flex base size depends on the contents, which may depend on
the cross size through an aspect ratio. We were only taking this into
account if the preferred cross size was numeric, but `auto` or `stretch`
can also be definite.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
The computation of the flex base size may involve transferring a
definite cross size into the main axis through the aspect ratio.
We were only considering numeric sizes as definite, but `stretch` can
also be definite.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
The computation of the automatic minimum size may involve transferring
a definite cross size into the main axis through the aspect ratio.
We were only considering numeric sizes as definite, but `stretch` can
also be definite.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
This method was taking an `IndefiniteContainingBlock` parameter, and
then it would first take the size corresponding to the main axis, and
then the one for the cross axis.
But it's simpler to just let it take a `FlexRelativeVec2<AuOrAuto>`
parameter.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* Update to rust 1.85
This is needed for cargo-deny
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Upgrade crown
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Clippy fixes
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
* Re-upgrade cargo-deny to 0.18
Keeping it locked to 0.18 just in case they
update their required rustc version again
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
---------
Signed-off-by: Simon Wülker <simon.wuelker@arcor.de>
We were always treating an indefinite `stretch` as the automatic size.
This instead treats it as `0px` on min sizing properties, and as `none`
on max sizing properties, aligning with Blink and this recent CSSWG
resolution: https://github.com/w3c/csswg-drafts/issues/11006
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* Add tests for sizing keywords on flex items
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* layout: Partial support for sizing keywords on flex items
When a flex item has `flex-basis: auto`, the used `flex-basis` is the
value of the main size property. In that case, if the main size property
was set to keyword, we were always assuming it was `auto`. Now we handle
non-`auto` keywords correctly.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
---------
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
* layout: Add AxesScrollSensitivity to enable control of scroll in axis
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout_2013: Be compatible with AxesScrollSensitivity
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: update struct AxesScrollSensitivity to euclid::Vector2D
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* display_list: implement From<Overflow> for ScrollSensitivity
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: simplify and reuse scroll related logic
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout_2013: simplify and reuse scroll related logic
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout, layout_2013: revert AxesScrollSensitivity to pair struct
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: Reimport ComputedOverflow as #35103 depends on it
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: Add AxesOverflow to replace PhysicalVec
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: implement scroll of viewport for different axes
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* layout: explicitly handle overflow match
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
* Update components/shared/webrender/Cargo.toml
Co-authored-by: Martin Robinson <mrobinson@igalia.com>
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
---------
Signed-off-by: Euclid Ye <yezhizhenjiakang@gmail.com>
Co-authored-by: Martin Robinson <mrobinson@igalia.com>
layout: Basic implementation of size keywords on `flex-basis`
This splits the logic to resolve the used value of `flex-basis` into its
own method, which preserves size keywords.
And then it changes `flex_base_size()` to resolve the provided keywords
properly. However, it doesn't handle size keywords in the cross axis.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
It had a single caller, and the relevant data was passed as parameters
because the caller needed it too. It seems simpler to just remove it
and inline the code into the caller.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
`Table::create_spanned_slot_based_on_cell_above()` was performing the
subtraction `self.slots.len() - 2`, which could theoretically result
in underflow if `self.slots.len()` is 0 or 1.
That shouldn't have been possible in practice, but it may be worth
addressing, to improve code robustness. So this patch:
- Switches to `self.current_y()?.checked_sub(1)?`, which is safe and
is easier to understand.
- Moves `create_spanned_slot_based_on_cell_above()` to `TableBuilder`,
since `current_y()` is there, and the method is only used when
building the table anyways.
- Ensures that both callers use `expect()` to assert that the method
returned a value.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
In addition to some small API changes, this downstream version of
WebRender no longer depends on a very old version of time. This is the
last step toward removing the dependency on `time0.1`.
The review for this commit should also include: 9f552bebab
Signed-off-by: Martin Robinson <mrobinson@igalia.com>
A box is usually sized by the formatting context in which it participates.
However, tables have some special sizing behaviors that we implemented
with a `content_inline_size_for_table` override.
However, breaking the assumptions of the formatting context isn't great.
It was also bad for performance that we could try to layout a table
among floats even though it wouldn't en up fitting because of a larger
min-content size.
Therefore, this changes the logic so that formatting contexts use some
special sizing for tables, and then tables only override that amount
when there are collapsed columns. Eventually, we should try to remove
that case too, see https://github.com/w3c/csswg-drafts/issues/11408
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
The outer display type of a table element applies to the table wrapper
box. The table grid box needs to be block-level as defined in
https://drafts.csswg.org/css-tables/#table-grid-box
Therefore this sets `display: table` on table grid boxes, and then when
painting collapsed table borders we can use the usual logic to compute
the StackingContextSection.
Signed-off-by: Oriol Brufau <obrufau@igalia.com>
In #35075 I painted them in front of the decorations (backgrounds and
borders) of any block-level box in the same stacking context. I did that
because other browsers paint them in front of the decorations of the
descendants of the table, but my approach also painted them in front of
decorations of following siblings of the table, which was wrong.
This patch makes it so that collapsed table orders are painted in the
same step as decorations. However, tables defer painting their collapsed
borders after the decorations of their descendants.
This matches Blink and WebKit, and brings us closer to Gecko (which is
slightly different in some corner cases).
Signed-off-by: Oriol Brufau <obrufau@igalia.com>