Changeset 246869 in webkit


Ignore:
Timestamp:
Jun 26, 2019 9:13:15 PM (5 years ago)
Author:
Simon Fraser
Message:

[Async overflow scrolling] Fix missing or misplaced content inside overflow:scroll
https://bugs.webkit.org/show_bug.cgi?id=199253
Source/WebCore:

rdar://problem/51855156, rdar://problem/51934514

Reviewed by Zalan Bujtas.

This patch fixes a couple of related issues triggered by failing to composite layers inside non-stacking-context
overflow scroll.

First, we relied on overlap testing to composite position:relative layers inside overflow:scroll, but this only
worked when they came later in z-order, so didn't work for layers with negative z-index.
RenderLayerCompositor::requiresCompositingForIndirectReason() was intended to trigger compositing in such cases,
but it only did so for position:absolute inside stacking-context scroller, because
isNonScrolledLayerInsideScrolledCompositedAncestor() tested ancestorMovedByScroller && !layerMovedByScroller.

I fixed this by sharing code between the three places that ask whether compositing crosses a containing-block
boundary to call a single function, RenderLayerCompositor::layerScrollBehahaviorRelativeToCompositedAncestor(),
that returns a ScrollPositioningBehavior. We now do compositing for both "moves" and "stationary" behaviors (but
not "none"), ensuring that position:relative inside non-stacking scroller is always composited.

However, this would trigger compositing on layers that should be using backing sharing; if they were outside the
visible part of the scroller, the overlap code would not trigger, but the
"IndirectCompositingReason::OverflowScrollPositioning" code would. This is undesirable; any layer that can use
backing sharing should, because that's fewer composited layers, so smaller layer trees and less backing store.
To fix this, I moved the backing-sharing check before the overlap check in
RenderLayerCompositor::computeCompositingRequirements().

The "layer.setHasCompositingDescendant(currentState.subtreeIsCompositing)" line was in the wrong place,
triggering assertions on some content; "subtreeIsCompositing" only refers to child layers, so this bit needs to
be set right after we've traversed the z-order lists.

Tests: compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller.html

compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller.html
compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller.html

  • rendering/RenderLayerCompositor.cpp:

(WebCore::RenderLayerCompositor::computeCompositingRequirements):
(WebCore::RenderLayerCompositor::traverseUnchangedSubtree):
(WebCore::RenderLayerCompositor::requiresCompositingForIndirectReason const):
(WebCore::isScrolledByOverflowScrollLayer):
(WebCore::enclosingCompositedScrollingLayer):
(WebCore::RenderLayerCompositor::layerScrollBehahaviorRelativeToCompositedAncestor):
(WebCore::RenderLayerCompositor::computeCoordinatedPositioningForLayer const):
(WebCore::isNonScrolledLayerInsideScrolledCompositedAncestor): Deleted.
(WebCore::RenderLayerCompositor::layerContainingBlockCrossesCoordinatedScrollingBoundary): Deleted.

  • rendering/RenderLayerCompositor.h:

LayoutTests:

Reviewed by Zalan Bujtas.

  • compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt:
  • compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt:
  • compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt:
  • compositing/rtl/rtl-scrolling-with-transformed-descendants-expected.txt:
  • compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller-expected.html: Added.
  • compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller.html: Added.
  • compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller-expected.txt: Added.
  • compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller.html: Added.
  • compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller-expected.html: Added.
  • compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller.html: Added.
  • compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt:
  • platform/ios-wk2/compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt:
  • platform/ios-wk2/compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt:
  • platform/ios-wk2/compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller-expected.txt: Added.
  • platform/ios-wk2/compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt:
  • platform/ios/compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt:
Location:
trunk
Files:
7 added
13 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r246868 r246869  
     12019-06-26  Simon Fraser  <simon.fraser@apple.com>
     2
     3        [Async overflow scrolling] Fix missing or misplaced content inside overflow:scroll
     4        https://bugs.webkit.org/show_bug.cgi?id=199253
     5
     6        Reviewed by Zalan Bujtas.
     7
     8        * compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt:
     9        * compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt:
     10        * compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt:
     11        * compositing/rtl/rtl-scrolling-with-transformed-descendants-expected.txt:
     12        * compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller-expected.html: Added.
     13        * compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller.html: Added.
     14        * compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller-expected.txt: Added.
     15        * compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller.html: Added.
     16        * compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller-expected.html: Added.
     17        * compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller.html: Added.
     18        * compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt:
     19        * platform/ios-wk2/compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt:
     20        * platform/ios-wk2/compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt:
     21        * platform/ios-wk2/compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller-expected.txt: Added.
     22        * platform/ios-wk2/compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt:
     23        * platform/ios/compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt:
     24
    1252019-06-26  Ryosuke Niwa  <rniwa@webkit.org>
    226
  • trunk/LayoutTests/compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt

    r246725 r246869  
    2828            (GraphicsLayer
    2929              (offsetFromRenderer width=0 height=100)
    30               (bounds 149.00 200.00)
     30              (bounds 149.00 2086.00)
     31              (usingTiledLayer 1)
    3132              (drawsContent 1)
    3233            )
  • trunk/LayoutTests/compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt

    r246725 r246869  
    66      (bounds 800.00 600.00)
    77      (contentsOpaque 1)
    8       (children 5
     8      (children 6
    99        (GraphicsLayer
    1010          (position 8.00 8.00)
     
    7070          )
    7171        )
     72        (GraphicsLayer
     73          (position 9.00 9.00)
     74          (bounds 285.00 300.00)
     75          (children 1
     76            (GraphicsLayer
     77              (position 40.00 380.00)
     78              (bounds 100.00 100.00)
     79              (contentsOpaque 1)
     80            )
     81          )
     82        )
    7283      )
    7384    )
  • trunk/LayoutTests/compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt

    r246725 r246869  
    66      (bounds 800.00 600.00)
    77      (contentsOpaque 1)
    8       (children 4
     8      (children 1
    99        (GraphicsLayer
    10           (position 8.00 8.00)
    11           (bounds 302.00 302.00)
     10          (bounds 800.00 600.00)
    1211          (drawsContent 1)
    13           (children 1
     12          (children 7
    1413            (GraphicsLayer
    15               (offsetFromRenderer width=1 height=1)
    16               (position 1.00 1.00)
     14              (position 9.00 9.00)
    1715              (bounds 285.00 300.00)
    1816              (children 1
    1917                (GraphicsLayer
    20                   (offsetFromRenderer width=1 height=1)
    21                   (anchor 0.00 0.00)
    22                   (bounds 285.00 500.00)
     18                  (position 40.00 140.00)
     19                  (bounds 100.00 100.00)
     20                  (contentsOpaque 1)
    2321                )
    2422              )
    2523            )
    26           )
    27         )
    28         (GraphicsLayer
    29           (position 9.00 9.00)
    30           (bounds 285.00 300.00)
    31           (children 1
    3224            (GraphicsLayer
    33               (position 10.00 10.00)
    34               (bounds 50.00 200.00)
    35               (contentsOpaque 1)
     25              (bounds 800.00 600.00)
     26              (drawsContent 1)
    3627            )
    37           )
    38         )
    39         (GraphicsLayer
    40           (position 9.00 9.00)
    41           (bounds 285.00 300.00)
    42           (children 1
    4328            (GraphicsLayer
    44               (position 40.00 20.00)
    45               (bounds 100.00 100.00)
    46               (contentsOpaque 1)
     29              (position 8.00 8.00)
     30              (bounds 302.00 302.00)
     31              (drawsContent 1)
     32              (children 1
     33                (GraphicsLayer
     34                  (offsetFromRenderer width=1 height=1)
     35                  (position 1.00 1.00)
     36                  (bounds 285.00 300.00)
     37                  (children 1
     38                    (GraphicsLayer
     39                      (offsetFromRenderer width=1 height=1)
     40                      (anchor 0.00 0.00)
     41                      (bounds 285.00 500.00)
     42                    )
     43                  )
     44                )
     45              )
    4746            )
    48           )
    49         )
    50         (GraphicsLayer
    51           (position 9.00 9.00)
    52           (bounds 285.00 300.00)
    53           (children 1
    5447            (GraphicsLayer
    55               (position 40.00 260.00)
    56               (bounds 100.00 100.00)
    57               (contentsOpaque 1)
     48              (position 9.00 9.00)
     49              (bounds 285.00 300.00)
     50              (children 1
     51                (GraphicsLayer
     52                  (position 10.00 10.00)
     53                  (bounds 50.00 200.00)
     54                  (contentsOpaque 1)
     55                )
     56              )
     57            )
     58            (GraphicsLayer
     59              (position 9.00 9.00)
     60              (bounds 285.00 300.00)
     61              (children 1
     62                (GraphicsLayer
     63                  (position 40.00 20.00)
     64                  (bounds 100.00 100.00)
     65                  (contentsOpaque 1)
     66                )
     67              )
     68            )
     69            (GraphicsLayer
     70              (position 9.00 9.00)
     71              (bounds 285.00 300.00)
     72              (children 1
     73                (GraphicsLayer
     74                  (position 40.00 260.00)
     75                  (bounds 100.00 100.00)
     76                  (contentsOpaque 1)
     77                )
     78              )
     79            )
     80            (GraphicsLayer
     81              (position 9.00 9.00)
     82              (bounds 285.00 300.00)
     83              (children 1
     84                (GraphicsLayer
     85                  (position 40.00 380.00)
     86                  (bounds 100.00 100.00)
     87                  (contentsOpaque 1)
     88                )
     89              )
    5890            )
    5991          )
  • trunk/LayoutTests/compositing/rtl/rtl-scrolling-with-transformed-descendants-expected.txt

    r246725 r246869  
    88      (bounds 800.00 600.00)
    99      (contentsOpaque 1)
    10       (children 3
     10      (children 5
    1111        (GraphicsLayer
    1212          (position 8.00 8.00)
     
    5959          )
    6060        )
     61        (GraphicsLayer
     62          (position 10.00 10.00)
     63          (bounds origin 366.00 0.00)
     64          (bounds 400.00 204.00)
     65          (clips 1)
     66          (children 1
     67            (GraphicsLayer
     68              (position 154.00 0.00)
     69              (bounds 150.00 200.00)
     70              (contentsOpaque 1)
     71            )
     72          )
     73        )
     74        (GraphicsLayer
     75          (position 10.00 10.00)
     76          (bounds origin 366.00 0.00)
     77          (bounds 400.00 204.00)
     78          (clips 1)
     79          (children 1
     80            (GraphicsLayer
     81              (bounds 150.00 200.00)
     82              (contentsOpaque 1)
     83            )
     84          )
     85        )
    6186      )
    6287    )
  • trunk/LayoutTests/compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt

    r245170 r246869  
    2929                      (contentsOpaque 1)
    3030                      (drawsContent 1)
    31                       (children 1
    32                         (GraphicsLayer
    33                           (bounds 140.00 140.00)
    34                         )
    35                       )
    3631                    )
    3732                  )
  • trunk/LayoutTests/platform/ios-wk2/compositing/layer-creation/clipping-scope/overlap-constrained-inside-scroller-expected.txt

    r246725 r246869  
    66      (bounds 800.00 600.00)
    77      (contentsOpaque 1)
    8       (children 5
     8      (children 6
    99        (GraphicsLayer
    1010          (position 8.00 8.00)
     
    7070          )
    7171        )
     72        (GraphicsLayer
     73          (position 9.00 9.00)
     74          (bounds 300.00 300.00)
     75          (children 1
     76            (GraphicsLayer
     77              (position 40.00 380.00)
     78              (bounds 100.00 100.00)
     79              (contentsOpaque 1)
     80            )
     81          )
     82        )
    7283      )
    7384    )
  • trunk/LayoutTests/platform/ios-wk2/compositing/layer-creation/clipping-scope/scroller-with-negative-z-children-expected.txt

    r246725 r246869  
    66      (bounds 800.00 600.00)
    77      (contentsOpaque 1)
    8       (children 4
     8      (children 1
    99        (GraphicsLayer
    10           (position 8.00 8.00)
    11           (bounds 302.00 302.00)
     10          (bounds 800.00 600.00)
    1211          (drawsContent 1)
    13           (children 1
     12          (children 7
    1413            (GraphicsLayer
    15               (offsetFromRenderer width=1 height=1)
    16               (position 1.00 1.00)
     14              (position 9.00 9.00)
    1715              (bounds 300.00 300.00)
    1816              (children 1
    1917                (GraphicsLayer
    20                   (offsetFromRenderer width=1 height=1)
    21                   (anchor 0.00 0.00)
    22                   (bounds 300.00 500.00)
     18                  (position 40.00 140.00)
     19                  (bounds 100.00 100.00)
     20                  (contentsOpaque 1)
    2321                )
    2422              )
    2523            )
    26           )
    27         )
    28         (GraphicsLayer
    29           (position 9.00 9.00)
    30           (bounds 300.00 300.00)
    31           (children 1
    3224            (GraphicsLayer
    33               (position 10.00 10.00)
    34               (bounds 50.00 200.00)
    35               (contentsOpaque 1)
     25              (bounds 800.00 600.00)
     26              (drawsContent 1)
    3627            )
    37           )
    38         )
    39         (GraphicsLayer
    40           (position 9.00 9.00)
    41           (bounds 300.00 300.00)
    42           (children 1
    4328            (GraphicsLayer
    44               (position 40.00 20.00)
    45               (bounds 100.00 100.00)
    46               (contentsOpaque 1)
     29              (position 8.00 8.00)
     30              (bounds 302.00 302.00)
     31              (drawsContent 1)
     32              (children 1
     33                (GraphicsLayer
     34                  (offsetFromRenderer width=1 height=1)
     35                  (position 1.00 1.00)
     36                  (bounds 300.00 300.00)
     37                  (children 1
     38                    (GraphicsLayer
     39                      (offsetFromRenderer width=1 height=1)
     40                      (anchor 0.00 0.00)
     41                      (bounds 300.00 500.00)
     42                    )
     43                  )
     44                )
     45              )
    4746            )
    48           )
    49         )
    50         (GraphicsLayer
    51           (position 9.00 9.00)
    52           (bounds 300.00 300.00)
    53           (children 1
    5447            (GraphicsLayer
    55               (position 40.00 260.00)
    56               (bounds 100.00 100.00)
    57               (contentsOpaque 1)
     48              (position 9.00 9.00)
     49              (bounds 300.00 300.00)
     50              (children 1
     51                (GraphicsLayer
     52                  (position 10.00 10.00)
     53                  (bounds 50.00 200.00)
     54                  (contentsOpaque 1)
     55                )
     56              )
     57            )
     58            (GraphicsLayer
     59              (position 9.00 9.00)
     60              (bounds 300.00 300.00)
     61              (children 1
     62                (GraphicsLayer
     63                  (position 40.00 20.00)
     64                  (bounds 100.00 100.00)
     65                  (contentsOpaque 1)
     66                )
     67              )
     68            )
     69            (GraphicsLayer
     70              (position 9.00 9.00)
     71              (bounds 300.00 300.00)
     72              (children 1
     73                (GraphicsLayer
     74                  (position 40.00 260.00)
     75                  (bounds 100.00 100.00)
     76                  (contentsOpaque 1)
     77                )
     78              )
     79            )
     80            (GraphicsLayer
     81              (position 9.00 9.00)
     82              (bounds 300.00 300.00)
     83              (children 1
     84                (GraphicsLayer
     85                  (position 40.00 380.00)
     86                  (bounds 100.00 100.00)
     87                  (contentsOpaque 1)
     88                )
     89              )
    5890            )
    5991          )
  • trunk/LayoutTests/platform/ios-wk2/compositing/shared-backing/overflow-scroll/nested-absolute-with-clipping-in-stacking-overflow-expected.txt

    r245170 r246869  
    2929                      (contentsOpaque 1)
    3030                      (drawsContent 1)
    31                       (children 1
    32                         (GraphicsLayer
    33                           (bounds 140.00 140.00)
    34                         )
    35                       )
    3631                    )
    3732                  )
  • trunk/LayoutTests/platform/ios/compositing/geometry/limit-layer-bounds-clipping-ancestor-expected.txt

    r246725 r246869  
    2828            (GraphicsLayer
    2929              (offsetFromRenderer width=0 height=100)
    30               (bounds 149.00 200.00)
     30              (bounds 149.00 2086.00)
     31              (usingTiledLayer 1)
    3132              (drawsContent 1)
    3233            )
  • trunk/Source/WebCore/ChangeLog

    r246868 r246869  
     12019-06-26  Simon Fraser  <simon.fraser@apple.com>
     2
     3        [Async overflow scrolling] Fix missing or misplaced content inside overflow:scroll
     4        https://bugs.webkit.org/show_bug.cgi?id=199253
     5        rdar://problem/51855156, rdar://problem/51934514
     6
     7        Reviewed by Zalan Bujtas.
     8
     9        This patch fixes a couple of related issues triggered by failing to composite layers inside non-stacking-context
     10        overflow scroll.
     11
     12        First, we relied on overlap testing to composite position:relative layers inside overflow:scroll, but this only
     13        worked when they came later in z-order, so didn't work for layers with negative z-index.
     14        RenderLayerCompositor::requiresCompositingForIndirectReason() was intended to trigger compositing in such cases,
     15        but it only did so for position:absolute inside stacking-context scroller, because
     16        isNonScrolledLayerInsideScrolledCompositedAncestor() tested ancestorMovedByScroller && !layerMovedByScroller.
     17
     18        I fixed this by sharing code between the three places that ask whether compositing crosses a containing-block
     19        boundary to call a single function, RenderLayerCompositor::layerScrollBehahaviorRelativeToCompositedAncestor(),
     20        that returns a ScrollPositioningBehavior. We now do compositing for both "moves" and "stationary" behaviors (but
     21        not "none"), ensuring that position:relative inside non-stacking scroller is always composited.
     22
     23        However, this would trigger compositing on layers that should be using backing sharing; if they were outside the
     24        visible part of the scroller, the overlap code would not trigger, but the
     25        "IndirectCompositingReason::OverflowScrollPositioning" code would. This is undesirable; any layer that can use
     26        backing sharing should, because that's fewer composited layers, so smaller layer trees and less backing store.
     27        To fix this, I moved the backing-sharing check before the overlap check in
     28        RenderLayerCompositor::computeCompositingRequirements().
     29
     30        The "layer.setHasCompositingDescendant(currentState.subtreeIsCompositing)" line was in the wrong place,
     31        triggering assertions on some content; "subtreeIsCompositing" only refers to child layers, so this bit needs to
     32        be set right after we've traversed the z-order lists.
     33
     34        Tests: compositing/scrolling/async-overflow-scrolling/hidden-relative-layer-content-in-scroller.html
     35               compositing/scrolling/async-overflow-scrolling/layer-for-negative-z-in-scroller.html
     36               compositing/scrolling/async-overflow-scrolling/negative-z-in-scroller.html
     37
     38        * rendering/RenderLayerCompositor.cpp:
     39        (WebCore::RenderLayerCompositor::computeCompositingRequirements):
     40        (WebCore::RenderLayerCompositor::traverseUnchangedSubtree):
     41        (WebCore::RenderLayerCompositor::requiresCompositingForIndirectReason const):
     42        (WebCore::isScrolledByOverflowScrollLayer):
     43        (WebCore::enclosingCompositedScrollingLayer):
     44        (WebCore::RenderLayerCompositor::layerScrollBehahaviorRelativeToCompositedAncestor):
     45        (WebCore::RenderLayerCompositor::computeCoordinatedPositioningForLayer const):
     46        (WebCore::isNonScrolledLayerInsideScrolledCompositedAncestor): Deleted.
     47        (WebCore::RenderLayerCompositor::layerContainingBlockCrossesCoordinatedScrollingBoundary): Deleted.
     48        * rendering/RenderLayerCompositor.h:
     49
    1502019-06-26  Ryosuke Niwa  <rniwa@webkit.org>
    251
  • trunk/Source/WebCore/rendering/RenderLayerCompositor.cpp

    r246725 r246869  
    864864    bool willBeComposited = layer.isComposited();
    865865    bool becameCompositedAfterDescendantTraversal = false;
     866    IndirectCompositingReason compositingReason = compositingState.subtreeIsCompositing ? IndirectCompositingReason::Stacking : IndirectCompositingReason::None;
    866867
    867868    if (layer.needsPostLayoutCompositingUpdate() || compositingState.fullPaintOrderTraversalRequired || compositingState.descendantsRequireCompositingUpdate) {
    868869        layer.setIndirectCompositingReason(IndirectCompositingReason::None);
    869870        willBeComposited = needsToBeComposited(layer, queryData);
     871    }
     872
     873    bool layerPaintsIntoProvidedBacking = false;
     874    if (!willBeComposited && compositingState.subtreeIsCompositing && backingSharingState.backingProviderCandidate() && canBeComposited(layer) && backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate(), layer)) {
     875        backingSharingState.appendSharingLayer(layer);
     876        LOG(Compositing, " layer %p can share with %p", &layer, backingSharingState.backingProviderCandidate());
     877        compositingReason = IndirectCompositingReason::None;
     878        layerPaintsIntoProvidedBacking = true;
    870879    }
    871880
     
    881890    overlapMap.geometryMap().pushMappingsToAncestor(&layer, ancestorLayer, respectTransforms);
    882891
    883     IndirectCompositingReason compositingReason = compositingState.subtreeIsCompositing ? IndirectCompositingReason::Stacking : IndirectCompositingReason::None;
    884     bool layerPaintsIntoProvidedBacking = false;
    885     bool didPushOverlapContainer = false;
    886 
    887892    // If we know for sure the layer is going to be composited, don't bother looking it up in the overlap map
    888     if (!willBeComposited && !overlapMap.isEmpty() && compositingState.testingOverlap) {
     893    if (!willBeComposited && !layerPaintsIntoProvidedBacking && !overlapMap.isEmpty() && compositingState.testingOverlap) {
    889894        // If we're testing for overlap, we only need to composite if we overlap something that is already composited.
    890         if (layerOverlaps(overlapMap, layer, layerExtent)) {
    891             if (backingSharingState.backingProviderCandidate() && canBeComposited(layer) && backingProviderLayerCanIncludeLayer(*backingSharingState.backingProviderCandidate(), layer)) {
    892                 backingSharingState.appendSharingLayer(layer);
    893                 LOG(Compositing, " layer %p can share with %p", &layer, backingSharingState.backingProviderCandidate());
    894                 compositingReason = IndirectCompositingReason::None;
    895                 layerPaintsIntoProvidedBacking = true;
    896             } else
    897                 compositingReason = IndirectCompositingReason::Overlap;
    898         } else
     895        if (layerOverlaps(overlapMap, layer, layerExtent))
     896            compositingReason = IndirectCompositingReason::Overlap;
     897        else
    899898            compositingReason = IndirectCompositingReason::None;
    900899    }
     
    923922    // ancestor with subtreeIsCompositing set to false.
    924923    CompositingState currentState = compositingState.stateForPaintOrderChildren(layer);
     924    bool didPushOverlapContainer = false;
    925925
    926926    auto layerWillComposite = [&] {
     
    994994        computeCompositingRequirements(&layer, *childLayer, overlapMap, currentState, backingSharingState, anyDescendantHas3DTransform);
    995995
     996    // Set the flag to say that this layer has compositing children.
     997    layer.setHasCompositingDescendant(currentState.subtreeIsCompositing);
     998
    996999    // If we just entered compositing mode, the root will have become composited (as long as accelerated compositing is enabled).
    9971000    if (layer.isRenderViewLayer()) {
     
    10221025        layer.reflectionLayer()->setIndirectCompositingReason(willBeComposited ? IndirectCompositingReason::Stacking : IndirectCompositingReason::None);
    10231026    }
    1024 
    1025     // Set the flag to say that this layer has compositing children.
    1026     layer.setHasCompositingDescendant(currentState.subtreeIsCompositing);
    10271027
    10281028    // setHasCompositingDescendant() may have changed the answer to needsToBeComposited() when clipping, so test that now.
     
    11511151            ASSERT(layerIsComposited);
    11521152    }
    1153    
     1153
    11541154    for (auto* childLayer : layer.normalFlowLayers())
    11551155        traverseUnchangedSubtree(&layer, *childLayer, overlapMap, currentState, backingSharingState, anyDescendantHas3DTransform);
     
    29932993}
    29942994
    2995 static RenderLayer* enclosingCompositedScrollingLayer(const RenderLayer& layer, const RenderLayer& intermediateLayer, bool& sawIntermediateLayer)
    2996 {
    2997     const auto* ancestorLayer = layer.parent();
    2998     while (ancestorLayer) {
    2999         if (ancestorLayer == &intermediateLayer)
    3000             sawIntermediateLayer = true;
    3001 
    3002         if (ancestorLayer->hasCompositedScrollableOverflow())
    3003             return const_cast<RenderLayer*>(ancestorLayer);
    3004 
    3005         ancestorLayer = ancestorLayer->parent();
    3006     }
    3007 
    3008     return nullptr;
    3009 }
    3010 
    3011 static bool isScrolledByOverflowScrollLayer(const RenderLayer& layer, const RenderLayer& overflowScrollLayer)
    3012 {
    3013     bool scrolledByOverflowScroll = false;
    3014     traverseAncestorLayers(layer, [&](const RenderLayer& ancestorLayer, bool inContainingBlockChain, bool) {
    3015         if (&ancestorLayer == &overflowScrollLayer) {
    3016             scrolledByOverflowScroll = inContainingBlockChain;
    3017             return AncestorTraversal::Stop;
    3018         }
    3019         return AncestorTraversal::Continue;
    3020     });
    3021     return scrolledByOverflowScroll;
    3022 }
    3023 
    3024 static bool isNonScrolledLayerInsideScrolledCompositedAncestor(const RenderLayer& layer, const RenderLayer& compositedAncestor, const RenderLayer& scrollingAncestor)
    3025 {
    3026     bool ancestorMovedByScroller = &compositedAncestor == &scrollingAncestor || isScrolledByOverflowScrollLayer(compositedAncestor, scrollingAncestor);
    3027     bool layerMovedByScroller = isScrolledByOverflowScrollLayer(layer, scrollingAncestor);
    3028 
    3029     return ancestorMovedByScroller && !layerMovedByScroller;
    3030 }
    3031 
    30322995// FIXME: why doesn't this handle the clipping cases?
    30332996bool RenderLayerCompositor::requiresCompositingForIndirectReason(const RenderLayer& layer, bool hasCompositedDescendants, bool has3DTransformedDescendants, bool paintsIntoProvidedBacking, IndirectCompositingReason& reason) const
     
    30583021    if (!paintsIntoProvidedBacking && layer.hasCompositedScrollingAncestor()) {
    30593022        auto* paintDestination = layer.paintOrderParent();
    3060         bool paintDestinationIsScrolling = false;
    3061         auto* scrollingAncestor = enclosingCompositedScrollingLayer(layer, *paintDestination, paintDestinationIsScrolling);
    3062         if (isNonScrolledLayerInsideScrolledCompositedAncestor(layer, *paintDestination, *scrollingAncestor)) {
     3023        if (paintDestination && layerScrollBehahaviorRelativeToCompositedAncestor(layer, *paintDestination) != ScrollPositioningBehavior::None) {
    30633024            reason = IndirectCompositingReason::OverflowScrollPositioning;
    30643025            return true;
     
    31653126}
    31663127
    3167 bool RenderLayerCompositor::layerContainingBlockCrossesCoordinatedScrollingBoundary(const RenderLayer& layer, const RenderLayer& compositedAncestor)
    3168 {
     3128static bool isScrolledByOverflowScrollLayer(const RenderLayer& layer, const RenderLayer& overflowScrollLayer)
     3129{
     3130    bool scrolledByOverflowScroll = false;
     3131    traverseAncestorLayers(layer, [&](const RenderLayer& ancestorLayer, bool inContainingBlockChain, bool) {
     3132        if (&ancestorLayer == &overflowScrollLayer) {
     3133            scrolledByOverflowScroll = inContainingBlockChain;
     3134            return AncestorTraversal::Stop;
     3135        }
     3136        return AncestorTraversal::Continue;
     3137    });
     3138    return scrolledByOverflowScroll;
     3139}
     3140
     3141static RenderLayer* enclosingCompositedScrollingLayer(const RenderLayer& layer, const RenderLayer& intermediateLayer, bool& sawIntermediateLayer)
     3142{
     3143    const auto* ancestorLayer = layer.parent();
     3144    while (ancestorLayer) {
     3145        if (ancestorLayer == &intermediateLayer)
     3146            sawIntermediateLayer = true;
     3147
     3148        if (ancestorLayer->hasCompositedScrollableOverflow())
     3149            return const_cast<RenderLayer*>(ancestorLayer);
     3150
     3151        ancestorLayer = ancestorLayer->parent();
     3152    }
     3153
     3154    return nullptr;
     3155}
     3156
     3157ScrollPositioningBehavior RenderLayerCompositor::layerScrollBehahaviorRelativeToCompositedAncestor(const RenderLayer& layer, const RenderLayer& compositedAncestor)
     3158{
     3159    if (!layer.hasCompositedScrollingAncestor())
     3160        return ScrollPositioningBehavior::None;
     3161
    31693162    bool compositedAncestorIsInsideScroller = false;
    31703163    auto* scrollingAncestor = enclosingCompositedScrollingLayer(layer, compositedAncestor, compositedAncestorIsInsideScroller);
    31713164    if (!scrollingAncestor) {
    31723165        ASSERT_NOT_REACHED(); // layer.hasCompositedScrollingAncestor() should guarantee we have one.
    3173         return false;
     3166        return ScrollPositioningBehavior::None;
    31743167    }
    31753168   
    3176     if (!compositedAncestorIsInsideScroller)
    3177         return false;
    3178 
    3179     return isNonScrolledLayerInsideScrolledCompositedAncestor(layer, compositedAncestor, *scrollingAncestor);
     3169    bool ancestorMovedByScroller = &compositedAncestor == scrollingAncestor || (compositedAncestorIsInsideScroller && isScrolledByOverflowScrollLayer(compositedAncestor, *scrollingAncestor));
     3170    bool layerMovedByScroller = isScrolledByOverflowScrollLayer(layer, *scrollingAncestor);
     3171
     3172    if (ancestorMovedByScroller == layerMovedByScroller)
     3173        return ScrollPositioningBehavior::None;
     3174
     3175    return layerMovedByScroller ? ScrollPositioningBehavior::Moves : ScrollPositioningBehavior::Stationary;
    31803176}
    31813177
     
    32283224    }
    32293225
    3230     bool compositedAncestorIsScrolling = false;
    3231     auto* scrollingAncestor = enclosingCompositedScrollingLayer(layer, *compositedAncestor, compositedAncestorIsScrolling);
    3232     if (!scrollingAncestor) {
    3233         ASSERT_NOT_REACHED(); // layer.hasCompositedScrollingAncestor() should guarantee we have one.
    3234         return ScrollPositioningBehavior::None;
    3235     }
    3236 
    3237     // There are two cases we have to deal with here:
    3238     // 1. There's a composited overflow:scroll in the parent chain between the renderer and its containing block, and the layer's
    3239     //    composited (z-order) ancestor is inside the scroller or is the scroller. In this case, we have to compensate for scroll position
    3240     //    changes to make the positioned layer stay in the same place. This only applies to position:absolute or descendants of position:absolute.
    3241     if (compositedAncestorIsScrolling && isNonScrolledLayerInsideScrolledCompositedAncestor(layer, *compositedAncestor, *scrollingAncestor))
    3242         return ScrollPositioningBehavior::Stationary;
    3243 
    3244     // 2. The layer's containing block is the overflow or inside the overflow:scroll, but its z-order ancestor is
    3245     //    outside the overflow:scroll. In that case, we have to move the layer via the scrolling tree to make
    3246     //    it move along with the overflow scrolling.
    3247     if (!compositedAncestorIsScrolling && isScrolledByOverflowScrollLayer(layer, *scrollingAncestor))
    3248         return ScrollPositioningBehavior::Moves;
    3249 
    3250     return ScrollPositioningBehavior::None;
     3226    return layerScrollBehahaviorRelativeToCompositedAncestor(layer, *compositedAncestor);
    32513227}
    32523228
  • trunk/Source/WebCore/rendering/RenderLayerCompositor.h

    r246725 r246869  
    498498    bool requiresCompositingForIndirectReason(const RenderLayer&, bool hasCompositedDescendants, bool has3DTransformedDescendants, bool paintsIntoProvidedBacking, IndirectCompositingReason&) const;
    499499
    500     static bool layerContainingBlockCrossesCoordinatedScrollingBoundary(const RenderLayer&, const RenderLayer& compositedAncestor);
     500    static ScrollPositioningBehavior layerScrollBehahaviorRelativeToCompositedAncestor(const RenderLayer&, const RenderLayer& compositedAncestor);
    501501
    502502    static bool styleChangeMayAffectIndirectCompositingReasons(const RenderStyle& oldStyle, const RenderStyle& newStyle);
Note: See TracChangeset for help on using the changeset viewer.