Changeset 142527 in webkit


Ignore:
Timestamp:
Feb 11, 2013 3:17:12 PM (11 years ago)
Author:
commit-queue@webkit.org
Message:

[CSS Exclusions] Handle shape-outside changing a float's overhang behavior
https://bugs.webkit.org/show_bug.cgi?id=106927

Patch by Bem Jones-Bey <Bem Jones-Bey> on 2013-02-11
Reviewed by Julien Chaffraix.

Source/WebCore:

When the position on a shape outside causes a float to spill out into
another block than it's container, it was not being drawn correctly. It
became apparent that in order to fix this properly, the approach to
positioning shape outsides and floats needed to be changed. The new
approach also fixes some other outstanding issues, like hit detection.

When a float has a shape outside, inline and float layout happens
using the exclusion shape bounds instead of the float's box. The
effect of this is that the float itself no longer has any effect on
layout, both with respect to positioning of the float's siblings as
well as positioning the float's box. This means that when the float is
positioned, it is the shape's box that must obey the positioning rules
for floats. When the shape is given a position relative to the float's
box, the rules for float positioning determine where the shape sits
in the parent, causing the float's box to be offset by the position of
the shape. Since the float's box does not affect layout (due to the
shape), this is similar to relative positioning in that the offset is
a paint time occurrence.

So the new approach is to implement positioning of shape outside on
floats similar to how relative positioning is implemented, using a
RenderLayer.

This is also tested by the existing tests for shape outside on floats positioning.

Test: fast/exclusions/shape-outside-floats/shape-outside-floats-overhang.html

  • rendering/ExclusionShapeOutsideInfo.h:

(WebCore::ExclusionShapeOutsideInfo::shapeLogicalOffset): Utility method to create a LayoutSize for computing the layer offset.
(ExclusionShapeOutsideInfo):

  • rendering/LayoutState.cpp:

(WebCore::LayoutState::LayoutState): Check for floats with shape outside as well as in flow positioning.

  • rendering/RenderBlock.cpp:

(WebCore::RenderBlock::flipFloatForWritingModeForChild): Remove old positioning implementation.
(WebCore::RenderBlock::paintFloats): Remove old positioning implementation.
(WebCore::RenderBlock::blockSelectionGaps): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderBlock::positionNewFloats): Remove old positioning implementation.
(WebCore::RenderBlock::addOverhangingFloats): Remove FIXME.
(WebCore::positionForPointRespectingEditingBoundaries): Check for floats with shape outside as well as in flow positioning.

  • rendering/RenderBlock.h:

(RenderBlock): Remove old positioning implementation.
(WebCore::RenderBlock::xPositionForFloatIncludingMargin): Remove old positioning implementation.
(WebCore::RenderBlock::yPositionForFloatIncludingMargin): Remove old positioning implementation.

  • rendering/RenderBox.cpp:

(WebCore::RenderBox::mapLocalToContainer): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderBox::offsetFromContainer): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderBox::computeRectForRepaint): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderBox::layoutOverflowRectForPropagation): Check for floats with shape outside as well as in flow positioning.

  • rendering/RenderBox.h: Make floats with shape outside get a layer.
  • rendering/RenderBoxModelObject.cpp:

(WebCore::RenderBoxModelObject::paintOffset): Method to return in flow

positioning offset + offset from shape outside on floats.

  • rendering/RenderBoxModelObject.h:

(RenderBoxModelObject): Add paintOffset method.

  • rendering/RenderInline.cpp:

(WebCore::RenderInline::clippedOverflowRectForRepaint): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderInline::computeRectForRepaint): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderInline::mapLocalToContainer): Check for floats with shape outside as well as in flow positioning.

  • rendering/RenderLayer.cpp:

(WebCore::RenderLayer::updateLayerPosition): Check for floats with shape outside as well as in flow positioning.
(WebCore::RenderLayer::calculateClipRects): Check for floats with shape outside as well as in flow positioning.

  • rendering/RenderLayer.h:

(WebCore::RenderLayer::paintOffset): Rename offsetForInFlowPosition to reflect that it's not just for

in flow positioning, it also reflects shape outside position on floats.

(RenderLayer):

  • rendering/RenderObject.h:

(WebCore::RenderObject::hasPaintOffset): Determines if this object is in flow positioined or is a float with shape outside.

  • rendering/style/RenderStyle.h: Add hasPaintOffset method, analagous to method with same name on RenderObject.

LayoutTests:

This is also tested by the existing tests for shape outside on floats positioning.

  • fast/exclusions/shape-outside-floats/shape-outside-floats-overhang-expected.html: Added.
  • fast/exclusions/shape-outside-floats/shape-outside-floats-overhang.html: Added.
Location:
trunk
Files:
2 added
15 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r142526 r142527  
     12013-02-11  Bem Jones-Bey  <bjonesbe@adobe.com>
     2
     3        [CSS Exclusions] Handle shape-outside changing a float's overhang behavior
     4        https://bugs.webkit.org/show_bug.cgi?id=106927
     5
     6        Reviewed by Julien Chaffraix.
     7
     8        This is also tested by the existing tests for shape outside on floats positioning.
     9
     10        * fast/exclusions/shape-outside-floats/shape-outside-floats-overhang-expected.html: Added.
     11        * fast/exclusions/shape-outside-floats/shape-outside-floats-overhang.html: Added.
     12
    1132013-02-11  Tim Horton  <timothy_horton@apple.com>
    214
  • trunk/Source/WebCore/ChangeLog

    r142526 r142527  
     12013-02-11  Bem Jones-Bey  <bjonesbe@adobe.com>
     2
     3        [CSS Exclusions] Handle shape-outside changing a float's overhang behavior
     4        https://bugs.webkit.org/show_bug.cgi?id=106927
     5
     6        Reviewed by Julien Chaffraix.
     7
     8        When the position on a shape outside causes a float to spill out into
     9        another block than it's container, it was not being drawn correctly. It
     10        became apparent that in order to fix this properly, the approach to
     11        positioning shape outsides and floats needed to be changed. The new
     12        approach also fixes some other outstanding issues, like hit detection.
     13
     14        When a float has a shape outside, inline and float layout happens
     15        using the exclusion shape bounds instead of the float's box.  The
     16        effect of this is that the float itself no longer has any effect on
     17        layout, both with respect to positioning of the float's siblings as
     18        well as positioning the float's box. This means that when the float is
     19        positioned, it is the shape's box that must obey the positioning rules
     20        for floats. When the shape is given a position relative to the float's
     21        box, the rules for float positioning determine where the shape sits
     22        in the parent, causing the float's box to be offset by the position of
     23        the shape. Since the float's box does not affect layout (due to the
     24        shape), this is similar to relative positioning in that the offset is
     25        a paint time occurrence.
     26
     27        So the new approach is to implement positioning of shape outside on
     28        floats similar to how relative positioning is implemented, using a
     29        RenderLayer.
     30
     31        This is also tested by the existing tests for shape outside on floats positioning.
     32
     33        Test: fast/exclusions/shape-outside-floats/shape-outside-floats-overhang.html
     34
     35        * rendering/ExclusionShapeOutsideInfo.h:
     36        (WebCore::ExclusionShapeOutsideInfo::shapeLogicalOffset): Utility method to create a LayoutSize for computing the layer offset.
     37        (ExclusionShapeOutsideInfo):
     38        * rendering/LayoutState.cpp:
     39        (WebCore::LayoutState::LayoutState): Check for floats with shape outside as well as in flow positioning.
     40        * rendering/RenderBlock.cpp:
     41        (WebCore::RenderBlock::flipFloatForWritingModeForChild): Remove old positioning implementation.
     42        (WebCore::RenderBlock::paintFloats): Remove old positioning implementation.
     43        (WebCore::RenderBlock::blockSelectionGaps): Check for floats with shape outside as well as in flow positioning.
     44        (WebCore::RenderBlock::positionNewFloats): Remove old positioning implementation.
     45        (WebCore::RenderBlock::addOverhangingFloats): Remove FIXME.
     46        (WebCore::positionForPointRespectingEditingBoundaries): Check for floats with shape outside as well as in flow positioning.
     47        * rendering/RenderBlock.h:
     48        (RenderBlock): Remove old positioning implementation.
     49        (WebCore::RenderBlock::xPositionForFloatIncludingMargin): Remove old positioning implementation.
     50        (WebCore::RenderBlock::yPositionForFloatIncludingMargin): Remove old positioning implementation.
     51        * rendering/RenderBox.cpp:
     52        (WebCore::RenderBox::mapLocalToContainer): Check for floats with shape outside as well as in flow positioning.
     53        (WebCore::RenderBox::offsetFromContainer): Check for floats with shape outside as well as in flow positioning.
     54        (WebCore::RenderBox::computeRectForRepaint): Check for floats with shape outside as well as in flow positioning.
     55        (WebCore::RenderBox::layoutOverflowRectForPropagation): Check for floats with shape outside as well as in flow positioning.
     56        * rendering/RenderBox.h: Make floats with shape outside get a layer.
     57        * rendering/RenderBoxModelObject.cpp:
     58        (WebCore::RenderBoxModelObject::paintOffset): Method to return in flow
     59            positioning offset + offset from shape outside on floats.
     60        * rendering/RenderBoxModelObject.h:
     61        (RenderBoxModelObject): Add paintOffset method.
     62        * rendering/RenderInline.cpp:
     63        (WebCore::RenderInline::clippedOverflowRectForRepaint): Check for floats with shape outside as well as in flow positioning.
     64        (WebCore::RenderInline::computeRectForRepaint): Check for floats with shape outside as well as in flow positioning.
     65        (WebCore::RenderInline::mapLocalToContainer): Check for floats with shape outside as well as in flow positioning.
     66        * rendering/RenderLayer.cpp:
     67        (WebCore::RenderLayer::updateLayerPosition): Check for floats with shape outside as well as in flow positioning.
     68        (WebCore::RenderLayer::calculateClipRects): Check for floats with shape outside as well as in flow positioning.
     69        * rendering/RenderLayer.h:
     70        (WebCore::RenderLayer::paintOffset): Rename offsetForInFlowPosition to reflect that it's not just for
     71            in flow positioning, it also reflects shape outside position on floats.
     72        (RenderLayer):
     73        * rendering/RenderObject.h:
     74        (WebCore::RenderObject::hasPaintOffset): Determines if this object is in flow positioined or is a float with shape outside.
     75        * rendering/style/RenderStyle.h: Add hasPaintOffset method, analagous to method with same name on RenderObject.
     76
    1772013-02-11  Tim Horton  <timothy_horton@apple.com>
    278
  • trunk/Source/WebCore/rendering/ExclusionShapeOutsideInfo.h

    r140978 r142527  
    3434
    3535#include "ExclusionShapeInfo.h"
     36#include "LayoutSize.h"
    3637
    3738namespace WebCore {
     
    4142class ExclusionShapeOutsideInfo : public ExclusionShapeInfo<RenderBox, &RenderStyle::shapeOutside>, public MappedInfo<RenderBox, ExclusionShapeOutsideInfo> {
    4243public:
     44    LayoutSize shapeLogicalOffset() const
     45    {
     46        return LayoutSize(shapeLogicalLeft(), shapeLogicalTop());
     47    }
     48
    4349    static PassOwnPtr<ExclusionShapeOutsideInfo> createInfo(const RenderBox* renderer) { return adoptPtr(new ExclusionShapeOutsideInfo(renderer)); }
    4450    static bool isEnabledFor(const RenderBox*);
  • trunk/Source/WebCore/rendering/LayoutState.cpp

    r138040 r142527  
    6666    m_layoutOffset = m_paintOffset;
    6767
    68     if (renderer->isInFlowPositioned() && renderer->hasLayer())
    69         m_paintOffset += renderer->layer()->offsetForInFlowPosition();
     68    if (renderer->hasPaintOffset() && renderer->hasLayer())
     69        m_paintOffset += renderer->layer()->paintOffset();
    7070
    7171    m_clipped = !fixed && prev->m_clipped;
  • trunk/Source/WebCore/rendering/RenderBlock.cpp

    r142042 r142527  
    31283128}
    31293129
    3130 LayoutPoint RenderBlock::flipFloatForWritingModeForChild(const FloatingObject* child, const LayoutPoint& point, FloatRenderingState renderingState) const
     3130LayoutPoint RenderBlock::flipFloatForWritingModeForChild(const FloatingObject* child, const LayoutPoint& point) const
    31313131{
    31323132    if (!style()->isFlippedBlocksWritingMode())
     
    31373137    // case.
    31383138    if (isHorizontalWritingMode())
    3139         return LayoutPoint(point.x(), point.y() + height() - child->renderer()->height() - 2 * yPositionForFloatIncludingMargin(child, renderingState));
    3140     return LayoutPoint(point.x() + width() - child->renderer()->width() - 2 * xPositionForFloatIncludingMargin(child, renderingState), point.y());
     3139        return LayoutPoint(point.x(), point.y() + height() - child->renderer()->height() - 2 * yPositionForFloatIncludingMargin(child));
     3140    return LayoutPoint(point.x() + width() - child->renderer()->width() - 2 * xPositionForFloatIncludingMargin(child), point.y());
    31413141}
    31423142
     
    31543154            PaintInfo currentPaintInfo(paintInfo);
    31553155            currentPaintInfo.phase = preservePhase ? paintInfo.phase : PaintPhaseBlockBackground;
    3156             LayoutPoint childPoint = flipFloatForWritingModeForChild(r, LayoutPoint(paintOffset.x() + xPositionForFloatIncludingMargin(r, FloatPaint) - r->m_renderer->x(), paintOffset.y() + yPositionForFloatIncludingMargin(r, FloatPaint) - r->m_renderer->y()), FloatPaint);
     3156            LayoutPoint childPoint = flipFloatForWritingModeForChild(r, LayoutPoint(paintOffset.x() + xPositionForFloatIncludingMargin(r) - r->m_renderer->x(), paintOffset.y() + yPositionForFloatIncludingMargin(r) - r->m_renderer->y()));
    31573157            r->m_renderer->paint(currentPaintInfo, childPoint);
    31583158            if (!preservePhase) {
     
    34853485            continue; // We must be a normal flow object in order to even be considered.
    34863486
    3487         if (curr->isInFlowPositioned() && curr->hasLayer()) {
     3487        if (curr->hasPaintOffset() && curr->hasLayer()) {
    34883488            // If the relposition offset is anything other than 0, then treat this just like an absolute positioned element.
    34893489            // Just disregard it completely.
    3490             LayoutSize relOffset = curr->layer()->offsetForInFlowPosition();
     3490            LayoutSize relOffset = curr->layer()->paintOffset();
    34913491            if (relOffset.width() || relOffset.height())
    34923492                continue;
     
    40144014        setLogicalLeftForFloat(floatingObject, floatLogicalLocation.x());
    40154015
    4016 #if ENABLE(CSS_EXCLUSIONS)
    4017         if (childBox->exclusionShapeOutsideInfo()) {
    4018             // The CSS Exclusions specification says that the margins are ignored when a float has a shape outside.
    4019             setLogicalLeftForChild(childBox, floatLogicalLocation.x() - childBox->exclusionShapeOutsideInfo()->shapeLogicalLeft());
    4020             setLogicalTopForChild(childBox, floatLogicalLocation.y() - childBox->exclusionShapeOutsideInfo()->shapeLogicalTop());
    4021         } else {
    4022 #endif
    4023             setLogicalLeftForChild(childBox, floatLogicalLocation.x() + childLogicalLeftMargin);
    4024             setLogicalTopForChild(childBox, floatLogicalLocation.y() + marginBeforeForChild(childBox));
    4025 #if ENABLE(CSS_EXCLUSIONS)
    4026         }
    4027 #endif
     4016        setLogicalLeftForChild(childBox, floatLogicalLocation.x() + childLogicalLeftMargin);
     4017        setLogicalTopForChild(childBox, floatLogicalLocation.y() + marginBeforeForChild(childBox));
    40284018
    40294019        LayoutState* layoutState = view()->layoutState();
     
    40544044                setLogicalLeftForFloat(floatingObject, floatLogicalLocation.x());
    40554045
    4056 #if ENABLE(CSS_EXCLUSIONS)
    4057                 if (childBox->exclusionShapeOutsideInfo()) {
    4058                     // The CSS Exclusions specification says that the margins are ignored when a float has a shape outside.
    4059                     setLogicalLeftForChild(childBox, floatLogicalLocation.x() - childBox->exclusionShapeOutsideInfo()->shapeLogicalLeft());
    4060                     setLogicalTopForChild(childBox, floatLogicalLocation.y() - childBox->exclusionShapeOutsideInfo()->shapeLogicalTop());
    4061                 } else {
    4062 #endif
    4063                     setLogicalLeftForChild(childBox, floatLogicalLocation.x() + childLogicalLeftMargin);
    4064                     setLogicalTopForChild(childBox, floatLogicalLocation.y() + marginBeforeForChild(childBox));
    4065 #if ENABLE(CSS_EXCLUSIONS)
    4066                 }
    4067 #endif
    4068 
     4046                setLogicalLeftForChild(childBox, floatLogicalLocation.x() + childLogicalLeftMargin);
     4047                setLogicalTopForChild(childBox, floatLogicalLocation.y() + marginBeforeForChild(childBox));
    40694048       
    40704049                if (childBlock)
     
    45594538        lowestFloatLogicalBottom = max(lowestFloatLogicalBottom, logicalBottom);
    45604539
    4561         // FIXME: Bug 106927 Handle situations where float and shape-outside overflow differently.
    45624540        if (logicalBottom > logicalHeight()) {
    45634541            // If the object is not in the list, we add it now.
     
    50385016{
    50395017    LayoutPoint childLocation = child->location();
    5040     if (child->isInFlowPositioned())
    5041         childLocation += child->offsetForInFlowPosition();
     5018    if (child->hasPaintOffset())
     5019        childLocation += child->paintOffset();
    50425020
    50435021    // FIXME: This is wrong if the child's writing-mode is different from the parent's.
  • trunk/Source/WebCore/rendering/RenderBlock.h

    r142015 r142527  
    690690    };
    691691
    692     // When a float has shape outside, it needs to be handled differently at
    693     // paint time and at layout time, since the coordinates of the shape
    694     // (affecting layout) and the coordinates of the float itself (affecting
    695     // where the content of the float is) can be in different places. This enum
    696     // is used to change behavior based on that state.
    697     enum FloatRenderingState { FloatLayout, FloatPaint };
    698 
    699     LayoutPoint flipFloatForWritingModeForChild(const FloatingObject*, const LayoutPoint&, FloatRenderingState = FloatLayout) const;
     692    LayoutPoint flipFloatForWritingModeForChild(const FloatingObject*, const LayoutPoint&) const;
    700693
    701694    LayoutUnit logicalTopForFloat(const FloatingObject* child) const { return isHorizontalWritingMode() ? child->y() : child->x(); }
     
    739732    }
    740733
    741     LayoutUnit xPositionForFloatIncludingMargin(const FloatingObject* child, FloatRenderingState renderingState = FloatLayout) const
     734    LayoutUnit xPositionForFloatIncludingMargin(const FloatingObject* child) const
    742735    {
    743736#if ENABLE(CSS_EXCLUSIONS)
    744737        ExclusionShapeOutsideInfo *shapeOutside = child->renderer()->exclusionShapeOutsideInfo();
    745         if (renderingState == FloatPaint && shapeOutside)
    746             return child->x() - (isHorizontalWritingMode() ? shapeOutside->shapeLogicalLeft() : shapeOutside->shapeLogicalTop());
    747         // FIXME: Bug 106928 This needs to properly handle the margin for floats with shape-outside for non-paint time.
     738        if (shapeOutside)
     739            return child->x();
    748740#endif
    749741
     
    754746    }
    755747       
    756     LayoutUnit yPositionForFloatIncludingMargin(const FloatingObject* child, FloatRenderingState renderingState = FloatLayout) const
     748    LayoutUnit yPositionForFloatIncludingMargin(const FloatingObject* child) const
    757749    {
    758750#if ENABLE(CSS_EXCLUSIONS)
    759751        ExclusionShapeOutsideInfo *shapeOutside = child->renderer()->exclusionShapeOutsideInfo();
    760         if (renderingState == FloatPaint && shapeOutside)
    761             return child->y() - (isHorizontalWritingMode() ? shapeOutside->shapeLogicalTop() : shapeOutside->shapeLogicalLeft());
    762         // FIXME: Bug 106928 This needs to properly handle the margin for floats with shape-outside.
     752        if (shapeOutside)
     753            return child->y();
    763754#endif
    764755
  • trunk/Source/WebCore/rendering/RenderBox.cpp

    r142021 r142527  
    16061606            LayoutState* layoutState = v->layoutState();
    16071607            LayoutSize offset = layoutState->m_paintOffset + locationOffset();
    1608             if (style()->hasInFlowPosition() && layer())
    1609                 offset += layer()->offsetForInFlowPosition();
     1608            if (style()->hasPaintOffset() && layer())
     1609                offset += layer()->paintOffset();
    16101610            transformState.move(offset);
    16111611            return;
     
    17191719
    17201720    LayoutSize offset;   
    1721     if (isInFlowPositioned())
    1722         offset += offsetForInFlowPosition();
     1721    if (hasPaintOffset())
     1722        offset += paintOffset();
    17231723
    17241724    if (!isInline() || isReplaced()) {
     
    18571857
    18581858            // We can't trust the bits on RenderObject, because this might be called while re-resolving style.
    1859             if (styleToUse->hasInFlowPosition() && layer())
    1860                 rect.move(layer()->offsetForInFlowPosition());
     1859            if (styleToUse->hasPaintOffset() && layer())
     1860                rect.move(layer()->paintOffset());
    18611861
    18621862            rect.moveBy(location());
     
    19021902    if (position == AbsolutePosition && o->isInFlowPositioned() && o->isRenderInline())
    19031903        topLeft += toRenderInline(o)->offsetForInFlowPositionedInline(this);
    1904     else if ((position == RelativePosition || position == StickyPosition) && layer()) {
     1904    else if (styleToUse->hasPaintOffset() && layer()) {
    19051905        // Apply the relative position offset when invalidating a rectangle.  The layer
    19061906        // is translated, but the render box isn't, so we need to do this to get the
    19071907        // right dirty rect.  Since this is called from RenderObject::setStyle, the relative position
    19081908        // flag on the RenderObject has been cleared, so use the one on the style().
    1909         topLeft += layer()->offsetForInFlowPosition();
     1909        topLeft += layer()->paintOffset();
    19101910    }
    19111911   
     
    42644264
    42654265    bool hasTransform = hasLayer() && layer()->transform();
    4266     if (isInFlowPositioned() || hasTransform) {
     4266    if (hasPaintOffset() || hasTransform) {
    42674267        // If we are relatively positioned or if we have a transform, then we have to convert
    42684268        // this rectangle into physical coordinates, apply relative positioning and transforms
     
    42734273            rect = layer()->currentTransform().mapRect(rect);
    42744274
    4275         if (isInFlowPositioned())
    4276             rect.move(offsetForInFlowPosition());
     4275        if (hasPaintOffset())
     4276            rect.move(paintOffset());
    42774277       
    42784278        // Now we need to flip back.
  • trunk/Source/WebCore/rendering/RenderBox.h

    r141963 r142527  
    5050    // hasAutoZIndex only returns true if the element is positioned or a flex-item since
    5151    // position:static elements that are not flex-items get their z-index coerced to auto.
    52     virtual bool requiresLayer() const OVERRIDE { return isRoot() || isPositioned() || createsGroup() || hasClipPath() || hasOverflowClip() || hasTransform() || hasHiddenBackface() || hasReflection() || style()->specifiesColumns() || !style()->hasAutoZIndex(); }
     52    virtual bool requiresLayer() const OVERRIDE { return isRoot() || isPositioned() || createsGroup() || hasClipPath() || hasOverflowClip() || hasTransform() || hasHiddenBackface() || hasReflection() || style()->specifiesColumns() || !style()->hasAutoZIndex() || (style()->shapeOutside() && isFloating()); }
    5353
    5454    // Use this with caution! No type checking is done!
  • trunk/Source/WebCore/rendering/RenderBoxModelObject.cpp

    r141775 r142527  
    533533
    534534    return LayoutSize();
     535}
     536
     537LayoutSize RenderBoxModelObject::paintOffset() const
     538{
     539    LayoutSize offset = offsetForInFlowPosition();
     540
     541#if ENABLE(CSS_EXCLUSIONS)
     542    if (isBox() && isFloating())
     543        if (ExclusionShapeOutsideInfo* shapeOutside = toRenderBox(this)->exclusionShapeOutsideInfo())
     544            offset -= shapeOutside->shapeLogicalOffset();
     545#endif
     546
     547    return offset;
    535548}
    536549
  • trunk/Source/WebCore/rendering/RenderBoxModelObject.h

    r142015 r142527  
    7171
    7272    LayoutSize offsetForInFlowPosition() const;
     73    LayoutSize paintOffset() const;
    7374
    7475    // IE extensions. Used to calculate offsetWidth/Height.  Overridden by inlines (RenderFlow)
  • trunk/Source/WebCore/rendering/RenderInline.cpp

    r142015 r142527  
    10131013        }
    10141014        if (inlineFlow->style()->hasInFlowPosition() && inlineFlow->hasLayer())
    1015             repaintRect.move(toRenderInline(inlineFlow)->layer()->offsetForInFlowPosition());
     1015            repaintRect.move(toRenderInline(inlineFlow)->layer()->paintOffset());
    10161016    }
    10171017
     
    10601060            LayoutState* layoutState = v->layoutState();
    10611061            if (style()->hasInFlowPosition() && layer())
    1062                 rect.move(layer()->offsetForInFlowPosition());
     1062                rect.move(layer()->paintOffset());
    10631063            rect.move(layoutState->m_paintOffset);
    10641064            if (layoutState->m_clipped)
     
    10931093        // right dirty rect. Since this is called from RenderObject::setStyle, the relative or sticky position
    10941094        // flag on the RenderObject has been cleared, so use the one on the style().
    1095         topLeft += layer()->offsetForInFlowPosition();
     1095        topLeft += layer()->paintOffset();
    10961096    }
    10971097   
     
    11451145            LayoutSize offset = layoutState->m_paintOffset;
    11461146            if (style()->hasInFlowPosition() && layer())
    1147                 offset += layer()->offsetForInFlowPosition();
     1147                offset += layer()->paintOffset();
    11481148            transformState.move(offset);
    11491149            return;
  • trunk/Source/WebCore/rendering/RenderLayer.cpp

    r142195 r142527  
    11861186   
    11871187    bool positionOrOffsetChanged = false;
    1188     if (renderer()->isInFlowPositioned()) {
    1189         LayoutSize newOffset = toRenderBoxModelObject(renderer())->offsetForInFlowPosition();
    1190         positionOrOffsetChanged = newOffset != m_offsetForInFlowPosition;
    1191         m_offsetForInFlowPosition = newOffset;
    1192         localPoint.move(m_offsetForInFlowPosition);
     1188    if (renderer()->hasPaintOffset()) {
     1189        LayoutSize newOffset = toRenderBoxModelObject(renderer())->paintOffset();
     1190        positionOrOffsetChanged = newOffset != m_paintOffset;
     1191        m_paintOffset = newOffset;
     1192        localPoint.move(m_paintOffset);
    11931193    } else {
    1194         m_offsetForInFlowPosition = LayoutSize();
     1194        m_paintOffset = LayoutSize();
    11951195    }
    11961196
     
    46004600        clipRects.setOverflowClipRect(clipRects.fixedClipRect());
    46014601        clipRects.setFixed(true);
    4602     } else if (renderer()->style()->hasInFlowPosition())
     4602    } else if (renderer()->style()->hasPaintOffset())
    46034603        clipRects.setPosClipRect(clipRects.overflowClipRect());
    46044604    else if (renderer()->style()->position() == AbsolutePosition)
  • trunk/Source/WebCore/rendering/RenderLayer.h

    r142057 r142527  
    426426#endif
    427427
    428     const LayoutSize& offsetForInFlowPosition() const { return m_offsetForInFlowPosition; }
     428    const LayoutSize& paintOffset() const { return m_paintOffset; }
    429429
    430430    void clearClipRectsIncludingDescendants(ClipRectsType typeToClear = AllClipRectTypes);
     
    11251125    LayoutRect m_outlineBox;
    11261126
    1127     // Our current relative position offset.
    1128     LayoutSize m_offsetForInFlowPosition;
     1127    // Paint time offset only, it is used for properly paint relative / sticky positioned elements and exclusion boxes on floats.
     1128    LayoutSize m_paintOffset;
    11291129
    11301130    // Our (x,y) coordinates are in our parent layer's coordinate space.
  • trunk/Source/WebCore/rendering/RenderObject.h

    r142056 r142527  
    526526    bool isOutOfFlowPositioned() const { return m_bitfields.isOutOfFlowPositioned(); } // absolute or fixed positioning
    527527    bool isInFlowPositioned() const { return m_bitfields.isRelPositioned() || m_bitfields.isStickyPositioned(); } // relative or sticky positioning
     528    bool hasPaintOffset() const
     529    {
     530        bool positioned = isInFlowPositioned();
     531#if ENABLE(CSS_EXCLUSIONS)
     532        // Shape outside on a float can reposition the float in much the
     533        // same way as relative positioning, so treat it as such.
     534        positioned = positioned || (m_bitfields.floating() && m_bitfields.isBox() && style()->shapeOutside());
     535#endif
     536        return positioned;
     537    }
    528538    bool isRelPositioned() const { return m_bitfields.isRelPositioned(); } // relative positioning
    529539    bool isStickyPositioned() const { return m_bitfields.isStickyPositioned(); }
  • trunk/Source/WebCore/rendering/style/RenderStyle.h

    r142404 r142527  
    461461    bool hasOutOfFlowPosition() const { return position() == AbsolutePosition || position() == FixedPosition; }
    462462    bool hasInFlowPosition() const { return position() == RelativePosition || position() == StickyPosition; }
     463    bool hasPaintOffset() const
     464    {
     465        bool paintOffset = hasInFlowPosition();
     466#if ENABLE(CSS_EXCLUSIONS)
     467        paintOffset = paintOffset || (isFloating() && shapeOutside());
     468#endif
     469        return paintOffset;
     470    }
    463471    bool hasViewportConstrainedPosition() const { return position() == FixedPosition || position() == StickyPosition; }
    464472    EFloat floating() const { return static_cast<EFloat>(noninherited_flags._floating); }
Note: See TracChangeset for help on using the changeset viewer.