summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMoonchild <moonchild@palemoon.org>2023-08-14 10:34:09 +0200
committerMoonchild <moonchild@palemoon.org>2023-08-14 10:34:09 +0200
commit3bb0c18a5915b789beda27598f9d578516189f90 (patch)
tree3ea009c4240abe3da01effb3faf915f3e300d891
parent9bfeaab2e6d220eef448bdd551bccb4cae1816b0 (diff)
parent53b548e31ab64d3a723f44f63b99af044ba53147 (diff)
downloaduxp-3bb0c18a5915b789beda27598f9d578516189f90.tar.gz
Merge branch '2284-flexpercentage-work'
-rw-r--r--layout/generic/ReflowInput.cpp15
-rw-r--r--layout/generic/ReflowInput.h7
-rw-r--r--layout/generic/nsFlexContainerFrame.cpp50
-rw-r--r--layout/reftests/bugs/1128354-1-ref.html17
-rw-r--r--layout/reftests/bugs/1128354-1.html23
-rw-r--r--toolkit/themes/shared/in-content/info-pages.inc.css2
6 files changed, 104 insertions, 10 deletions
diff --git a/layout/generic/ReflowInput.cpp b/layout/generic/ReflowInput.cpp
index 1af7e798ef..4f5424dc44 100644
--- a/layout/generic/ReflowInput.cpp
+++ b/layout/generic/ReflowInput.cpp
@@ -226,6 +226,7 @@ ReflowInput::ReflowInput(
mFlags.mAssumingHScrollbar = mFlags.mAssumingVScrollbar = false;
mFlags.mIsColumnBalancing = false;
mFlags.mIsFlexContainerMeasuringHeight = false;
+ mFlags.mTreatBSizeAsIndefinite = false;
mFlags.mDummyParentReflowInput = false;
mFlags.mShrinkWrap = !!(aFlags & COMPUTE_SIZE_SHRINK_WRAP);
mFlags.mUseAutoBSize = !!(aFlags & COMPUTE_SIZE_USE_AUTO_BSIZE);
@@ -2041,6 +2042,10 @@ ReflowInput::ComputeContainingBlockRectangle(
WritingMode wm = aContainingBlockRI->GetWritingMode();
+ if (aContainingBlockRI->mFlags.mTreatBSizeAsIndefinite) {
+ cbSize.BSize(wm) = NS_UNCONSTRAINEDSIZE;
+ }
+
// mFrameType for abs-pos tables is NS_CSS_FRAME_TYPE_BLOCK, so we need to
// special case them here.
if (NS_FRAME_GET_TYPE(mFrameType) == NS_CSS_FRAME_TYPE_ABSOLUTE ||
@@ -2077,12 +2082,13 @@ ReflowInput::ComputeContainingBlockRectangle(
}
} else {
// an element in quirks mode gets a containing block based on looking for a
- // parent with a non-auto height if the element has a percent height
- // Note: We don't emulate this quirk for percents in calc() or in
- // vertical writing modes.
+ // parent with a non-auto height if the element has a percent height.
+ // Note: We don't emulate this quirk for percents in calc(), or in vertical
+ // writing modes, or if the containing block is a flex or grid item.
if (!wm.IsVertical() &&
NS_AUTOHEIGHT == cbSize.BSize(wm)) {
if (eCompatibility_NavQuirks == aPresContext->CompatibilityMode() &&
+ !aContainingBlockRI->mFrame->IsFlexOrGridItem() &&
mStylePosition->mHeight.GetUnit() == eStyleUnit_Percent) {
cbSize.BSize(wm) = CalcQuirkContainingBlockHeight(aContainingBlockRI);
}
@@ -2218,7 +2224,8 @@ ReflowInput::InitConstraints(nsPresContext* aPresContext,
// in quirks mode, get the cb height using the special quirk method
if (!wm.IsVertical() &&
eCompatibility_NavQuirks == aPresContext->CompatibilityMode()) {
- if (!IS_TABLE_CELL(fType)) {
+ if (!IS_TABLE_CELL(fType) &&
+ !cbrs->mFrame->IsFlexOrGridItem()) {
cbSize.BSize(wm) = CalcQuirkContainingBlockHeight(cbrs);
if (cbSize.BSize(wm) == NS_AUTOHEIGHT) {
blockSizeUnit = eStyleUnit_Auto;
diff --git a/layout/generic/ReflowInput.h b/layout/generic/ReflowInput.h
index a70549d8eb..52c90e6eeb 100644
--- a/layout/generic/ReflowInput.h
+++ b/layout/generic/ReflowInput.h
@@ -206,6 +206,13 @@ public:
uint32_t mIsFlexContainerMeasuringHeight:1; // nsFlexContainerFrame is
// reflowing this child to
// measure its intrinsic height.
+ uint32_t mTreatBSizeAsIndefinite:1; // If this flag is set, the BSize of this frame should be considered
+ // indefinite for the purposes of percent resolution on child frames (we
+ // should behave as if ComputedBSize() were NS_INTRINSIC_ISIZE when doing
+ // percent resolution against this.ComputedBSize()). For example: flex
+ // items may have their ComputedBSize() resolved ahead-of-time by their
+ // flex container, and yet their BSize might have to be considered
+ // indefinite per https://drafts.csswg.org/css-flexbox/#definite-sizes
uint32_t mDummyParentReflowInput:1; // a "fake" reflow state made
// in order to be the parent
// of a real one
diff --git a/layout/generic/nsFlexContainerFrame.cpp b/layout/generic/nsFlexContainerFrame.cpp
index 18a0643f14..d60308f424 100644
--- a/layout/generic/nsFlexContainerFrame.cpp
+++ b/layout/generic/nsFlexContainerFrame.cpp
@@ -557,6 +557,8 @@ public:
return mFlexShrink * mFlexBaseSize;
}
+ bool TreatBSizeAsIndefinite() const { return mTreatBSizeAsIndefinite; }
+
const AspectRatio IntrinsicRatio() const { return mIntrinsicRatio; }
bool HasIntrinsicRatio() const { return !!mIntrinsicRatio; }
@@ -799,6 +801,9 @@ protected:
// Does this item need to resolve a min-[width|height]:auto (in main-axis).
bool mNeedsMinSizeAutoResolution;
+ // Should we take care to treat this item's resolved BSize as indefinite?
+ bool mTreatBSizeAsIndefinite;
+
const WritingMode mWM; // The flex item's writing mode.
uint8_t mAlignSelf; // My "align-self" computed value (with "auto"
// swapped out for parent"s "align-items" value,
@@ -1990,6 +1995,40 @@ FlexItem::FlexItem(ReflowInput& aFlexItemReflowInput,
mAlignSelf &= ~NS_STYLE_ALIGN_FLAG_BITS;
}
+ // Our main-size is considered definite if any of these are true:
+ // (a) flex container has definite main size.
+ // (b) flex item has a definite flex basis and is fully inflexible
+ // (NOTE: We don't actually check "fully inflexible" because webcompat
+ // may not agree with that restriction...)
+ //
+ // Hence, we need to take care to treat the final main-size as *indefinite*
+ // if none of these conditions are satisfied.
+
+ // The flex item's main size is its BSize, and is considered definite under
+ // certain conditions laid out for definite flex-item main-sizes in the spec.
+ if (aAxisTracker.IsMainAxisHorizontal() ||
+ (containerRS->ComputedBSize() != NS_UNCONSTRAINEDSIZE &&
+ !containerRS->mFlags.mTreatBSizeAsIndefinite)) {
+ // The flex *container* has a definite main-size (either by being
+ // row-oriented [and using its own inline size which is by definition
+ // definite, or by being column-oriented and having a definite
+ // block-size). The spec says this means all of the flex items'
+ // post-flexing main sizes should *also* be treated as definite.
+ mTreatBSizeAsIndefinite = false;
+ } else if (aFlexBaseSize != NS_UNCONSTRAINEDSIZE) {
+ // The flex item has a definite flex basis, which we'll treat as making
+ // its main-size definite.
+ // XXXdholbert Technically the spec requires the flex item to *also* be
+ // fully inflexible in order to have its size treated as definite in this
+ // scenario, but no browser implements that additional restriction, so
+ // it's not clear that this additional requirement would be
+ // web-compatible...
+ mTreatBSizeAsIndefinite = false;
+ } else {
+ // Otherwise, we have to treat the item's BSize as indefinite.
+ mTreatBSizeAsIndefinite = true;
+ }
+
SetFlexBaseSizeAndMainSize(aFlexBaseSize);
CheckForMinSizeAuto(aFlexItemReflowInput, aAxisTracker);
@@ -2054,6 +2093,7 @@ FlexItem::FlexItem(nsIFrame* aChildFrame, nscoord aCrossSize,
mIsStretched(false),
mIsStrut(true), // (this is the constructor for making struts, after all)
mNeedsMinSizeAutoResolution(false),
+ mTreatBSizeAsIndefinite(false),
mWM(aContainerWM),
mAlignSelf(NS_STYLE_ALIGN_FLEX_START)
{
@@ -4463,6 +4503,9 @@ nsFlexContainerFrame::DoFlexLayout(nsPresContext* aPresContext,
childReflowInput.SetComputedWidth(item->GetMainSize());
} else {
childReflowInput.SetComputedHeight(item->GetMainSize());
+ if (item->TreatBSizeAsIndefinite()) {
+ childReflowInput.mFlags.mTreatBSizeAsIndefinite = true;
+ }
}
}
@@ -4802,6 +4845,9 @@ nsFlexContainerFrame::ReflowFlexItem(nsPresContext* aPresContext,
} else {
childReflowInput.SetComputedHeight(aItem.GetMainSize());
didOverrideComputedHeight = true;
+ if (aItem.TreatBSizeAsIndefinite()) {
+ childReflowInput.mFlags.mTreatBSizeAsIndefinite = true;
+ }
}
// Override reflow state's computed cross-size if either:
@@ -4819,6 +4865,10 @@ nsFlexContainerFrame::ReflowFlexItem(nsPresContext* aPresContext,
childReflowInput.SetComputedWidth(aItem.GetCrossSize());
didOverrideComputedWidth = true;
} else {
+ // Note that in the above cases we don't need to worry about the BSize
+ // needing to be treated as indefinite, because this is for cases where
+ // the block size would always be considered definite (or where its
+ // definiteness would be irrelevant).
childReflowInput.SetComputedHeight(aItem.GetCrossSize());
didOverrideComputedHeight = true;
}
diff --git a/layout/reftests/bugs/1128354-1-ref.html b/layout/reftests/bugs/1128354-1-ref.html
index a559370f22..a90b26e281 100644
--- a/layout/reftests/bugs/1128354-1-ref.html
+++ b/layout/reftests/bugs/1128354-1-ref.html
@@ -13,10 +13,21 @@
}
.flexInnerHoriz {
- display: flex;
+ height: -moz-fit-content;
+ margin: 0 0 auto 0;
background: pink;
}
-
+ .height50pct {
+ height: -moz-fit-content;
+ margin: 0 0 auto 0;
+ background: brown;
+ }
+ .height0pct {
+ height: -moz-fit-content;
+ margin: 0 0 auto 0;
+ background: yellow;
+ }
+
.spacer {
background: lightblue;
height: 200px;
@@ -28,6 +39,8 @@
<div class="flexVert">
<div class="flexIntermediateHoriz">
<div class="flexInnerHoriz">text</div>
+ <div class="height50pct">fifty</div>
+ <div class="height0pct">zero</div>
<div class="spacer"></div>
</div>
</div>
diff --git a/layout/reftests/bugs/1128354-1.html b/layout/reftests/bugs/1128354-1.html
index c83bcf8b25..7c6dc87272 100644
--- a/layout/reftests/bugs/1128354-1.html
+++ b/layout/reftests/bugs/1128354-1.html
@@ -14,11 +14,26 @@
.flexInnerHoriz {
display: flex;
- height: 100%; /* If you delete this line, then pink area is stretched
- to have its height match blue area. */
+ /* This percent should not be resolvable, because our parent's
+ * height is indefinite (because our parent is a flex item with an
+ * indefinite flex basis, in an indefinite-main-sized flex container).
+ * So we just end up with our content height.
+ */
+ height: 100%;
background: pink;
}
-
+ .height50pct {
+ /* This percent should not be resolvable, for the same reason as above.
+ */
+ height: 50%;
+ background: brown;
+ }
+ .height0pct {
+ /* This percent should not be resolvable, for the same reason as above.
+ */
+ height: 0%;
+ background: yellow;
+ }
.spacer {
background: lightblue;
height: 200px;
@@ -30,6 +45,8 @@
<div class="flexVert">
<div class="flexIntermediateHoriz">
<div class="flexInnerHoriz">text</div>
+ <div class="height50pct">fifty</div>
+ <div class="height0pct">zero</div>
<div class="spacer"></div>
</div>
</div>
diff --git a/toolkit/themes/shared/in-content/info-pages.inc.css b/toolkit/themes/shared/in-content/info-pages.inc.css
index 4889602a09..29fcbe1ea8 100644
--- a/toolkit/themes/shared/in-content/info-pages.inc.css
+++ b/toolkit/themes/shared/in-content/info-pages.inc.css
@@ -96,7 +96,7 @@ ul {
/* Trees */
.tree-container {
margin-top: 1.2em;
- flex-grow: 1;
+ flex: 1 0px;
min-height: 12em;
}