Diff
Modified: trunk/LayoutTests/ChangeLog (201515 => 201516)
--- trunk/LayoutTests/ChangeLog 2016-05-31 17:53:20 UTC (rev 201515)
+++ trunk/LayoutTests/ChangeLog 2016-05-31 18:42:17 UTC (rev 201516)
@@ -1,3 +1,14 @@
+2016-05-31 Dave Hyatt <hy...@apple.com>
+
+ REGRESSION (r189567): Elements with aspect ratios not handled correctly inside flexbox.
+ https://bugs.webkit.org/show_bug.cgi?id=158040
+
+ Reviewed by Zalan Bujtas.
+
+ * fast/flexbox/aspect-ratio-intrinsic-adjust-expected.html: Added.
+ * fast/flexbox/aspect-ratio-intrinsic-adjust.html: Added.
+ * fast/flexbox/resources/subjects_sm.png: Added.
+
2016-05-25 Sergio Villar Senin <svil...@igalia.com>
[css-grid] Empty grid without explicit tracks shouldn't have any size
Added: trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust-expected.html (0 => 201516)
--- trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust-expected.html (rev 0)
+++ trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust-expected.html 2016-05-31 18:42:17 UTC (rev 201516)
@@ -0,0 +1,47 @@
+<!doctype html>
+<html lang="en">
+
+<head>
+ <meta charset="utf-8" />
+ <title>img.weird-stretch</title>
+ <style>
+ body {
+ width: 400px;
+ margin: 0 auto;
+ }
+ .weird-stretch-container {
+ float: right;
+ width: 400px;
+ height: 250px;
+ display: -webkit-flex;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -webkit-align-items: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -webkit-justify-content: center;
+ -ms-flex-pack: center;
+ justify-content: center
+ }
+
+ </style>
+</head>
+
+<body>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" width="100px" />
+ </div>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" width="63px" />
+ </div>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" width="132px" height="210px" />
+ </div>
+</body>
+
+</html>
Added: trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust.html (0 => 201516)
--- trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust.html (rev 0)
+++ trunk/LayoutTests/fast/flexbox/aspect-ratio-intrinsic-adjust.html 2016-05-31 18:42:17 UTC (rev 201516)
@@ -0,0 +1,51 @@
+<!doctype html>
+<html lang="en">
+
+<head>
+ <meta charset="utf-8" />
+ <title>img.weird-stretch</title>
+ <style>
+ body {
+ width: 400px;
+ margin: 0 auto;
+ }
+ .weird-stretch-container {
+ float: right;
+ width: 400px;
+ height: 250px;
+ display: -webkit-flex;
+ display: -ms-flexbox;
+ display: flex;
+ -webkit-box-align: center;
+ -webkit-align-items: center;
+ -ms-flex-align: center;
+ align-items: center;
+ -webkit-box-pack: center;
+ -webkit-justify-content: center;
+ -ms-flex-pack: center;
+ justify-content: center
+ }
+
+ img.weird-stretch {
+ max-width: 100%;
+ max-height: 100%
+ }
+ </style>
+</head>
+
+<body>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" width="100px" />
+ </div>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" height="100px" />
+ </div>
+
+ <div class="weird-stretch-container">
+ <img class="weird-stretch" alt="" src="" width="132px" height="210px" />
+ </div>
+</body>
+
+</html>
Added: trunk/LayoutTests/fast/flexbox/resources/subjects_sm.png
(Binary files differ)
Property changes on: trunk/LayoutTests/fast/flexbox/resources/subjects_sm.png
___________________________________________________________________
Added: svn:mime-type
Modified: trunk/Source/WebCore/ChangeLog (201515 => 201516)
--- trunk/Source/WebCore/ChangeLog 2016-05-31 17:53:20 UTC (rev 201515)
+++ trunk/Source/WebCore/ChangeLog 2016-05-31 18:42:17 UTC (rev 201516)
@@ -1,3 +1,33 @@
+2016-05-31 Dave Hyatt <hy...@apple.com>
+
+ REGRESSION (r189567): Elements with aspect ratios not handled correctly inside flexbox.
+ https://bugs.webkit.org/show_bug.cgi?id=158040
+
+ Reviewed by Zalan Bujtas.
+
+ Added new tests in fast/flexbox.
+
+ * rendering/RenderFlexibleBox.cpp:
+ (WebCore::RenderFlexibleBox::clientLogicalBottomAfterRepositioning):
+ (WebCore::RenderFlexibleBox::hasOrthogonalFlow):
+ (WebCore::RenderFlexibleBox::mainAxisContentExtent):
+ (WebCore::RenderFlexibleBox::computeMainAxisExtentForChild):
+ (WebCore::RenderFlexibleBox::mainAxisBorderAndPaddingExtentForChild):
+ (WebCore::RenderFlexibleBox::mainAxisLengthIsDefinite):
+ (WebCore::RenderFlexibleBox::mainAxisScrollbarExtentForChild):
+ (WebCore::RenderFlexibleBox::prepareOrderIteratorAndMargins):
+ (WebCore::RenderFlexibleBox::crossAxisLengthIsDefinite):
+ (WebCore::RenderFlexibleBox::computeMainSizeFromAspectRatioUsing):
+ (WebCore::RenderFlexibleBox::adjustChildSizeForAspectRatioCrossAxisMinAndMax):
+ (WebCore::RenderFlexibleBox::useChildAspectRatio):
+ (WebCore::RenderFlexibleBox::adjustChildSizeForMinAndMax):
+ (WebCore::RenderFlexibleBox::resetAutoMarginsAndLogicalTopInCrossAxis):
+ (WebCore::RenderFlexibleBox::mainAxisOverflowForChild):
+ (WebCore::RenderFlexibleBox::mainAxisExtentIsDefinite): Deleted.
+ (WebCore::RenderFlexibleBox::mainAxisLengthIsIndefinite): Deleted.
+ * rendering/RenderFlexibleBox.h:
+ (WebCore::RenderFlexibleBox::isFlexibleBoxImpl):
+
2016-05-31 Alex Christensen <achristen...@webkit.org>
Build fix after r201482.
Modified: trunk/Source/WebCore/rendering/RenderFlexibleBox.cpp (201515 => 201516)
--- trunk/Source/WebCore/rendering/RenderFlexibleBox.cpp 2016-05-31 17:53:20 UTC (rev 201515)
+++ trunk/Source/WebCore/rendering/RenderFlexibleBox.cpp 2016-05-31 18:42:17 UTC (rev 201516)
@@ -367,7 +367,7 @@
return std::max(clientLogicalBottom(), maxChildLogicalBottom);
}
-bool RenderFlexibleBox::hasOrthogonalFlow(RenderBox& child) const
+bool RenderFlexibleBox::hasOrthogonalFlow(const RenderBox& child) const
{
// FIXME: If the child is a flexbox, then we need to check isHorizontalFlow.
return isHorizontalFlow() != child.isHorizontalWritingMode();
@@ -454,14 +454,14 @@
return contentLogicalWidth();
}
-Optional<LayoutUnit> RenderFlexibleBox::computeMainAxisExtentForChild(RenderBox& child, SizeType sizeType, const Length& size)
+Optional<LayoutUnit> RenderFlexibleBox::computeMainAxisExtentForChild(const RenderBox& child, SizeType sizeType, const Length& size)
{
// FIXME: This is wrong for orthogonal flows. It should use the flexbox's writing-mode, not the child's in order
// to figure out the logical height/width.
if (isColumnFlow()) {
// We don't have to check for "auto" here - computeContentLogicalHeight will just return Nullopt for that case anyway.
if (size.isIntrinsic())
- child.layoutIfNeeded();
+ const_cast<RenderBox&>(child).layoutIfNeeded(); // FIXME: Should not need to do a layout here.
return child.computeContentLogicalHeight(sizeType, size, child.logicalHeight() - child.borderAndPaddingLogicalHeight());
}
// FIXME: Figure out how this should work for regions and pass in the appropriate values.
@@ -652,17 +652,16 @@
{
return isHorizontalFlow() ? child.horizontalBorderAndPaddingExtent() : child.verticalBorderAndPaddingExtent();
}
-
-bool RenderFlexibleBox::mainAxisExtentIsDefinite() const
+
+bool RenderFlexibleBox::mainAxisLengthIsDefinite(const RenderBox& child, const Length& flexBasis) const
{
- return isColumnFlow() ? hasDefiniteLogicalHeight() : hasDefiniteLogicalWidth();
+ if (flexBasis.isAuto())
+ return false;
+ if (flexBasis.isPercentOrCalculated())
+ return isColumnFlow() ? bool(child.computePercentageLogicalHeight(flexBasis)) : hasDefiniteLogicalWidth();
+ return true;
}
-bool RenderFlexibleBox::mainAxisLengthIsIndefinite(const Length& flexBasis) const
-{
- return flexBasis.isAuto() || (flexBasis.isPercentOrCalculated() && !mainAxisExtentIsDefinite());
-}
-
LayoutUnit RenderFlexibleBox::mainAxisScrollbarExtentForChild(RenderBox& child) const
{
return isHorizontalFlow() ? child.verticalScrollbarWidth() : child.horizontalScrollbarHeight();
@@ -859,19 +858,84 @@
}
}
-LayoutUnit RenderFlexibleBox::adjustChildSizeForMinAndMax(RenderBox& child, LayoutUnit childSize)
+bool RenderFlexibleBox::crossAxisLengthIsDefinite(const RenderBox& child, const Length& length) const
{
+ if (length.isAuto())
+ return false;
+ if (length.isPercentOrCalculated())
+ return hasOrthogonalFlow(child) ? hasDefiniteLogicalWidth() : bool(child.computePercentageLogicalHeight(length));
+ return length.isFixed();
+}
+
+
+Optional<LayoutUnit> RenderFlexibleBox::computeMainSizeFromAspectRatioUsing(const RenderBox& child, Length crossSizeLength) const
+{
+ ASSERT(child.hasAspectRatio());
+ ASSERT(child.intrinsicSize().height() > 0);
+
+ Optional<LayoutUnit> crossSize;
+ if (crossSizeLength.isFixed())
+ crossSize = LayoutUnit(crossSizeLength.value());
+ else {
+ ASSERT(crossSizeLength.isPercentOrCalculated());
+ crossSize = hasOrthogonalFlow(child) ?
+ adjustBorderBoxLogicalWidthForBoxSizing(valueForLength(crossSizeLength, contentWidth())) :
+ child.computePercentageLogicalHeight(crossSizeLength);
+ }
+
+ if (!crossSize)
+ return crossSize;
+
+ const LayoutSize& childIntrinsicSize = child.intrinsicSize();
+ double ratio = childIntrinsicSize.width().toFloat() / childIntrinsicSize.height().toFloat();
+ if (isHorizontalFlow())
+ return LayoutUnit(crossSize.value() * ratio);
+ return LayoutUnit(crossSize.value() / ratio);
+}
+
+LayoutUnit RenderFlexibleBox::adjustChildSizeForAspectRatioCrossAxisMinAndMax(const RenderBox& child, LayoutUnit childSize)
+{
+ Length crossMin = isHorizontalFlow() ? child.style().minHeight() : child.style().minWidth();
+ Length crossMax = isHorizontalFlow() ? child.style().maxHeight() : child.style().maxWidth();
+
+ if (crossAxisLengthIsDefinite(child, crossMax)) {
+ Optional<LayoutUnit> maxValue = computeMainSizeFromAspectRatioUsing(child, crossMax);
+ if (maxValue)
+ childSize = std::min(maxValue.value(), childSize);
+ }
+
+ if (crossAxisLengthIsDefinite(child, crossMin)) {
+ Optional<LayoutUnit> minValue = computeMainSizeFromAspectRatioUsing(child, crossMin);
+ if (minValue)
+ childSize = std::max(minValue.value(), childSize);
+ }
+
+ return childSize;
+}
+
+bool RenderFlexibleBox::useChildAspectRatio(const RenderBox& child) const
+{
+ if (!child.hasAspectRatio())
+ return false;
+ if (!child.intrinsicSize().height())
+ return false;
+ Length crossSize = isHorizontalFlow() ? child.style().height() : child.style().width();
+ return crossAxisLengthIsDefinite(child, crossSize);
+}
+
+LayoutUnit RenderFlexibleBox::adjustChildSizeForMinAndMax(const RenderBox& child, LayoutUnit childSize)
+{
Length max = isHorizontalFlow() ? child.style().maxWidth() : child.style().maxHeight();
Optional<LayoutUnit> maxExtent = Nullopt;
if (max.isSpecifiedOrIntrinsic()) {
maxExtent = computeMainAxisExtentForChild(child, MaxSize, max);
childSize = std::min(childSize, maxExtent.valueOr(childSize));
}
-
+
Length min = isHorizontalFlow() ? child.style().minWidth() : child.style().minHeight();
if (min.isSpecifiedOrIntrinsic())
return std::max(childSize, computeMainAxisExtentForChild(child, MinSize, min).valueOr(childSize));
-
+
if (!isFlexibleBoxImpl() && min.isAuto() && mainAxisOverflowForChild(child) == OVISIBLE && !(isColumnFlow() && is<RenderFlexibleBox>(child))) {
// This is the implementation of CSS flexbox section 4.5 which defines the minimum size of "pure" flex
// items. For any other item the value should be 0, this also includes RenderFlexibleBox's derived clases
@@ -880,15 +944,23 @@
// size handling from the flex box spec first (4.5).
LayoutUnit contentSize = computeMainAxisExtentForChild(child, MinSize, Length(MinContent)).value();
ASSERT(contentSize >= 0);
+ if (child.hasAspectRatio() && child.intrinsicSize().height() > 0)
+ contentSize = adjustChildSizeForAspectRatioCrossAxisMinAndMax(child, contentSize);
contentSize = std::min(contentSize, maxExtent.valueOr(contentSize));
-
+
Length mainSize = isHorizontalFlow() ? child.style().width() : child.style().height();
- if (!mainAxisLengthIsIndefinite(mainSize)) {
+ if (mainAxisLengthIsDefinite(child, mainSize)) {
LayoutUnit resolvedMainSize = computeMainAxisExtentForChild(child, MainOrPreferredSize, mainSize).value();
ASSERT(resolvedMainSize >= 0);
LayoutUnit specifiedSize = std::min(resolvedMainSize, maxExtent.valueOr(resolvedMainSize));
-
return std::max(childSize, std::min(specifiedSize, contentSize));
+ } else if (useChildAspectRatio(child)) {
+ Length crossSizeLength = isHorizontalFlow() ? child.style().height() : child.style().width();
+ Optional<LayoutUnit> transferredSize = computeMainSizeFromAspectRatioUsing(child, crossSizeLength);
+ if (transferredSize) {
+ transferredSize = adjustChildSizeForAspectRatioCrossAxisMinAndMax(child, transferredSize.value());
+ return std::max(childSize, std::min(transferredSize.value(), contentSize));
+ }
}
return std::max(childSize, contentSize);
}
@@ -1091,7 +1163,7 @@
child.updateLogicalHeight();
}
-EOverflow RenderFlexibleBox::mainAxisOverflowForChild(RenderBox& child) const
+EOverflow RenderFlexibleBox::mainAxisOverflowForChild(const RenderBox& child) const
{
if (isHorizontalFlow())
return child.style().overflowX();
Modified: trunk/Source/WebCore/rendering/RenderFlexibleBox.h (201515 => 201516)
--- trunk/Source/WebCore/rendering/RenderFlexibleBox.h 2016-05-31 17:53:20 UTC (rev 201515)
+++ trunk/Source/WebCore/rendering/RenderFlexibleBox.h 2016-05-31 18:42:17 UTC (rev 201516)
@@ -86,7 +86,7 @@
typedef Vector<LayoutRect, 8> ChildFrameRects;
bool isFlexibleBox() const final { return true; }
- bool hasOrthogonalFlow(RenderBox& child) const;
+ bool hasOrthogonalFlow(const RenderBox& child) const;
bool isColumnFlow() const;
bool isLeftToRightFlow() const;
bool isMultiline() const;
@@ -98,7 +98,7 @@
LayoutUnit mainAxisExtent() const;
LayoutUnit crossAxisContentExtent() const;
LayoutUnit mainAxisContentExtent(LayoutUnit contentLogicalHeight);
- Optional<LayoutUnit> computeMainAxisExtentForChild(RenderBox& child, SizeType, const Length& size);
+ Optional<LayoutUnit> computeMainAxisExtentForChild(const RenderBox& child, SizeType, const Length& size);
WritingMode transformedWritingMode() const;
LayoutUnit flowAwareBorderStart() const;
LayoutUnit flowAwareBorderEnd() const;
@@ -122,7 +122,7 @@
LayoutUnit mainAxisBorderAndPaddingExtentForChild(RenderBox& child) const;
LayoutUnit mainAxisScrollbarExtentForChild(RenderBox& child) const;
LayoutUnit preferredMainAxisContentExtentForChild(RenderBox& child, bool hasInfiniteLineLength);
- EOverflow mainAxisOverflowForChild(RenderBox&) const;
+ EOverflow mainAxisOverflowForChild(const RenderBox&) const;
void layoutFlexItems(bool relayoutChildren, Vector<LineContext>&);
LayoutUnit autoMarginOffsetInMainAxis(const OrderedFlexItemList&, LayoutUnit& availableFreeSpace);
@@ -139,7 +139,8 @@
LayoutUnit computeChildMarginValue(const Length& margin);
void prepareOrderIteratorAndMargins();
- LayoutUnit adjustChildSizeForMinAndMax(RenderBox&, LayoutUnit childSize);
+ LayoutUnit adjustChildSizeForMinAndMax(const RenderBox&, LayoutUnit childSize);
+ LayoutUnit adjustChildSizeForAspectRatioCrossAxisMinAndMax(const RenderBox&, LayoutUnit childSize);
bool computeNextFlexLine(OrderedFlexItemList& orderedChildren, LayoutUnit& preferredMainAxisExtent, double& totalFlexGrow, double& totalWeightedFlexShrink, LayoutUnit& minMaxAppliedMainAxisExtent, bool& hasInfiniteLineLength);
bool resolveFlexibleLengths(FlexSign, const OrderedFlexItemList&, LayoutUnit& availableFreeSpace, double& totalFlexGrow, double& totalWeightedFlexShrink, InflexibleFlexItemSize&, Vector<LayoutUnit>& childSizes, bool hasInfiniteLineLength);
@@ -158,9 +159,11 @@
void flipForRightToLeftColumn();
void flipForWrapReverse(const Vector<LineContext>&, LayoutUnit crossAxisStartEdge);
- bool mainAxisExtentIsDefinite() const;
- bool mainAxisLengthIsIndefinite(const Length& flexBasis) const;
-
+ bool mainAxisLengthIsDefinite(const RenderBox&, const Length&) const;
+ bool crossAxisLengthIsDefinite(const RenderBox&, const Length&) const;
+ bool useChildAspectRatio(const RenderBox&) const;
+ Optional<LayoutUnit> computeMainSizeFromAspectRatioUsing(const RenderBox& child, Length crossSizeLength) const;
+
virtual bool isFlexibleBoxImpl() const { return false; };
mutable OrderIterator m_orderIterator;