Title: [138040] trunk
Revision
138040
Author
commit-qu...@webkit.org
Date
2012-12-18 10:43:38 -0800 (Tue, 18 Dec 2012)

Log Message

[CSS Exclusions] Blocks should not re-use their parent's ExclusionShapeInsideInfo
if they participate in inline layout
https://bugs.webkit.org/show_bug.cgi?id=104582

Patch by Bear Travis <betra...@adobe.com> on 2012-12-18
Reviewed by Julien Chaffraix.

Source/WebCore:

Blocks that participate in inline layout should not re-use a parent's
ExclusionShapeInsideInfo, as the parent and child would both use the info for
layout at the same time. This patch alters LayoutState to not include
ExclusionShapeInsideInfo if the current block participates in inline layout (ie,
it is a float, inline-block, or inline-table).

Test: fast/exclusions/shape-inside/shape-inside-recursive-layout.html

* rendering/ExclusionShapeInsideInfo.h:
(WebCore::ExclusionShapeInsideInfo::ownerBlock): Return the block associated with
the shape-inside style.
* rendering/LayoutState.cpp:
(WebCore::LayoutState::LayoutState): Do not re-use ExclusionShapeInsideInfo
on a block that participates in inline layout (floats and inline blocks).
* rendering/RenderBlock.h:
(WebCore::RenderBlock::allowsExclusionShapeInsideInfoSharing): Returns whether the
block can re-use an ExclusionShapeInsideInfo from its parent block.
* rendering/RenderBlockLineLayout.cpp:
(WebCore::RenderBlock::layoutRunsAndFloatsInRange): Adding an assert to make sure
we do not overwrite ExclusionShapeInsideInfo's state during a recursive layout.
* rendering/RenderView.h:
(WebCore::RenderView::pushLayoutState): Push a new LayoutState in the case that
ExclusionShapeInsideInfo exists but should not be propagated.

LayoutTests:

Test that recursive inline layouts work correctly.

* fast/exclusions/resources/simple-rectangle.js:
(createRectangleTest): Remove extra ':' from pseudo-element.
(createRectangleTestResult): Ditto.
* fast/exclusions/shape-inside/shape-inside-recursive-layout-expected.html: Added.
* fast/exclusions/shape-inside/shape-inside-recursive-layout.html: Added.

Modified Paths

Added Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (138039 => 138040)


--- trunk/LayoutTests/ChangeLog	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/LayoutTests/ChangeLog	2012-12-18 18:43:38 UTC (rev 138040)
@@ -1,3 +1,19 @@
+2012-12-18  Bear Travis  <betra...@adobe.com>
+
+        [CSS Exclusions] Blocks should not re-use their parent's ExclusionShapeInsideInfo
+        if they participate in inline layout
+        https://bugs.webkit.org/show_bug.cgi?id=104582
+
+        Reviewed by Julien Chaffraix.
+
+        Test that recursive inline layouts work correctly.
+ 
+        * fast/exclusions/resources/simple-rectangle.js:
+        (createRectangleTest): Remove extra ':' from pseudo-element.
+        (createRectangleTestResult): Ditto.
+        * fast/exclusions/shape-inside/shape-inside-recursive-layout-expected.html: Added.
+        * fast/exclusions/shape-inside/shape-inside-recursive-layout.html: Added.
+ 
 2012-12-18  Zan Dobersek  <zandober...@gmail.com>
 
         Unreviewed GTK gardening.

Modified: trunk/LayoutTests/fast/exclusions/resources/simple-rectangle.js (138039 => 138040)


--- trunk/LayoutTests/fast/exclusions/resources/simple-rectangle.js	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/LayoutTests/fast/exclusions/resources/simple-rectangle.js	2012-12-18 18:43:38 UTC (rev 138040)
@@ -24,7 +24,7 @@
     rules.push('left: ' + (shapeBounds.x - 1) + units, 'top: ' + (shapeBounds.y - 1) + units, 'width: ' + rectangleBounds[2], 'height: ' + rectangleBounds[3]);
     rules.push('position: absolute', 'display: block', 'content: \' \'');
     rules.push('border: 1px solid blue');
-    stylesheet.insertRule('#' + elementId + '::before{' + rules.join(';') + '}');
+    stylesheet.insertRule('#' + elementId + ':before{' + rules.join(';') + '}');
     if (content)
         elem.innerHTML = content;
 }
@@ -51,7 +51,7 @@
     rules.push('left: ' + (shapeBounds.x - 1) + units, 'top: ' + (shapeBounds.y - 1) + units, 'width: ' + shapeBounds.width + units, 'height: ' + shapeBounds.height + units);
     rules.push('position: absolute', 'display: block', 'content: \' \'');
     rules.push('border: 1px solid blue');
-    stylesheet.insertRule('#' + elementId + '::before{' + rules.join(';') + '}');
+    stylesheet.insertRule('#' + elementId + ':before{' + rules.join(';') + '}');
     if (content)
         elem.innerHTML = content;
 }

Added: trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout-expected.html (0 => 138040)


--- trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout-expected.html	                        (rev 0)
+++ trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout-expected.html	2012-12-18 18:43:38 UTC (rev 138040)
@@ -0,0 +1,111 @@
+<!DOCTYPE html>
+<html>
+<head>
+<script src=''></script>
+<style id='stylesheet'>
+.content {
+    font: 50px/1 Ahem, sans-serif;
+    color: green;
+    word-break: break-all;
+    width: 100px;
+    height: 100px;
+    margin: 0;
+    padding: 0;
+}
+#inline-block * {
+    display: inline-block;
+}
+#float * {
+    float: left;
+}
+#list ul {
+    display: inline-block;
+    list-style: none;
+}
+#table table {
+    display: inline-table;
+    border-collapse: collapse;
+}
+#table tr {
+    dispay: inline-table;
+}
+#table td, #table tr {
+    padding: 0; margin: 0;
+}
+#old-flexbox {
+    display: -webkit-inline-box;
+}
+#new-flexbox {
+    display: -webkit-inline-flex;
+}
+#grid {
+    display: -webkit-inline-grid;
+    -webkit-grid-rows: 100px;
+    -webkit-grid-columns: 100px;
+}
+#grid > .content {
+    -webkit-grid-row: 1;
+    -webkit-grid-column: 1;
+}
+</style>
+<script>
+window._onload_ = function() {
+    var elementBounds = { width: 200, height: 200 };
+    var shapeBounds = { x: 50, y: 50, width: 100, height: 100 };
+    createRectangleTestResult('inline-block', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('float', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('list', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('table', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('old-flexbox', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('new-flexbox', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTestResult('grid', 'stylesheet', elementBounds, shapeBounds, 'px');
+}
+</script>
+</head>
+<body>
+<p>This set of tests ensures that basic recursive layouts with inline-block elements
+function correctly with shape-inside. They require the Ahem font, and should each display
+a green square within a blue border.</p>
+
+<p>Inline-block div</p>
+<div id='inline-block'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Floating div</p>
+<div id='float'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Inline list</p>
+<div id='list'>
+    <ul class='content'>
+        <li>xx</li>
+        <li>xx</li>
+    </ul>
+</div>
+
+<p>Inline table</p>
+<div id='table'>
+    <table class='content'>
+        <tr><td>x</td><td>x</td></tr>
+        <tr><td>x</td><td>x</td></tr>
+    </table>
+</div>
+
+<p>Old flexbox</p>
+<div id='old-flexbox'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>New flexbox</p>
+<div id='new-flexbox'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Grid</p>
+<div id='grid'>
+    <div class='content'>xxxx</div>
+</div>
+</body>
+</html>
\ No newline at end of file

Added: trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout.html (0 => 138040)


--- trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout.html	                        (rev 0)
+++ trunk/LayoutTests/fast/exclusions/shape-inside/shape-inside-recursive-layout.html	2012-12-18 18:43:38 UTC (rev 138040)
@@ -0,0 +1,111 @@
+<!DOCTYPE html>
+<html>
+<head>
+<script src=''></script>
+<style id='stylesheet'>
+.content {
+    font: 50px/1 Ahem, sans-serif;
+    color: green;
+    word-break: break-all;
+    width: 100px;
+    height: 100px;
+    margin: 0;
+    padding: 0;
+}
+#inline-block * {
+    display: inline-block;
+}
+#float * {
+    float: left;
+}
+#list ul {
+    display: inline-block;
+    list-style: none;
+}
+#table table {
+    display: inline-table;
+    border-collapse: collapse;
+}
+#table tr {
+    dispay: inline-table;
+}
+#table td, #table tr {
+    padding: 0; margin: 0;
+}
+#old-flexbox {
+    display: -webkit-inline-box;
+}
+#new-flexbox {
+    display: -webkit-inline-flex;
+}
+#grid {
+    display: -webkit-inline-grid;
+    -webkit-grid-rows: 100px;
+    -webkit-grid-columns: 100px;
+}
+#grid > .content {
+    -webkit-grid-row: 1;
+    -webkit-grid-column: 1;
+}
+</style>
+<script>
+window._onload_ = function() {
+    var elementBounds = { width: 200, height: 200 };
+    var shapeBounds = { x: 50, y: 50, width: 100, height: 100 };
+    createRectangleTest('inline-block', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('float', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('list', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('table', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('old-flexbox', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('new-flexbox', 'stylesheet', elementBounds, shapeBounds, 'px');
+    createRectangleTest('grid', 'stylesheet', elementBounds, shapeBounds, 'px');
+}
+</script>
+</head>
+<body>
+<p>This set of tests ensures that basic recursive layouts with inline-block elements
+function correctly with shape-inside. They require the Ahem font, and should each display
+a green square within a blue border.</p>
+
+<p>Inline-block div</p>
+<div id='inline-block'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Floating div</p>
+<div id='float'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Inline list</p>
+<div id='list'>
+    <ul class='content'>
+        <li>xx</li>
+        <li>xx</li>
+    </ul>
+</div>
+
+<p>Inline table</p>
+<div id='table'>
+    <table class='content'>
+        <tr><td>x</td><td>x</td></tr>
+        <tr><td>x</td><td>x</td></tr>
+    </table>
+</div>
+
+<p>Old flexbox</p>
+<div id='old-flexbox'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>New flexbox</p>
+<div id='new-flexbox'>
+    <div class='content'>xxxx</div>
+</div>
+
+<p>Grid</p>
+<div id='grid'>
+    <div class='content'>xxxx</div>
+</div>
+</body>
+</html>
\ No newline at end of file

Modified: trunk/Source/WebCore/ChangeLog (138039 => 138040)


--- trunk/Source/WebCore/ChangeLog	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/ChangeLog	2012-12-18 18:43:38 UTC (rev 138040)
@@ -1,3 +1,35 @@
+2012-12-18  Bear Travis  <betra...@adobe.com>
+
+        [CSS Exclusions] Blocks should not re-use their parent's ExclusionShapeInsideInfo
+        if they participate in inline layout
+        https://bugs.webkit.org/show_bug.cgi?id=104582
+
+        Reviewed by Julien Chaffraix.
+
+        Blocks that participate in inline layout should not re-use a parent's
+        ExclusionShapeInsideInfo, as the parent and child would both use the info for
+        layout at the same time. This patch alters LayoutState to not include
+        ExclusionShapeInsideInfo if the current block participates in inline layout (ie,
+        it is a float, inline-block, or inline-table).
+
+        Test: fast/exclusions/shape-inside/shape-inside-recursive-layout.html
+
+        * rendering/ExclusionShapeInsideInfo.h:
+        (WebCore::ExclusionShapeInsideInfo::ownerBlock): Return the block associated with
+        the shape-inside style.
+        * rendering/LayoutState.cpp:
+        (WebCore::LayoutState::LayoutState): Do not re-use ExclusionShapeInsideInfo
+        on a block that participates in inline layout (floats and inline blocks).
+        * rendering/RenderBlock.h:
+        (WebCore::RenderBlock::allowsExclusionShapeInsideInfoSharing): Returns whether the
+        block can re-use an ExclusionShapeInsideInfo from its parent block.
+        * rendering/RenderBlockLineLayout.cpp:
+        (WebCore::RenderBlock::layoutRunsAndFloatsInRange): Adding an assert to make sure
+        we do not overwrite ExclusionShapeInsideInfo's state during a recursive layout.
+        * rendering/RenderView.h:
+        (WebCore::RenderView::pushLayoutState): Push a new LayoutState in the case that
+        ExclusionShapeInsideInfo exists but should not be propagated.
+
 2012-12-18  Tony Chang  <t...@chromium.org>
 
         REGRESSION(r136324): flex items with percent heights not resizing

Modified: trunk/Source/WebCore/rendering/ExclusionShapeInsideInfo.h (138039 => 138040)


--- trunk/Source/WebCore/rendering/ExclusionShapeInsideInfo.h	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/rendering/ExclusionShapeInsideInfo.h	2012-12-18 18:43:38 UTC (rev 138040)
@@ -102,6 +102,7 @@
     void dirtyShapeSize() { m_shapeSizeDirty = true; }
 
     LayoutUnit logicalLineTop() const { return m_lineTop; }
+    RenderBlock* ownerBlock() const { return m_block; }
 
 private:
     ExclusionShapeInsideInfo(RenderBlock*);

Modified: trunk/Source/WebCore/rendering/LayoutState.cpp (138039 => 138040)


--- trunk/Source/WebCore/rendering/LayoutState.cpp	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/rendering/LayoutState.cpp	2012-12-18 18:43:38 UTC (rev 138040)
@@ -112,8 +112,9 @@
 
 #if ENABLE(CSS_EXCLUSIONS)
     if (renderer->isRenderBlock()) {
-        m_exclusionShapeInsideInfo = toRenderBlock(renderer)->exclusionShapeInsideInfo();
-        if (!m_exclusionShapeInsideInfo)
+        const RenderBlock* renderBlock = toRenderBlock(renderer);
+        m_exclusionShapeInsideInfo = renderBlock->exclusionShapeInsideInfo();
+        if (!m_exclusionShapeInsideInfo && m_next->m_exclusionShapeInsideInfo && renderBlock->allowsExclusionShapeInsideInfoSharing())
             m_exclusionShapeInsideInfo = m_next->m_exclusionShapeInsideInfo;
     }
 #endif

Modified: trunk/Source/WebCore/rendering/RenderBlock.h (138039 => 138040)


--- trunk/Source/WebCore/rendering/RenderBlock.h	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/rendering/RenderBlock.h	2012-12-18 18:43:38 UTC (rev 138040)
@@ -434,6 +434,7 @@
 
 #if ENABLE(CSS_EXCLUSIONS)
     ExclusionShapeInsideInfo* exclusionShapeInsideInfo() const;
+    bool allowsExclusionShapeInsideInfoSharing() const { return !isInline() && !isFloating(); }
 #endif
 
     virtual void reportMemoryUsage(MemoryObjectInfo*) const OVERRIDE;

Modified: trunk/Source/WebCore/rendering/RenderBlockLineLayout.cpp (138039 => 138040)


--- trunk/Source/WebCore/rendering/RenderBlockLineLayout.cpp	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/rendering/RenderBlockLineLayout.cpp	2012-12-18 18:43:38 UTC (rev 138040)
@@ -1499,6 +1499,7 @@
     LayoutUnit absoluteLogicalTop;
     ExclusionShapeInsideInfo* exclusionShapeInsideInfo = layoutExclusionShapeInsideInfo(this);
     if (exclusionShapeInsideInfo) {
+        ASSERT(exclusionShapeInsideInfo->ownerBlock() == this || allowsExclusionShapeInsideInfoSharing());
         if (exclusionShapeInsideInfo != this->exclusionShapeInsideInfo()) {
             // FIXME Bug 100284: If subsequent LayoutStates are pushed, we will have to add
             // their offsets from the original shape-inside container.

Modified: trunk/Source/WebCore/rendering/RenderView.h (138039 => 138040)


--- trunk/Source/WebCore/rendering/RenderView.h	2012-12-18 18:35:42 UTC (rev 138039)
+++ trunk/Source/WebCore/rendering/RenderView.h	2012-12-18 18:43:38 UTC (rev 138040)
@@ -249,6 +249,7 @@
             || m_layoutState->lineGrid() || (renderer->style()->lineGrid() != RenderStyle::initialLineGrid() && renderer->isBlockFlow())
 #if ENABLE(CSS_EXCLUSIONS)
             || (renderer->isRenderBlock() && toRenderBlock(renderer)->exclusionShapeInsideInfo())
+            || (m_layoutState->exclusionShapeInsideInfo() && renderer->isRenderBlock() && !toRenderBlock(renderer)->allowsExclusionShapeInsideInfoSharing())
 #endif
             ) {
             m_layoutState = new (renderArena()) LayoutState(m_layoutState, renderer, offset, pageHeight, pageHeightChanged, colInfo);
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
http://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to