WebKit Bugzilla
Attachment 370447 Details for
Bug 198139
: Fix scrolling tree state for more obscure combinations of positioning and paint order
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
Patch
bug-198139-20190522145018.patch (text/plain), 22.27 KB, created by
Simon Fraser (smfr)
on 2019-05-22 14:50:19 PDT
(
hide
)
Description:
Patch
Filename:
MIME Type:
Creator:
Simon Fraser (smfr)
Created:
2019-05-22 14:50:19 PDT
Size:
22.27 KB
patch
obsolete
>Subversion Revision: 245606 >diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog >index 44cc704186752bc1401f71c8d00419ef0168ca51..fa927863522a543b2540c954df2fc114144006f9 100644 >--- a/Source/WebCore/ChangeLog >+++ b/Source/WebCore/ChangeLog >@@ -1,3 +1,36 @@ >+2019-05-22 Simon Fraser <simon.fraser@apple.com> >+ >+ Fix scrolling tree state for more obscure combinations of positioning and paint order >+ https://bugs.webkit.org/show_bug.cgi?id=198139 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ There were three places in RenderLayerCompositor that used a version of ancestor >+ layer traversal looking at containing blocks, and all three had issues. So make a >+ shared function to do the ancestor walk, and use it thrice. >+ >+ isScrolledByOverflowScrollLayer() fumbled containingBlockCanSkipLayers, so failed >+ to create a scrolling tree node for a composited layer inside position:fixed in >+ overflow (tested by composited-in-absolute-in-overflow.html). >+ >+ collectStationaryLayerRelatedOverflowNodes() failed to handle nested >+ overflow:scroll; it needs to find all the composited scrollers that affect the >+ position of the given layer relative to its compositing ancestor, which may be the >+ scroller, or a descendant of the scroller. However, it didn't walk up far enough >+ and find more that one ancestor. Tested by absolute-in-nested-sc-scrollers.html. >+ >+ enclosingClippingScopes() was OK but now uses the share function. >+ >+ Tests: scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers.html >+ scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow.html >+ >+ * rendering/RenderLayerCompositor.cpp: >+ (WebCore::traverseAncestorLayers): >+ (WebCore::enclosingClippingScopes): >+ (WebCore::isScrolledByOverflowScrollLayer): >+ (WebCore::collectStationaryLayerRelatedOverflowNodes): >+ (WebCore::collectRelatedCoordinatedScrollingNodes): >+ > 2019-05-22 Simon Fraser <simon.fraser@apple.com> > > Inner scroller of nested overflow:scrolls jitters when scrolling >diff --git a/Source/WebCore/rendering/RenderLayerCompositor.cpp b/Source/WebCore/rendering/RenderLayerCompositor.cpp >index 51c0d3a0141f2fe28fe666a9ebd1ed01b5c9e048..11e43eb25b68db802d9bf318bb77d3a87d9621a2 100644 >--- a/Source/WebCore/rendering/RenderLayerCompositor.cpp >+++ b/Source/WebCore/rendering/RenderLayerCompositor.cpp >@@ -1794,6 +1794,33 @@ void RenderLayerCompositor::computeExtent(const LayerOverlapMap& overlapMap, con > extent.extentComputed = true; > } > >+enum class AncestorTraversal { Continue, Stop }; >+ >+// This is a simplified version of containing block walking that only handles absolute position. >+static AncestorTraversal traverseAncestorLayers(const RenderLayer& layer, const WTF::Function<AncestorTraversal(const RenderLayer&, bool inContainingBlockChain, bool isPaintOrderAncestor)>& ancestorFunc) >+{ >+ bool containingBlockCanSkipLayers = layer.renderer().isAbsolutelyPositioned(); >+ RenderLayer* nextPaintOrderParent = layer.paintOrderParent(); >+ >+ for (const auto* ancestorLayer = layer.parent(); ancestorLayer; ancestorLayer = ancestorLayer->parent()) { >+ bool inContainingBlockChain = true; >+ >+ if (containingBlockCanSkipLayers) >+ inContainingBlockChain = ancestorLayer->renderer().canContainAbsolutelyPositionedObjects(); >+ >+ if (ancestorFunc(*ancestorLayer, inContainingBlockChain, ancestorLayer == nextPaintOrderParent) == AncestorTraversal::Stop) >+ return AncestorTraversal::Stop; >+ >+ if (inContainingBlockChain) >+ containingBlockCanSkipLayers = ancestorLayer->renderer().isAbsolutelyPositioned(); >+ >+ if (ancestorLayer == nextPaintOrderParent) >+ nextPaintOrderParent = ancestorLayer->paintOrderParent(); >+ } >+ >+ return AncestorTraversal::Continue; >+} >+ > static bool createsClippingScope(const RenderLayer& layer) > { > return layer.hasCompositedScrollableOverflow(); >@@ -1807,27 +1834,20 @@ static Vector<LayerOverlapMap::LayerAndBounds> enclosingClippingScopes(const Ren > if (!layer.hasCompositedScrollingAncestor()) > return clippingScopes; > >- bool containingBlockCanSkipLayers = layer.renderer().isAbsolutelyPositioned(); >- for (const auto* ancestorLayer = layer.parent(); ancestorLayer; ancestorLayer = ancestorLayer->parent()) { >- bool inContainingBlockChain = true; >- if (containingBlockCanSkipLayers) { >- inContainingBlockChain = ancestorLayer->renderer().canContainAbsolutelyPositionedObjects(); >- if (inContainingBlockChain) >- containingBlockCanSkipLayers = ancestorLayer->renderer().isAbsolutelyPositioned(); >- } >- >- if (inContainingBlockChain && createsClippingScope(*ancestorLayer)) { >+ traverseAncestorLayers(layer, [&](const RenderLayer& ancestorLayer, bool inContainingBlockChain, bool) { >+ if (inContainingBlockChain && createsClippingScope(ancestorLayer)) { > LayoutRect clipRect; >- if (is<RenderBox>(ancestorLayer->renderer())) { >+ if (is<RenderBox>(ancestorLayer.renderer())) { > // FIXME: This is expensive. Broken with transforms. >- LayoutPoint offsetFromRoot = ancestorLayer->convertToLayerCoords(&rootLayer, { }); >- clipRect = downcast<RenderBox>(ancestorLayer->renderer()).overflowClipRect(offsetFromRoot); >+ LayoutPoint offsetFromRoot = ancestorLayer.convertToLayerCoords(&rootLayer, { }); >+ clipRect = downcast<RenderBox>(ancestorLayer.renderer()).overflowClipRect(offsetFromRoot); > } > >- LayerOverlapMap::LayerAndBounds layerAndBounds { const_cast<RenderLayer&>(*ancestorLayer), clipRect }; >+ LayerOverlapMap::LayerAndBounds layerAndBounds { const_cast<RenderLayer&>(ancestorLayer), clipRect }; > clippingScopes.insert(1, layerAndBounds); // Order is roots to leaves. > } >- } >+ return AncestorTraversal::Continue; >+ }); > > return clippingScopes; > } >@@ -3040,24 +3060,17 @@ static RenderLayer* enclosingCompositedScrollingLayer(const RenderLayer& layer, > return nullptr; > } > >-// Return true if overflowScrollLayer is in layer's containing block chain. > static bool isScrolledByOverflowScrollLayer(const RenderLayer& layer, const RenderLayer& overflowScrollLayer) > { >- bool containingBlockCanSkipLayers = layer.renderer().isAbsolutelyPositioned(); >- >- for (const auto* currLayer = layer.parent(); currLayer; currLayer = currLayer->parent()) { >- bool inContainingBlockChain = true; >- if (containingBlockCanSkipLayers) { >- inContainingBlockChain = currLayer->renderer().canContainAbsolutelyPositionedObjects(); >- if (inContainingBlockChain) >- containingBlockCanSkipLayers = currLayer->renderer().isAbsolutelyPositioned(); >+ bool scrolledByOverflowScroll = false; >+ traverseAncestorLayers(layer, [&](const RenderLayer& ancestorLayer, bool inContainingBlockChain, bool) { >+ if (&ancestorLayer == &overflowScrollLayer) { >+ scrolledByOverflowScroll = inContainingBlockChain; >+ return AncestorTraversal::Stop; > } >- >- if (currLayer == &overflowScrollLayer) >- return inContainingBlockChain; >- } >- >- return false; >+ return AncestorTraversal::Continue; >+ }); >+ return scrolledByOverflowScroll; > } > > static bool isNonScrolledLayerInsideScrolledCompositedAncestor(const RenderLayer& layer, const RenderLayer& compositedAncestor, const RenderLayer& scrollingAncestor) >@@ -3083,7 +3096,7 @@ bool RenderLayerCompositor::layerContainingBlockCrossesCoordinatedScrollingBound > return isNonScrolledLayerInsideScrolledCompositedAncestor(layer, compositedAncestor, *scrollingAncestor); > } > >-static void collectStationaryLayerRelatedOverflowNodes(const RenderLayer& layer, const RenderLayer& /*compositedAncestor*/, Vector<ScrollingNodeID>& scrollingNodes) >+static void collectStationaryLayerRelatedOverflowNodes(const RenderLayer& layer, const RenderLayer&, Vector<ScrollingNodeID>& scrollingNodes) > { > ASSERT(layer.isComposited()); > >@@ -3097,23 +3110,20 @@ static void collectStationaryLayerRelatedOverflowNodes(const RenderLayer& layer, > }; > > ASSERT(layer.renderer().isAbsolutelyPositioned()); >- bool containingBlockCanSkipLayers = true; > >- for (const auto* currLayer = layer.parent(); currLayer; currLayer = currLayer->parent()) { >- bool inContainingBlockChain = true; >- if (containingBlockCanSkipLayers) { >- inContainingBlockChain = currLayer->renderer().canContainAbsolutelyPositionedObjects(); >- if (inContainingBlockChain) >- containingBlockCanSkipLayers = currLayer->renderer().isAbsolutelyPositioned(); >- } >+ // Collect all the composited scrollers which affect the position of this layer relative to its compositing ancestor (which might be inside the scroller or the scroller itself). >+ bool seenPaintOrderAncestor = false; >+ traverseAncestorLayers(layer, [&](const RenderLayer& ancestorLayer, bool isContainingBlockChain, bool isPaintOrderAncestor) { >+ seenPaintOrderAncestor |= isPaintOrderAncestor; >+ if (isContainingBlockChain && isPaintOrderAncestor) >+ return AncestorTraversal::Stop; > >- if (currLayer->hasCompositedScrollableOverflow()) { >- appendOverflowLayerNodeID(*currLayer); >- break; >- } >- } >-} >+ if (seenPaintOrderAncestor && !isContainingBlockChain && ancestorLayer.hasCompositedScrollableOverflow()) >+ appendOverflowLayerNodeID(ancestorLayer); > >+ return AncestorTraversal::Continue; >+ }); >+} > > ScrollPositioningBehavior RenderLayerCompositor::computeCoordinatedPositioningForLayer(const RenderLayer& layer) const > { >@@ -3182,7 +3192,6 @@ static Vector<ScrollingNodeID> collectRelatedCoordinatedScrollingNodes(const Ren > } > case ScrollPositioningBehavior::Stationary: { > ASSERT(layer.renderer().isAbsolutelyPositioned()); >- // Collect all the composited scrollers between this layer and its composited ancestor. > auto* compositedAncestor = layer.ancestorCompositingLayer(); > if (!compositedAncestor) > return overflowNodeData; >diff --git a/LayoutTests/ChangeLog b/LayoutTests/ChangeLog >index 93ab50707f5bfaf61aaffd7078b8c729c061dde1..d8c08ddb1bdc20c6a149b955c16f0aaa54f3269d 100644 >--- a/LayoutTests/ChangeLog >+++ b/LayoutTests/ChangeLog >@@ -1,3 +1,17 @@ >+2019-05-22 Simon Fraser <simon.fraser@apple.com> >+ >+ Fix scrolling tree state for more obscure combinations of positioning and paint order >+ https://bugs.webkit.org/show_bug.cgi?id=198139 >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * platform/ios-wk2/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt: Added. >+ * platform/ios-wk2/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt: Added. >+ * scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt: Added. >+ * scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers.html: Added. >+ * scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt: Added. >+ * scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow.html: Added. >+ > 2019-05-22 Simon Fraser <simon.fraser@apple.com> > > Inner scroller of nested overflow:scrolls jitters when scrolling >diff --git a/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt b/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt >new file mode 100644 >index 0000000000000000000000000000000000000000..33045c310fa7d5222f0aee94ec4a597c631504b3 >--- /dev/null >+++ b/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt >@@ -0,0 +1,50 @@ >+ >+(Frame scrolling node >+ (scrollable area size 800 600) >+ (contents size 800 600) >+ (parent relative scrollable rect at (0,0) size 800x600) >+ (scrollable area parameters >+ (horizontal scroll elasticity 1) >+ (vertical scroll elasticity 1) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0)) >+ (layout viewport at (0,0) size 800x600) >+ (min layout viewport origin (0,0)) >+ (max layout viewport origin (0,0)) >+ (behavior for fixed 0) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 300 300) >+ (contents size 300 794) >+ (parent relative scrollable rect at (30,22) size 300x300) >+ (scrollable area parameters >+ (horizontal scroll elasticity 1) >+ (vertical scroll elasticity 1) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 250 250) >+ (contents size 250 500) >+ (parent relative scrollable rect at (24,24) size 250x250) >+ (scrollable area parameters >+ (horizontal scroll elasticity 1) >+ (vertical scroll elasticity 1) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ (children 1 >+ (Positioned node >+ (layout constraints >+ (layer-position-at-last-layout (-2,6)) >+ (positioning-behavior stationary)) >+ (related overflow nodes 2) >+ ) >+ ) >+ ) >+ ) >+ ) >+ ) >+) >+ >diff --git a/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt b/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt >new file mode 100644 >index 0000000000000000000000000000000000000000..3349b35b836daf5949525527e9f9ed3fece28beb >--- /dev/null >+++ b/LayoutTests/platform/ios-wk2/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt >@@ -0,0 +1,29 @@ >+ >+(Frame scrolling node >+ (scrollable area size 800 600) >+ (contents size 800 600) >+ (parent relative scrollable rect at (0,0) size 800x600) >+ (scrollable area parameters >+ (horizontal scroll elasticity 1) >+ (vertical scroll elasticity 1) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0)) >+ (layout viewport at (0,0) size 800x600) >+ (min layout viewport origin (0,0)) >+ (max layout viewport origin (0,0)) >+ (behavior for fixed 0) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 300 300) >+ (contents size 300 1000) >+ (parent relative scrollable rect at (30,22) size 300x300) >+ (scrollable area parameters >+ (horizontal scroll elasticity 1) >+ (vertical scroll elasticity 1) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ ) >+ ) >+) >+ >diff --git a/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt b/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt >new file mode 100644 >index 0000000000000000000000000000000000000000..86b8d927b4b71ed3abbcce2ceefa18cbe506ba16 >--- /dev/null >+++ b/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers-expected.txt >@@ -0,0 +1,50 @@ >+ >+(Frame scrolling node >+ (scrollable area size 800 600) >+ (contents size 800 600) >+ (parent relative scrollable rect at (0,0) size 800x600) >+ (scrollable area parameters >+ (horizontal scroll elasticity 2) >+ (vertical scroll elasticity 2) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0)) >+ (layout viewport at (0,0) size 800x600) >+ (min layout viewport origin (0,0)) >+ (max layout viewport origin (0,0)) >+ (behavior for fixed 0) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 285 285) >+ (contents size 285 794) >+ (parent relative scrollable rect at (30,22) size 285x285) >+ (scrollable area parameters >+ (horizontal scroll elasticity 0) >+ (vertical scroll elasticity 0) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 235 235) >+ (contents size 235 500) >+ (parent relative scrollable rect at (24,24) size 235x235) >+ (scrollable area parameters >+ (horizontal scroll elasticity 0) >+ (vertical scroll elasticity 0) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ (children 1 >+ (Positioned node >+ (layout constraints >+ (layer-position-at-last-layout (-2,6)) >+ (positioning-behavior stationary)) >+ (related overflow nodes 2) >+ ) >+ ) >+ ) >+ ) >+ ) >+ ) >+) >+ >diff --git a/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers.html b/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers.html >new file mode 100644 >index 0000000000000000000000000000000000000000..a62637c53ccea2bed8b2a2ce6b273147ea1e771d >--- /dev/null >+++ b/LayoutTests/scrollingcoordinator/scrolling-tree/absolute-in-nested-sc-scrollers.html >@@ -0,0 +1,68 @@ >+<!DOCTYPE html> <!-- webkit-test-runner [ internal:AsyncOverflowScrollingEnabled=true ] --> >+<html> >+<head> >+ <title>Tests that we make a scrolling tree node for composited layers nested inside position:absolute in a scroller</title> >+ <style> >+ .scroller { >+ overflow: scroll; >+ margin: 20px; >+ height: 300px; >+ width: 300px; >+ border: 2px solid black; >+ opacity: 0.8; >+ } >+ >+ .scroller > .scroller { >+ height: 250px; >+ width: 250px; >+ } >+ >+ .absolute { >+ position:absolute; >+ left: 50px; >+ top: 50px; >+ width: 200px; >+ height: 120px; >+ padding: 20px; >+ background: gray; >+ } >+ >+ .composited { >+ transform: translateZ(0); >+ } >+ >+ .box { >+ width: 100px; >+ height: 100px; >+ background-color: green; >+ } >+ >+ .spacer { >+ height: 500px; >+ width: 20px; >+ background-color: silver; >+ } >+ </style> >+ <script> >+ if (window.testRunner) >+ testRunner.dumpAsText(); >+ >+ window.addEventListener('load', () => { >+ if (window.internals) >+ document.getElementById('tree').innerText = internals.scrollingStateTreeAsText(); >+ }, false); >+ </script> >+</head> >+<body> >+ <div class="scroller"> >+ <div class="scroller"> >+ <div class="absolute"> >+ <!-- <div class="composited box"></div> --> >+ </div> >+ <div class="spacer"></div> >+ </div> >+ <div class="spacer"></div> >+ </div> >+<pre id="tree"></pre> >+</body> >+</html> >diff --git a/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt b/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt >new file mode 100644 >index 0000000000000000000000000000000000000000..9c8b4d2e662aa2b3bbf07a1d8e76e14f6c730530 >--- /dev/null >+++ b/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow-expected.txt >@@ -0,0 +1,29 @@ >+ >+(Frame scrolling node >+ (scrollable area size 800 600) >+ (contents size 800 600) >+ (parent relative scrollable rect at (0,0) size 800x600) >+ (scrollable area parameters >+ (horizontal scroll elasticity 2) >+ (vertical scroll elasticity 2) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0)) >+ (layout viewport at (0,0) size 800x600) >+ (min layout viewport origin (0,0)) >+ (max layout viewport origin (0,0)) >+ (behavior for fixed 0) >+ (children 1 >+ (Overflow scrolling node >+ (scrollable area size 285 285) >+ (contents size 285 1000) >+ (parent relative scrollable rect at (30,22) size 285x285) >+ (scrollable area parameters >+ (horizontal scroll elasticity 0) >+ (vertical scroll elasticity 0) >+ (horizontal scrollbar mode 0) >+ (vertical scrollbar mode 0) >+ (has enabled vertical scrollbar 1)) >+ ) >+ ) >+) >+ >diff --git a/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow.html b/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow.html >new file mode 100644 >index 0000000000000000000000000000000000000000..7c45a982ffbd04be83322d80b67a6470b817ca87 >--- /dev/null >+++ b/LayoutTests/scrollingcoordinator/scrolling-tree/composited-in-absolute-in-overflow.html >@@ -0,0 +1,58 @@ >+<!DOCTYPE html> <!-- webkit-test-runner [ internal:AsyncOverflowScrollingEnabled=true ] --> >+<html> >+<head> >+ <title>Tests that we make a scrolling tree node for composited layers nested inside position:absolute in a scroller</title> >+ <style> >+ .scroller { >+ overflow: scroll; >+ margin: 20px; >+ height: 300px; >+ width: 300px; >+ border: 2px solid black; >+ } >+ >+ .absolute { >+ position:absolute; >+ left: 50px; >+ top: 50px; >+ width: 200px; >+ height: 120px; >+ padding: 20px; >+ background: gray; >+ } >+ >+ .composited { >+ transform: translateZ(0); >+ } >+ >+ .box { >+ width: 100px; >+ height: 100px; >+ background-color: green; >+ } >+ >+ .spacer { >+ height: 500px; >+ } >+ </style> >+ <script> >+ if (window.testRunner) >+ testRunner.dumpAsText(); >+ >+ window.addEventListener('load', () => { >+ if (window.internals) >+ document.getElementById('tree').innerText = internals.scrollingStateTreeAsText(); >+ }, false); >+ </script> >+</head> >+<body> >+ <div class="scroller"> >+ <div class="spacer"></div> >+ <div class="absolute"> >+ <div class="composited box"></div> >+ </div> >+ <div class="spacer"></div> >+ </div> >+<pre id="tree"></pre> >+</body> >+</html>
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Flags:
koivisto
:
review+
Actions:
View
|
Formatted Diff
|
Diff
Attachments on
bug 198139
: 370447