WebKit Bugzilla
Attachment 356341 Details for
Bug 192289
: [LFC][BFC][MarginCollapsing] Check for clearance for top and bottom margins
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
Patch
Patch.txt (text/plain), 35.10 KB, created by
zalan
on 2018-12-02 09:48:29 PST
(
hide
)
Description:
Patch
Filename:
MIME Type:
Creator:
zalan
Created:
2018-12-02 09:48:29 PST
Size:
35.10 KB
patch
obsolete
>diff --git a/Source/JavaScriptCore/ChangeLog b/Source/JavaScriptCore/ChangeLog >index ee484a9dfea..053c3f812a3 100644 >--- a/Source/JavaScriptCore/ChangeLog >+++ b/Source/JavaScriptCore/ChangeLog >@@ -1,3 +1,12 @@ >+2018-12-01 Zalan Bujtas <zalan@apple.com> >+ >+ Add a runtime feature flag for LayoutFormattingContext. >+ https://bugs.webkit.org/show_bug.cgi?id=192280 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * Configurations/FeatureDefines.xcconfig: >+ > 2018-12-01 Simon Fraser <simon.fraser@apple.com> > > Heap.h refers to the non-existent HeapStatistics >diff --git a/Source/JavaScriptCore/Configurations/FeatureDefines.xcconfig b/Source/JavaScriptCore/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Source/JavaScriptCore/Configurations/FeatureDefines.xcconfig >+++ b/Source/JavaScriptCore/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; > >diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog >index dcf602f7fb2..c6b3fe771a7 100644 >--- a/Source/WebCore/ChangeLog >+++ b/Source/WebCore/ChangeLog >@@ -1,3 +1,17 @@ >+2018-12-01 Zalan Bujtas <zalan@apple.com> >+ >+ Add a runtime feature flag for LayoutFormattingContext. >+ https://bugs.webkit.org/show_bug.cgi?id=192280 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * Configurations/FeatureDefines.xcconfig: >+ * page/FrameViewLayoutContext.cpp: >+ (WebCore::layoutUsingFormattingContext): >+ * page/RuntimeEnabledFeatures.h: >+ (WebCore::RuntimeEnabledFeatures::setLayoutFormattingContextEnabled): >+ (WebCore::RuntimeEnabledFeatures::layoutFormattingContextEnabled const): >+ > 2018-12-01 Brent Fulgham <bfulgham@apple.com> > > Lifetime of HTMLMediaElement is not properly handled in asynchronous actions >diff --git a/Source/WebCore/Configurations/FeatureDefines.xcconfig b/Source/WebCore/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Source/WebCore/Configurations/FeatureDefines.xcconfig >+++ b/Source/WebCore/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; > >diff --git a/Source/WebCore/PAL/ChangeLog b/Source/WebCore/PAL/ChangeLog >index 463be2fd8a0..a3fb049f869 100644 >--- a/Source/WebCore/PAL/ChangeLog >+++ b/Source/WebCore/PAL/ChangeLog >@@ -1,3 +1,12 @@ >+2018-12-01 Zalan Bujtas <zalan@apple.com> >+ >+ Add a runtime feature flag for LayoutFormattingContext. >+ https://bugs.webkit.org/show_bug.cgi?id=192280 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * Configurations/FeatureDefines.xcconfig: >+ > 2018-12-01 Alexey Proskuryakov <ap@apple.com> > > Modernize version check for _suppressedAutoAddedHTTPHeaders >diff --git a/Source/WebCore/PAL/Configurations/FeatureDefines.xcconfig b/Source/WebCore/PAL/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Source/WebCore/PAL/Configurations/FeatureDefines.xcconfig >+++ b/Source/WebCore/PAL/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; > >diff --git a/Source/WebCore/layout/LayoutUnits.h b/Source/WebCore/layout/LayoutUnits.h >index cfe83f52c67..b1c3d521d45 100644 >--- a/Source/WebCore/layout/LayoutUnits.h >+++ b/Source/WebCore/layout/LayoutUnits.h >@@ -30,6 +30,7 @@ > #include "LayoutUnit.h" > #include "LayoutPoint.h" > #include "LayoutRect.h" >+#include <wtf/Optional.h> > > namespace WebCore { > namespace Layout { >diff --git a/Source/WebCore/layout/Verification.cpp b/Source/WebCore/layout/Verification.cpp >index 79de1783d60..b433c4dd1c0 100644 >--- a/Source/WebCore/layout/Verification.cpp >+++ b/Source/WebCore/layout/Verification.cpp >@@ -46,7 +46,7 @@ static bool areEssentiallyEqual(float a, LayoutUnit b) > if (a == b.toFloat()) > return true; > >- return ::abs(a - b.toFloat()) <= 4 * LayoutUnit::epsilon(); >+ return fabs(a - b.toFloat()) <= 4 * LayoutUnit::epsilon(); > } > > static bool outputMismatchingSimpleLineInformationIfNeeded(TextStream& stream, const LayoutState& layoutState, const RenderBlockFlow& blockFlow, const Container& inlineFormattingRoot) >diff --git a/Source/WebCore/layout/blockformatting/BlockFormattingContext.h b/Source/WebCore/layout/blockformatting/BlockFormattingContext.h >index e677e0174f0..66e5b89f381 100644 >--- a/Source/WebCore/layout/blockformatting/BlockFormattingContext.h >+++ b/Source/WebCore/layout/blockformatting/BlockFormattingContext.h >@@ -89,8 +89,8 @@ private: > static LayoutUnit marginTop(const LayoutState&, const Box&); > static LayoutUnit marginBottom(const LayoutState&, const Box&); > >- static bool isMarginBottomCollapsedWithParent(const Box&); >- static bool isMarginTopCollapsedWithParentMarginBottom(const Box&); >+ static bool isMarginBottomCollapsesWithParent(const Box&); >+ static bool isMarginTopCollapsesWithParentMarginBottom(const Box&); > > private: > static LayoutUnit collapsedMarginBottomFromLastChild(const LayoutState&, const Box&); >@@ -102,7 +102,7 @@ private: > static LayoutUnit collapsedMarginTopFromFirstChild(const LayoutState&, const Box&); > static LayoutUnit nonCollapsedMarginTop(const LayoutState&, const Box&); > >- static bool isMarginTopCollapsedWithParent(const LayoutState&, const Box&); >+ static bool isMarginTopCollapsesWithParent(const LayoutState&, const Box&); > }; > > static HeightAndMargin inFlowNonReplacedHeightAndMargin(const LayoutState&, const Box&, std::optional<LayoutUnit> usedHeight = { }); >diff --git a/Source/WebCore/layout/blockformatting/BlockFormattingContextGeometry.cpp b/Source/WebCore/layout/blockformatting/BlockFormattingContextGeometry.cpp >index 819f0303e09..6c5812ab0b2 100644 >--- a/Source/WebCore/layout/blockformatting/BlockFormattingContextGeometry.cpp >+++ b/Source/WebCore/layout/blockformatting/BlockFormattingContextGeometry.cpp >@@ -84,14 +84,14 @@ HeightAndMargin BlockFormattingContext::Geometry::inFlowNonReplacedHeightAndMarg > // 2. the bottom edge of the bottom (possibly collapsed) margin of its last in-flow child, if the child's bottom margin... > auto* lastInFlowChild = downcast<Container>(layoutBox).lastInFlowChild(); > ASSERT(lastInFlowChild); >- if (!MarginCollapse::isMarginBottomCollapsedWithParent(*lastInFlowChild)) { >+ if (!MarginCollapse::isMarginBottomCollapsesWithParent(*lastInFlowChild)) { > auto& lastInFlowDisplayBox = layoutState.displayBoxForLayoutBox(*lastInFlowChild); > return { lastInFlowDisplayBox.bottom() + lastInFlowDisplayBox.marginBottom() - borderAndPaddingTop, nonCollapsedMargin, collapsedMargin }; > } > > // 3. the bottom border edge of the last in-flow child whose top margin doesn't collapse with the element's bottom margin > auto* inFlowChild = lastInFlowChild; >- while (inFlowChild && MarginCollapse::isMarginTopCollapsedWithParentMarginBottom(*inFlowChild)) >+ while (inFlowChild && MarginCollapse::isMarginTopCollapsesWithParentMarginBottom(*inFlowChild)) > inFlowChild = inFlowChild->previousInFlowSibling(); > if (inFlowChild) { > auto& inFlowDisplayBox = layoutState.displayBoxForLayoutBox(*inFlowChild); >diff --git a/Source/WebCore/layout/blockformatting/BlockMarginCollapse.cpp b/Source/WebCore/layout/blockformatting/BlockMarginCollapse.cpp >index eb793b3cd4f..6695c2e1942 100644 >--- a/Source/WebCore/layout/blockformatting/BlockMarginCollapse.cpp >+++ b/Source/WebCore/layout/blockformatting/BlockMarginCollapse.cpp >@@ -69,6 +69,21 @@ static bool hasPaddingAfter(const Box& layoutBox) > return hasPadding(layoutBox.style().paddingAfter()); > } > >+static bool hasClearance(const Box&) >+{ >+ // FIXME >+ return false; >+} >+ >+static bool establishesBlockFormattingContext(const Box& layoutBox) >+{ >+ // WebKit treats the document element renderer as a block formatting context root. It probably only impacts margin collapsing, so let's not do >+ // a layout wide quirk on this for now. >+ if (layoutBox.isDocumentBox()) >+ return true; >+ return layoutBox.establishesBlockFormattingContext(); >+} >+ > static LayoutUnit marginValue(LayoutUnit currentMarginValue, LayoutUnit candidateMarginValue) > { > if (!candidateMarginValue) >@@ -85,75 +100,7 @@ static LayoutUnit marginValue(LayoutUnit currentMarginValue, LayoutUnit candidat > return currentMarginValue + candidateMarginValue; > } > >-static bool isMarginTopCollapsedWithSibling(const Box& layoutBox) >-{ >- ASSERT(layoutBox.isBlockLevelBox()); >- >- if (layoutBox.isFloatingPositioned()) >- return false; >- >- if (!layoutBox.isPositioned() || layoutBox.isInFlowPositioned()) >- return true; >- >- // Out of flow positioned. >- ASSERT(layoutBox.isOutOfFlowPositioned()); >- return layoutBox.style().top().isAuto(); >-} >- >-static bool isMarginBottomCollapsedWithSibling(const Box& layoutBox) >-{ >- ASSERT(layoutBox.isBlockLevelBox()); >- >- if (layoutBox.isFloatingPositioned()) >- return false; >- >- if (!layoutBox.isPositioned() || layoutBox.isInFlowPositioned()) >- return true; >- >- // Out of flow positioned. >- ASSERT(layoutBox.isOutOfFlowPositioned()); >- return layoutBox.style().bottom().isAuto(); >-} >- >-bool BlockFormattingContext::Geometry::MarginCollapse::isMarginTopCollapsedWithParent(const LayoutState& layoutState, const Box& layoutBox) >-{ >- // The first inflow child could propagate its top margin to parent. >- // https://www.w3.org/TR/CSS21/box.html#collapsing-margins >- if (layoutBox.isAnonymous()) >- return false; >- >- ASSERT(layoutBox.isBlockLevelBox()); >- >- if (layoutBox.isFloatingOrOutOfFlowPositioned()) >- return false; >- >- // Only the first inlflow child collapses with parent. >- if (layoutBox.previousInFlowSibling()) >- return false; >- >- // We never margin collapse the initial containing block. >- ASSERT(layoutBox.parent()); >- auto& parent = *layoutBox.parent(); >- if (parent.establishesBlockFormattingContext()) >- return false; >- >- // Margins of the root element's box do not collapse. >- if (parent.isDocumentBox() || parent.isInitialContainingBlock()) >- return false; >- >- if (hasBorderBefore(parent)) >- return false; >- >- if (hasPaddingBefore(parent)) >- return false; >- >- if (BlockFormattingContext::Quirks::shouldIgnoreMarginTop(layoutState, layoutBox)) >- return false; >- >- return true; >-} >- >-static bool isMarginBottomCollapsedThrough(const Box& layoutBox) >+static bool hasAdjoiningMarginTopAndBottom(const Box& layoutBox) > { > ASSERT(layoutBox.isBlockLevelBox()); > >@@ -191,7 +138,7 @@ LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::collapsedMarginTopF > > // FIXME: Take collapsed through margin into account. > auto& firstInFlowChild = *downcast<Container>(layoutBox).firstInFlowChild(); >- if (!isMarginTopCollapsedWithParent(layoutState, firstInFlowChild)) >+ if (!isMarginTopCollapsesWithParent(layoutState, firstInFlowChild)) > return 0; > // Collect collapsed margin top recursively. > return marginValue(computedNonCollapsedMarginTop(layoutState, firstInFlowChild), collapsedMarginTopFromFirstChild(layoutState, firstInFlowChild)); >@@ -205,20 +152,6 @@ LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::nonCollapsedMarginT > return marginValue(computedNonCollapsedMarginTop(layoutState, layoutBox), collapsedMarginTopFromFirstChild(layoutState, layoutBox)); > } > >-/*static bool hasAdjoiningMarginTopAndBottom(const Box&) >-{ >- // Two margins are adjoining if and only if: >- // 1. both belong to in-flow block-level boxes that participate in the same block formatting context >- // 2. no line boxes, no clearance, no padding and no border separate them (Note that certain zero-height line boxes (see 9.4.2) are ignored for this purpose.) >- // 3. both belong to vertically-adjacent box edges, i.e. form one of the following pairs: >- // top margin of a box and top margin of its first in-flow child >- // bottom margin of box and top margin of its next in-flow following sibling >- // bottom margin of a last in-flow child and bottom margin of its parent if the parent has 'auto' computed height >- // top and bottom margins of a box that does not establish a new block formatting context and that has zero computed 'min-height', >- // zero or 'auto' computed 'height', and no in-flow children >- // A collapsed margin is considered adjoining to another margin if any of its component margins is adjoining to that margin. >- return false; >-}*/ > LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::computedNonCollapsedMarginTop(const LayoutState& layoutState, const Box& layoutBox) > { > ASSERT(layoutBox.isBlockLevelBox()); >@@ -233,139 +166,232 @@ LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::computedNonCollapse > return computedNonCollapsedVerticalMarginValue(layoutState, layoutBox).bottom; > } > >-LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::marginTop(const LayoutState& layoutState, const Box& layoutBox) >+bool BlockFormattingContext::Geometry::MarginCollapse::isMarginTopCollapsesWithParentMarginBottom(const Box&) > { >- if (layoutBox.isAnonymous()) >- return 0; >+ return false; >+} > >+LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::collapsedMarginBottomFromLastChild(const LayoutState& layoutState, const Box& layoutBox) >+{ > ASSERT(layoutBox.isBlockLevelBox()); > >- // TODO: take _hasAdjoiningMarginTopAndBottom() into account. >- if (isMarginTopCollapsedWithParent(layoutState, layoutBox)) >+ // Check if the last child propagates its margin bottom. >+ if (!is<Container>(layoutBox) || !downcast<Container>(layoutBox).hasInFlowChild()) > return 0; > >- // FIXME: Find out the logic behind this. >- if (BlockFormattingContext::Quirks::shouldIgnoreMarginTop(layoutState, layoutBox)) >+ // Do not collapse margin with a box from a non-block formatting context <div><span>foobar</span></div>. >+ if (layoutBox.establishesFormattingContext() && !layoutBox.establishesBlockFormattingContextOnly()) >+ return 0; >+ >+ // FIXME: Check for collapsed through margin. >+ auto& lastInFlowChild = *downcast<Container>(layoutBox).lastInFlowChild(); >+ if (!isMarginBottomCollapsesWithParent(lastInFlowChild)) > return 0; > >- if (!isMarginTopCollapsedWithSibling(layoutBox)) { >- if (!isMarginBottomCollapsedThrough(layoutBox)) >- return nonCollapsedMarginTop(layoutState, layoutBox); >- // Compute the collapsed through value. >- auto marginTop = nonCollapsedMarginTop(layoutState, layoutBox); >- auto marginBottom = nonCollapsedMarginBottom(layoutState, layoutBox); >- return marginValue(marginTop, marginBottom); >- } >+ // Collect collapsed margin bottom recursively. >+ return marginValue(computedNonCollapsedMarginBottom(layoutState, lastInFlowChild), collapsedMarginBottomFromLastChild(layoutState, lastInFlowChild)); >+} > >- // The bottom margin of an in-flow block-level element always collapses with the top margin of its next in-flow block-level sibling, >- // unless that sibling has clearance. >- auto* previousInFlowSibling = layoutBox.previousInFlowSibling(); >- if (!previousInFlowSibling) >- return nonCollapsedMarginTop(layoutState, layoutBox); >+LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::nonCollapsedMarginBottom(const LayoutState& layoutState, const Box& layoutBox) >+{ >+ ASSERT(layoutBox.isBlockLevelBox()); > >- auto previousSiblingMarginBottom = nonCollapsedMarginBottom(layoutState, *previousInFlowSibling); >- auto marginTop = nonCollapsedMarginTop(layoutState, layoutBox); >- return marginValue(marginTop, previousSiblingMarginBottom); >+ // Non collapsed margin bottom includes collapsed margin from inflow last child. >+ return marginValue(computedNonCollapsedMarginBottom(layoutState, layoutBox), collapsedMarginBottomFromLastChild(layoutState, layoutBox)); > } > >-LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::marginBottom(const LayoutState& layoutState, const Box& layoutBox) >+bool BlockFormattingContext::Geometry::MarginCollapse::isMarginBottomCollapsesWithParent(const Box& layoutBox) > { >+ // last inflow box to parent. >+ // https://www.w3.org/TR/CSS21/box.html#collapsing-margins > if (layoutBox.isAnonymous()) >- return 0; >+ return false; > > ASSERT(layoutBox.isBlockLevelBox()); > >- // TODO: take _hasAdjoiningMarginTopAndBottom() into account. >- if (isMarginBottomCollapsedWithParent(layoutBox)) >- return 0; >+ // Margins between a floated box and any other box do not collapse (not even between a float and its in-flow children). >+ if (layoutBox.isFloatingPositioned()) >+ return false; > >- if (isMarginBottomCollapsedThrough(layoutBox)) >- return 0; >+ // Margins of absolutely positioned boxes do not collapse (not even with their in-flow children). -Unless bottom is statically positioned >+ if (layoutBox.isOutOfFlowPositioned() && !layoutBox.style().bottom().isAuto()) >+ return false; > >- // Floats and out of flow positioned boxes do not collapse their margins. >- if (!isMarginBottomCollapsedWithSibling(layoutBox)) >- return nonCollapsedMarginBottom(layoutState, layoutBox); >+ // Margins of inline-block boxes do not collapse (not even with their in-flow children). >+ if (layoutBox.isInlineBlockBox()) >+ return false; > >- // The bottom margin of an in-flow block-level element always collapses with the top margin of its next in-flow block-level sibling, >- // unless that sibling has clearance. >+ // Only the last inlflow child collapses with parent. > if (layoutBox.nextInFlowSibling()) >- return 0; >- return nonCollapsedMarginBottom(layoutState, layoutBox); >+ return false; >+ >+ if (hasClearance(layoutBox)) >+ return false; >+ >+ // the child's bottom margin neither collapses with a top margin that has clearance, nor (if the box's min-height is non-zero) with the box's top margin. >+ if (hasAdjoiningMarginTopAndBottom(layoutBox)) >+ return false; >+ >+ auto& parent = *layoutBox.parent(); >+ if (hasBorderAfter(parent)) >+ return false; >+ >+ if (hasPaddingAfter(parent)) >+ return false; >+ >+ // Margins of elements that establish new block formatting contexts (such as floats and elements with 'overflow' other than 'visible') >+ // do not collapse with their in-flow children. >+ if (establishesBlockFormattingContext(parent)) >+ return false; >+ >+ if (!parent.style().height().isAuto()) >+ return false; >+ >+ return true; > } > >-bool BlockFormattingContext::Geometry::MarginCollapse::isMarginBottomCollapsedWithParent(const Box& layoutBox) >+bool BlockFormattingContext::Geometry::MarginCollapse::isMarginTopCollapsesWithParent(const LayoutState& layoutState, const Box& layoutBox) > { >- // last inflow box to parent. >+ // The first inflow child could propagate its top margin to parent. > // https://www.w3.org/TR/CSS21/box.html#collapsing-margins > if (layoutBox.isAnonymous()) > return false; > > ASSERT(layoutBox.isBlockLevelBox()); >- >- if (layoutBox.isFloatingOrOutOfFlowPositioned()) >+ // Margins between a floated box and any other box do not collapse (not even between a float and its in-flow children). >+ if (layoutBox.isFloatingPositioned()) > return false; > >- if (isMarginBottomCollapsedThrough(layoutBox)) >+ // Margins of absolutely positioned boxes do not collapse (not even with their in-flow children). -Unless top is statically positioned >+ if (layoutBox.isOutOfFlowPositioned() && !layoutBox.style().top().isAuto()) > return false; > >- // We never margin collapse the initial containing block. >- ASSERT(layoutBox.parent()); >- auto& parent = *layoutBox.parent(); >- // Only the last inlflow child collapses with parent. >- if (layoutBox.nextInFlowSibling()) >+ // Margins of inline-block boxes do not collapse (not even with their in-flow children). >+ if (layoutBox.isInlineBlockBox()) > return false; > >- if (parent.establishesBlockFormattingContext()) >+ // The top margin of an in-flow block element collapses with its first in-flow block-level child's top margin >+ // if the element has no top border, no top padding, and the child has no clearance. >+ if (layoutBox.previousInFlowSibling()) > return false; > >- // Margins of the root element's box do not collapse. >- if (parent.isDocumentBox() || parent.isInitialContainingBlock()) >+ if (hasClearance(layoutBox)) > return false; > >+ auto& parent = *layoutBox.parent(); > if (hasBorderBefore(parent)) > return false; > > if (hasPaddingBefore(parent)) > return false; > >- if (!parent.style().height().isAuto()) >+ // Margins of elements that establish new block formatting contexts (such as floats and elements with 'overflow' other than 'visible') >+ // do not collapse with their in-flow children. >+ if (establishesBlockFormattingContext(parent)) >+ return false; >+ >+ if (BlockFormattingContext::Quirks::shouldIgnoreMarginTop(layoutState, layoutBox)) > return false; > > return true; > } > >-bool BlockFormattingContext::Geometry::MarginCollapse::isMarginTopCollapsedWithParentMarginBottom(const Box&) >+static bool isMarginBottomCollapsesWithSibling(const Box& layoutBox) > { >- return false; >+ ASSERT(layoutBox.isBlockLevelBox()); >+ >+ // Margins between a floated box and any other box do not collapse (not even between a float and its in-flow children). >+ if (layoutBox.isFloatingPositioned()) >+ return false; >+ >+ // Margins of inline-block boxes do not collapse (not even with their in-flow children). >+ if (layoutBox.isInlineBlockBox()) >+ return false; >+ >+ // Margins of absolutely positioned boxes do not collapse (not even with their in-flow children) - Unless bottom is statically positioned. >+ if (layoutBox.isOutOfFlowPositioned() && !layoutBox.style().bottom().isAuto()) >+ return false; >+ >+ // The bottom margin of an in-flow block-level element always collapses with the top margin of its next in-flow block-level sibling, >+ // unless that sibling has clearance. >+ auto* nextInFlowSibling = layoutBox.nextInFlowSibling(); >+ if (!nextInFlowSibling) >+ return false; >+ >+ if (hasClearance(*nextInFlowSibling)) >+ return false; >+ >+ return true; > } > >-LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::collapsedMarginBottomFromLastChild(const LayoutState& layoutState, const Box& layoutBox) >+static bool isMarginTopCollapsesWithSibling(const Box& layoutBox) > { > ASSERT(layoutBox.isBlockLevelBox()); >+ // Margins between a floated box and any other box do not collapse (not even between a float and its in-flow children). >+ if (layoutBox.isFloatingPositioned()) >+ return false; > >- // Check if the last child propagates its margin bottom. >- if (!is<Container>(layoutBox) || !downcast<Container>(layoutBox).hasInFlowChild()) >+ // Margins of inline-block boxes do not collapse (not even with their in-flow children). >+ if (layoutBox.isInlineBlockBox()) >+ return false; >+ >+ // Margins of absolutely positioned boxes do not collapse (not even with their in-flow children) - Unless top is statically positioned. >+ if (layoutBox.isOutOfFlowPositioned() && !layoutBox.style().top().isAuto()) >+ return false; >+ >+ // The bottom margin of an in-flow block-level element always collapses with the top margin of its next in-flow block-level sibling, >+ // unless that sibling has clearance. >+ auto* previousInFlowSibling = layoutBox.previousInFlowSibling(); >+ if (!previousInFlowSibling) >+ return false; >+ >+ if (hasClearance(*previousInFlowSibling)) >+ return false; >+ >+ return true; >+} >+ >+LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::marginTop(const LayoutState& layoutState, const Box& layoutBox) >+{ >+ if (layoutBox.isAnonymous()) > return 0; > >- // Do not collapse margin with a box from a non-block formatting context <div><span>foobar</span></div>. >- if (layoutBox.establishesFormattingContext() && !layoutBox.establishesBlockFormattingContextOnly()) >+ ASSERT(layoutBox.isBlockLevelBox()); >+ >+ if (isMarginTopCollapsesWithParent(layoutState, layoutBox)) > return 0; > >- // FIXME: Check for collapsed through margin. >- auto& lastInFlowChild = *downcast<Container>(layoutBox).lastInFlowChild(); >- if (!isMarginBottomCollapsedWithParent(lastInFlowChild)) >+ // FIXME: Find out the logic behind this. >+ if (BlockFormattingContext::Quirks::shouldIgnoreMarginTop(layoutState, layoutBox)) > return 0; > >- // Collect collapsed margin bottom recursively. >- return marginValue(computedNonCollapsedMarginBottom(layoutState, lastInFlowChild), collapsedMarginBottomFromLastChild(layoutState, lastInFlowChild)); >+ auto nonCollapsedMarginTop = MarginCollapse::nonCollapsedMarginTop(layoutState, layoutBox); >+ if (isMarginTopCollapsesWithSibling(layoutBox)) >+ return marginValue(nonCollapsedMarginTop, nonCollapsedMarginBottom(layoutState, *layoutBox.previousInFlowSibling())); >+ >+ if (hasAdjoiningMarginTopAndBottom(layoutBox)) >+ return marginValue(nonCollapsedMarginTop, nonCollapsedMarginBottom(layoutState, layoutBox)); >+ >+ return nonCollapsedMarginTop; > } > >-LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::nonCollapsedMarginBottom(const LayoutState& layoutState, const Box& layoutBox) >+LayoutUnit BlockFormattingContext::Geometry::MarginCollapse::marginBottom(const LayoutState& layoutState, const Box& layoutBox) > { >+ if (layoutBox.isAnonymous()) >+ return 0; >+ > ASSERT(layoutBox.isBlockLevelBox()); > >- // Non collapsed margin bottom includes collapsed margin from inflow last child. >- return marginValue(computedNonCollapsedMarginBottom(layoutState, layoutBox), collapsedMarginBottomFromLastChild(layoutState, layoutBox)); >+ if (isMarginBottomCollapsesWithParent(layoutBox)) >+ return 0; >+ >+ if (isMarginBottomCollapsesWithSibling(layoutBox)) >+ return 0; >+ >+ if (hasAdjoiningMarginTopAndBottom(layoutBox)) >+ return 0; >+ >+ return nonCollapsedMarginBottom(layoutState, layoutBox); > } > > } >diff --git a/Source/WebCore/layout/inlineformatting/InlineFormattingContextGeometry.cpp b/Source/WebCore/layout/inlineformatting/InlineFormattingContextGeometry.cpp >index 35f77c0cc60..453b2167df3 100644 >--- a/Source/WebCore/layout/inlineformatting/InlineFormattingContextGeometry.cpp >+++ b/Source/WebCore/layout/inlineformatting/InlineFormattingContextGeometry.cpp >@@ -181,7 +181,9 @@ LayoutUnit InlineFormattingContext::Geometry::runWidth(const InlineContent& inli > LayoutUnit width; > auto startPosition = from; > auto iterator = inlineContent.find(const_cast<InlineItem*>(&inlineItem)); >+#if !ASSERT_DISABLED > auto inlineItemEnd = inlineContent.end(); >+#endif > while (length) { > ASSERT(iterator != inlineItemEnd); > auto& currentInlineItem = **iterator; >diff --git a/Source/WebCore/layout/inlineformatting/InlineLineBreaker.cpp b/Source/WebCore/layout/inlineformatting/InlineLineBreaker.cpp >index 688234e38a9..4096e42d727 100644 >--- a/Source/WebCore/layout/inlineformatting/InlineLineBreaker.cpp >+++ b/Source/WebCore/layout/inlineformatting/InlineLineBreaker.cpp >@@ -162,7 +162,9 @@ LayoutUnit InlineLineBreaker::textWidth(const InlineRunProvider::Run& inlineRun, > // FIXME: It does not do proper kerning/ligature handling. > LayoutUnit width; > auto iterator = m_inlineContent.find(const_cast<InlineItem*>(&inlineItem)); >+#if !ASSERT_DISABLED > auto inlineItemEnd = m_inlineContent.end(); >+#endif > while (length) { > ASSERT(iterator != inlineItemEnd); > auto& currentInlineItem = **iterator; >diff --git a/Source/WebCore/page/FrameViewLayoutContext.cpp b/Source/WebCore/page/FrameViewLayoutContext.cpp >index 7a9957a17f8..8e946390833 100644 >--- a/Source/WebCore/page/FrameViewLayoutContext.cpp >+++ b/Source/WebCore/page/FrameViewLayoutContext.cpp >@@ -36,6 +36,7 @@ > #include "Logging.h" > #include "RenderElement.h" > #include "RenderView.h" >+#include "RuntimeEnabledFeatures.h" > #include "ScriptDisallowedScope.h" > #include "Settings.h" > >@@ -55,6 +56,8 @@ namespace WebCore { > #if ENABLE(LAYOUT_FORMATTING_CONTEXT) > static void layoutUsingFormattingContext(const RenderView& renderView) > { >+ if (!RuntimeEnabledFeatures::sharedFeatures().layoutFormattingContextEnabled()) >+ return; > auto initialContainingBlock = Layout::TreeBuilder::createLayoutTree(renderView); > auto layoutState = std::make_unique<Layout::LayoutState>(*initialContainingBlock, renderView.size()); > layoutState->setInQuirksMode(renderView.document().inQuirksMode()); >diff --git a/Source/WebCore/page/RuntimeEnabledFeatures.h b/Source/WebCore/page/RuntimeEnabledFeatures.h >index ac795057f54..d28a8f7648b 100644 >--- a/Source/WebCore/page/RuntimeEnabledFeatures.h >+++ b/Source/WebCore/page/RuntimeEnabledFeatures.h >@@ -178,6 +178,11 @@ public: > void setPointerEventsEnabled(bool isEnabled) { m_pointerEventsEnabled = isEnabled; } > bool pointerEventsEnabled() const { return m_pointerEventsEnabled; } > >+#if ENABLE(LAYOUT_FORMATTING_CONTEXT) >+ void setLayoutFormattingContextEnabled(bool isEnabled) { m_layoutFormattingContextEnabled = isEnabled; } >+ bool layoutFormattingContextEnabled() const { return m_layoutFormattingContextEnabled; } >+#endif >+ > #if ENABLE(CSS_PAINTING_API) > void setCSSPaintingAPIEnabled(bool isEnabled) { m_CSSPaintingAPIEnabled = isEnabled; } > bool cssPaintingAPIEnabled() const { return m_CSSPaintingAPIEnabled; } >@@ -372,6 +377,10 @@ private: > bool m_pointerEventsEnabled { false }; > bool m_webSQLEnabled { true }; > >+#if ENABLE(LAYOUT_FORMATTING_CONTEXT) >+ bool m_layoutFormattingContextEnabled { false }; >+#endif >+ > #if ENABLE(CSS_PAINTING_API) > bool m_CSSPaintingAPIEnabled { false }; > #endif >diff --git a/Source/WebKit/ChangeLog b/Source/WebKit/ChangeLog >index 9783723a257..ee91ea62e6c 100644 >--- a/Source/WebKit/ChangeLog >+++ b/Source/WebKit/ChangeLog >@@ -1,3 +1,15 @@ >+2018-12-01 Zalan Bujtas <zalan@apple.com> >+ >+ Add a runtime feature flag for LayoutFormattingContext. >+ https://bugs.webkit.org/show_bug.cgi?id=192280 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * Configurations/FeatureDefines.xcconfig: >+ * Shared/WebPreferences.yaml: >+ * WebProcess/InjectedBundle/InjectedBundle.cpp: >+ (WebKit::InjectedBundle::overrideBoolPreferenceForTestRunner): >+ > 2018-12-01 Chris Dumez <cdumez@apple.com> > > [PSON] process-swapping may occur even though opener has handle to openee >diff --git a/Source/WebKit/Configurations/FeatureDefines.xcconfig b/Source/WebKit/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Source/WebKit/Configurations/FeatureDefines.xcconfig >+++ b/Source/WebKit/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; > >diff --git a/Source/WebKit/Shared/WebPreferences.yaml b/Source/WebKit/Shared/WebPreferences.yaml >index 6e6836b0a43..a37ba990513 100644 >--- a/Source/WebKit/Shared/WebPreferences.yaml >+++ b/Source/WebKit/Shared/WebPreferences.yaml >@@ -1326,6 +1326,15 @@ DarkModeCSSEnabled: > category: experimental > condition: ENABLE(DARK_MODE_CSS) > >+LayoutFormattingContextEnabled: >+ type: bool >+ defaultValue: false >+ humanReadableName: "Next-gen layout" >+ humanReadableDescription: "Enable next-gen layout" >+ webcoreBinding: RuntimeEnabledFeatures >+ category: experimental >+ condition: ENABLE(LAYOUT_FORMATTING_CONTEXT) >+ > CSSPaintingAPIEnabled: > type: bool > defaultValue: false >diff --git a/Source/WebKit/WebProcess/InjectedBundle/InjectedBundle.cpp b/Source/WebKit/WebProcess/InjectedBundle/InjectedBundle.cpp >index a0a2fc8b492..88054071b6a 100644 >--- a/Source/WebKit/WebProcess/InjectedBundle/InjectedBundle.cpp >+++ b/Source/WebKit/WebProcess/InjectedBundle/InjectedBundle.cpp >@@ -256,6 +256,11 @@ void InjectedBundle::overrideBoolPreferenceForTestRunner(WebPageGroupProxy* page > if (preference == "CSSCustomPropertiesAndValuesEnabled") > RuntimeEnabledFeatures::sharedFeatures().setCSSCustomPropertiesAndValuesEnabled(enabled); > >+#if ENABLE(LAYOUT_FORMATTING_CONTEXT) >+ if (preference == "LayoutFormattingContextEnabled") >+ RuntimeEnabledFeatures::sharedFeatures().setLayoutFormattingContextEnabled(enabled); >+#endif >+ > #if ENABLE(CSS_PAINTING_API) > if (preference == "CSSPaintingAPIEnabled") > RuntimeEnabledFeatures::sharedFeatures().setCSSPaintingAPIEnabled(enabled); >diff --git a/Source/WebKitLegacy/mac/ChangeLog b/Source/WebKitLegacy/mac/ChangeLog >index 281551fdcd9..d5be801ddee 100644 >--- a/Source/WebKitLegacy/mac/ChangeLog >+++ b/Source/WebKitLegacy/mac/ChangeLog >@@ -1,3 +1,12 @@ >+2018-12-01 Zalan Bujtas <zalan@apple.com> >+ >+ Add a runtime feature flag for LayoutFormattingContext. >+ https://bugs.webkit.org/show_bug.cgi?id=192280 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * Configurations/FeatureDefines.xcconfig: >+ > 2018-11-30 Alex Christensen <achristensen@webkit.org> > > Move URL from WebCore to WTF >diff --git a/Source/WebKitLegacy/mac/Configurations/FeatureDefines.xcconfig b/Source/WebKitLegacy/mac/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Source/WebKitLegacy/mac/Configurations/FeatureDefines.xcconfig >+++ b/Source/WebKitLegacy/mac/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; > >diff --git a/Tools/TestWebKitAPI/Configurations/FeatureDefines.xcconfig b/Tools/TestWebKitAPI/Configurations/FeatureDefines.xcconfig >index de8c44c9e16..f4993e58fee 100644 >--- a/Tools/TestWebKitAPI/Configurations/FeatureDefines.xcconfig >+++ b/Tools/TestWebKitAPI/Configurations/FeatureDefines.xcconfig >@@ -228,7 +228,7 @@ ENABLE_KEYBOARD_CODE_ATTRIBUTE = ENABLE_KEYBOARD_CODE_ATTRIBUTE; > > ENABLE_KEYBOARD_KEY_ATTRIBUTE = ENABLE_KEYBOARD_KEY_ATTRIBUTE; > >-ENABLE_LAYOUT_FORMATTING_CONTEXT = ; >+ENABLE_LAYOUT_FORMATTING_CONTEXT = ENABLE_LAYOUT_FORMATTING_CONTEXT; > > ENABLE_LEGACY_CSS_VENDOR_PREFIXES = ENABLE_LEGACY_CSS_VENDOR_PREFIXES; >
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Raw
Actions:
View
Attachments on
bug 192289
:
356341
|
356343