Chromium Code Reviews| Index: third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp |
| diff --git a/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp b/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp |
| index 486a11a43eb50a95648e8c40706d57d7d6d7f796..47c1d6628e832c8ab559a123699578321c0a54e5 100644 |
| --- a/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp |
| +++ b/third_party/WebKit/Source/core/layout/LayoutBoxModelObject.cpp |
| @@ -873,6 +873,38 @@ void LayoutBoxModelObject::updateStickyPositionConstraints() const { |
| toFloatSize(stickyLocation), |
| flippedStickyBoxRect.size())); |
| + // To correctly compute the offsets, the constraints need to know about any |
| + // nested position:sticky between themselves and their containingBlock, and |
| + // between the containingBlock and their scrollAncestor. |
| + // |
| + // The respective search ranges are [parent(), containingBlock) and |
| + // [containingBlock, scrollAncestor). |
| + |
| + // TODO(smcgruer): Fold these into the walks to find the containingBlock and |
| + // scrollAncestor. |
| + |
| + LayoutObject* maybeStickyAncestor = parent(); |
| + while (maybeStickyAncestor && maybeStickyAncestor != containingBlock) { |
| + if (maybeStickyAncestor->isStickyPositioned()) { |
| + constraints.setNearestStickyElementToContainingBlock( |
| + toLayoutBoxModelObject(maybeStickyAncestor)); |
| + break; |
| + } |
| + maybeStickyAncestor = maybeStickyAncestor->parent(); |
| + } |
| + |
| + if (scrollAncestor) { |
|
flackr
2017/01/20 02:42:44
nullptr scrollAncestor just means the scroll ances
smcgruer
2017/01/20 17:18:14
So I'm clear, we need to do something like:
L
flackr
2017/01/23 16:45:42
Yes, that would work, but probably simpler to use
smcgruer
2017/01/24 18:38:25
Done.
|
| + maybeStickyAncestor = containingBlock; |
| + while (maybeStickyAncestor && maybeStickyAncestor != scrollAncestor) { |
| + if (maybeStickyAncestor->isStickyPositioned()) { |
| + constraints.setNearestStickyElementFromContainingBlockToScrollContainer( |
| + toLayoutBoxModelObject(maybeStickyAncestor)); |
| + break; |
| + } |
| + maybeStickyAncestor = maybeStickyAncestor->parent(); |
| + } |
| + } |
| + |
| // We skip the right or top sticky offset if there is not enough space to |
| // honor both the left/right or top/bottom offsets. |
| LayoutUnit horizontalOffsets = |
| @@ -976,9 +1008,36 @@ LayoutSize LayoutBoxModelObject::stickyPositionOffset() const { |
| // compositing inputs. |
| if (!scrollableArea->stickyConstraintsMap().contains(layer())) |
| return LayoutSize(); |
| - return LayoutSize( |
| - scrollableArea->stickyConstraintsMap().get(layer()).computeStickyOffset( |
| - constrainingRect)); |
| + |
| + auto it = scrollableArea->stickyConstraintsMap().find(layer()); |
| + DCHECK(it != scrollableArea->stickyConstraintsMap().end()); |
|
flackr
2017/01/20 02:42:44
Please merge this with the check on 1009 above so
smcgruer
2017/01/24 18:38:25
Done in PS4 (missed this comment.)
|
| + |
| + StickyPositionScrollingConstraints& constraints = it->value; |
| + |
| + FloatSize accumulatedOffsetToContainingBlock; |
| + FloatSize accumulatedOffsetToScrollContainer; |
| + |
| + const LayoutBoxModelObject* toContainingBlock = |
| + constraints.nearestStickyElementToContainingBlock(); |
| + if (toContainingBlock) { |
| + accumulatedOffsetToContainingBlock = |
| + scrollableArea->stickyConstraintsMap() |
| + .get(toContainingBlock->layer()) |
| + .getAccumulatedStickyOffsetToContainingBlock(); |
| + } |
| + |
| + const LayoutBoxModelObject* toViewport = |
| + constraints.nearestStickyElementFromContainingBlockToScrollContainer(); |
| + if (toViewport) { |
| + accumulatedOffsetToScrollContainer = |
| + scrollableArea->stickyConstraintsMap() |
| + .get(toViewport->layer()) |
| + .getAccumulatedStickyOffsetFromContainingBlockToScrollContainer(); |
| + } |
| + |
| + return LayoutSize(constraints.computeStickyOffset( |
| + constrainingRect, accumulatedOffsetToContainingBlock, |
| + accumulatedOffsetToScrollContainer)); |
| } |
| LayoutPoint LayoutBoxModelObject::adjustedPositionRelativeTo( |