Title: [135827] branches/safari-536.28-branch/Source/WebCore
Revision
135827
Author
simon.fra...@apple.com
Date
2012-11-26 23:24:14 -0800 (Mon, 26 Nov 2012)

Log Message

<rdar://problem/12755408>
Merge r135080

    2012-11-18  Simon Fraser  <simon.fra...@apple.com>

    Make convertToLayerCoords iterative, rather than recursive
    https://bugs.webkit.org/show_bug.cgi?id=102618

    Reviewed by Antti Koivisto.

    RenderLayer::convertToLayerCoords() is a hot function on profiles.
    Change it to be iterative, rather than recursive, so that the
    bulk of the function can be inlined.

    Was tested with assertions against the old code during development.

    * rendering/RenderLayer.cpp:
    (WebCore::accumulateOffsetTowardsAncestor):
    (WebCore::RenderLayer::convertToLayerCoords):

Modified Paths

Diff

Modified: branches/safari-536.28-branch/Source/WebCore/ChangeLog (135826 => 135827)


--- branches/safari-536.28-branch/Source/WebCore/ChangeLog	2012-11-27 07:22:35 UTC (rev 135826)
+++ branches/safari-536.28-branch/Source/WebCore/ChangeLog	2012-11-27 07:24:14 UTC (rev 135827)
@@ -1,3 +1,25 @@
+2012-11-26  Simon Fraser  <simon.fra...@apple.com>
+
+        <rdar://problem/12755408>
+        Merge r135080
+
+    2012-11-18  Simon Fraser  <simon.fra...@apple.com>
+    
+            Make convertToLayerCoords iterative, rather than recursive
+            https://bugs.webkit.org/show_bug.cgi?id=102618
+    
+            Reviewed by Antti Koivisto.
+    
+            RenderLayer::convertToLayerCoords() is a hot function on profiles.
+            Change it to be iterative, rather than recursive, so that the
+            bulk of the function can be inlined.
+            
+            Was tested with assertions against the old code during development.
+    
+            * rendering/RenderLayer.cpp:
+            (WebCore::accumulateOffsetTowardsAncestor):
+            (WebCore::RenderLayer::convertToLayerCoords):
+
 2012-11-26  Lucas Forschler  <lforsch...@apple.com>
 
         Merge r134327

Modified: branches/safari-536.28-branch/Source/WebCore/rendering/RenderLayer.cpp (135826 => 135827)


--- branches/safari-536.28-branch/Source/WebCore/rendering/RenderLayer.cpp	2012-11-27 07:22:35 UTC (rev 135826)
+++ branches/safari-536.28-branch/Source/WebCore/rendering/RenderLayer.cpp	2012-11-27 07:24:14 UTC (rev 135827)
@@ -1380,27 +1380,29 @@
     roundedRect = pixelSnappedIntRect(rect);
 }
 
-void RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, LayoutPoint& location) const
+// Returns the layer reached on the walk up towards the ancestor.
+static inline const RenderLayer* accumulateOffsetTowardsAncestor(const RenderLayer* layer, const RenderLayer* ancestorLayer, LayoutPoint& location)
 {
-    if (ancestorLayer == this)
-        return;
+    ASSERT(ancestorLayer != layer);
 
-    EPosition position = renderer()->style()->position();
-    if (position == FixedPosition && (!ancestorLayer || ancestorLayer == renderer()->view()->layer())) {
+    const RenderBoxModelObject* renderer = layer->renderer();
+    EPosition position = renderer->style()->position();
+
+    if (position == FixedPosition && (!ancestorLayer || ancestorLayer == renderer->view()->layer())) {
         // If the fixed layer's container is the root, just add in the offset of the view. We can obtain this by calling
         // localToAbsolute() on the RenderView.
-        FloatPoint absPos = renderer()->localToAbsolute(FloatPoint(), true);
+        FloatPoint absPos = renderer->localToAbsolute(FloatPoint(), true);
         location += flooredLayoutSize(absPos);
-        return;
+        return ancestorLayer;
     }
- 
+
     if (position == FixedPosition) {
         // For a fixed layers, we need to walk up to the root to see if there's a fixed position container
         // (e.g. a transformed layer). It's an error to call convertToLayerCoords() across a layer with a transform,
         // so we should always find the ancestor at or before we find the fixed position container.
         RenderLayer* fixedPositionContainerLayer = 0;
         bool foundAncestor = false;
-        for (RenderLayer* currLayer = parent(); currLayer; currLayer = currLayer->parent()) {
+        for (RenderLayer* currLayer = layer->parent(); currLayer; currLayer = currLayer->parent()) {
             if (currLayer == ancestorLayer)
                 foundAncestor = true;
 
@@ -1415,20 +1417,20 @@
 
         if (fixedPositionContainerLayer != ancestorLayer) {
             LayoutPoint fixedContainerCoords;
-            convertToLayerCoords(fixedPositionContainerLayer, fixedContainerCoords);
+            layer->convertToLayerCoords(fixedPositionContainerLayer, fixedContainerCoords);
 
             LayoutPoint ancestorCoords;
             ancestorLayer->convertToLayerCoords(fixedPositionContainerLayer, ancestorCoords);
 
             location += (fixedContainerCoords - ancestorCoords);
-            return;
+            return ancestorLayer;
         }
     }
     
     RenderLayer* parentLayer;
     if (position == AbsolutePosition || position == FixedPosition) {
         // Do what enclosingPositionedAncestor() does, but check for ancestorLayer along the way.
-        parentLayer = parent();
+        parentLayer = layer->parent();
         bool foundAncestorFirst = false;
         while (parentLayer) {
             if (isPositionedContainer(parentLayer))
@@ -1448,23 +1450,32 @@
             RenderLayer* positionedAncestor = parentLayer->enclosingPositionedAncestor();
 
             LayoutPoint thisCoords;
-            convertToLayerCoords(positionedAncestor, thisCoords);
+            layer->convertToLayerCoords(positionedAncestor, thisCoords);
             
             LayoutPoint ancestorCoords;
             ancestorLayer->convertToLayerCoords(positionedAncestor, ancestorCoords);
 
             location += (thisCoords - ancestorCoords);
-            return;
+            return ancestorLayer;
         }
     } else
-        parentLayer = parent();
+        parentLayer = layer->parent();
     
     if (!parentLayer)
+        return 0;
+
+    location += toSize(layer->location());
+    return parentLayer;
+}
+
+void RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, LayoutPoint& location) const
+{
+    if (ancestorLayer == this)
         return;
 
-    parentLayer->convertToLayerCoords(ancestorLayer, location);
-
-    location += toSize(m_topLeft);
+    const RenderLayer* currLayer = this;
+    while (currLayer && currLayer != ancestorLayer)
+        currLayer = accumulateOffsetTowardsAncestor(currLayer, ancestorLayer, location);
 }
 
 void RenderLayer::convertToLayerCoords(const RenderLayer* ancestorLayer, LayoutRect& rect) const
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
http://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to