Commit b9ab6d54 authored by shawnsingh@google.com's avatar shawnsingh@google.com

Tighten the matrix usage in cc/layer_tree_host_common.cpp

As calculateDrawTransforms has evolved, the math has become substantially more
overhead. This patch refactors the matrix math to reduce the number of matrix
copies and matrix multiplications. Changes that would drastically affect
readability or robustness are avoided.

With this patch, cc_perftests improves by approximately 6-8%.
SevenTabSwitcher: 2030 runs/s --> 2220 runs/s  (9.3%)
tenTabSwitcher: 757 runs/s --> 807 runs/s  (6.6%)

BUG=163769

Review URL: https://codereview.chromium.org/11280271

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@171051 0039d316-1c4b-4281-b951-d872f2087c98
parent cd14ae50
...@@ -507,30 +507,30 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo ...@@ -507,30 +507,30 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo
gfx::PointF anchorPoint = layer->anchorPoint(); gfx::PointF anchorPoint = layer->anchorPoint();
gfx::PointF position = layer->position() - layer->scrollDelta(); gfx::PointF position = layer->position() - layer->scrollDelta();
gfx::Transform layerLocalTransform; gfx::Transform combinedTransform = parentMatrix;
// LT = Tr[origin] * Tr[origin2anchor] // LT = Tr[origin] * Tr[origin2anchor]
layerLocalTransform.Translate3d(position.x() + anchorPoint.x() * bounds.width(), position.y() + anchorPoint.y() * bounds.height(), layer->anchorPointZ()); combinedTransform.Translate3d(position.x() + anchorPoint.x() * bounds.width(), position.y() + anchorPoint.y() * bounds.height(), layer->anchorPointZ());
// LT = Tr[origin] * Tr[origin2anchor] * M[layer] // LT = Tr[origin] * Tr[origin2anchor] * M[layer]
layerLocalTransform.PreconcatTransform(layer->transform()); combinedTransform.PreconcatTransform(layer->transform());
// LT = Tr[origin] * Tr[origin2anchor] * M[layer] * Tr[anchor2origin] // LT = Tr[origin] * Tr[origin2anchor] * M[layer] * Tr[anchor2origin]
layerLocalTransform.Translate3d(-anchorPoint.x() * bounds.width(), -anchorPoint.y() * bounds.height(), -layer->anchorPointZ()); combinedTransform.Translate3d(-anchorPoint.x() * bounds.width(), -anchorPoint.y() * bounds.height(), -layer->anchorPointZ());
gfx::Transform combinedTransform = parentMatrix;
combinedTransform.PreconcatTransform(layerLocalTransform);
// The layer's contentsSize is determined from the combinedTransform, which then informs the // The layer's contentsSize is determined from the combinedTransform, which then informs the
// layer's drawTransform. // layer's drawTransform.
updateLayerContentsScale(layer, combinedTransform, deviceScaleFactor, pageScaleFactor, animatingTransformToScreen); updateLayerContentsScale(layer, combinedTransform, deviceScaleFactor, pageScaleFactor, animatingTransformToScreen);
// If there is a tranformation from the impl thread then it should be at the // If there is a transformation from the impl thread then it should be at
// start of the combinedTransform, but we don't want it to affect the contentsScale. // the start of the combinedTransform, but we don't want it to affect the
combinedTransform = layer->implTransform() * combinedTransform; // computation of contentsScale above.
// Note carefully: this is Concat, not Preconcat (implTransform * combinedTransform).
combinedTransform.ConcatTransform(layer->implTransform());
if (layer->fixedToContainerLayer()) { if (layer->fixedToContainerLayer()) {
// Special case: this layer is a composited fixed-position layer; we need to // Special case: this layer is a composited fixed-position layer; we need to
// explicitly compensate for all ancestors' nonzero scrollDeltas to keep this layer // explicitly compensate for all ancestors' nonzero scrollDeltas to keep this layer
// fixed correctly. // fixed correctly.
combinedTransform = currentScrollCompensationMatrix * combinedTransform; // Note carefully: this is Concat, not Preconcat (currentScrollCompensation * combinedTransform).
combinedTransform.ConcatTransform(currentScrollCompensationMatrix);
} }
// The drawTransform that gets computed below is effectively the layer's drawTransform, unless // The drawTransform that gets computed below is effectively the layer's drawTransform, unless
...@@ -566,22 +566,23 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo ...@@ -566,22 +566,23 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo
RenderSurfaceType* renderSurface = layer->renderSurface(); RenderSurfaceType* renderSurface = layer->renderSurface();
renderSurface->clearLayerLists(); renderSurface->clearLayerLists();
// The owning layer's draw transform has a scale from content to layer space which we need to undo and // The owning layer's draw transform has a scale from content to layer
// replace with a scale from the surface's subtree into layer space. // space which we do not want; so here we use the combinedTransform
drawTransform.Scale(layer->contentsScaleX(), layer->contentsScaleY()); // instead of the drawTransform. However, we do need to add a different
drawTransform.Scale(1 / renderSurfaceSublayerScale.x(), 1 / renderSurfaceSublayerScale.y()); // scale factor that accounts for the surface's pixel dimensions.
renderSurface->setDrawTransform(drawTransform); combinedTransform.Scale(1 / renderSurfaceSublayerScale.x(), 1 / renderSurfaceSublayerScale.y());
renderSurface->setDrawTransform(combinedTransform);
// The origin of the new surface is the upper left corner of the layer. // The owning layer's transform was re-parented by the surface, so the layer's new drawTransform
// only needs to scale the layer to surface space.
gfx::Transform layerDrawTransform; gfx::Transform layerDrawTransform;
layerDrawTransform.Scale(renderSurfaceSublayerScale.x(), renderSurfaceSublayerScale.y()); layerDrawTransform.Scale(renderSurfaceSublayerScale.x() / layer->contentsScaleX(), renderSurfaceSublayerScale.y() / layer->contentsScaleY());
layerDrawTransform.Scale(1.0 / layer->contentsScaleX(), 1.0 / layer->contentsScaleY());
layer->setDrawTransform(layerDrawTransform); layer->setDrawTransform(layerDrawTransform);
// Inside the surface's subtree, we scale everything to the owning layer's scale. // Inside the surface's subtree, we scale everything to the owning layer's scale.
// The sublayer matrix transforms centered layer rects into target // The sublayer matrix transforms centered layer rects into target
// surface content space. // surface content space.
sublayerMatrix.MakeIdentity(); DCHECK(sublayerMatrix.IsIdentity());
sublayerMatrix.Scale(renderSurfaceSublayerScale.x(), renderSurfaceSublayerScale.y()); sublayerMatrix.Scale(renderSurfaceSublayerScale.x(), renderSurfaceSublayerScale.y());
// The opacity value is moved from the layer to its surface, so that the entire subtree properly inherits opacity. // The opacity value is moved from the layer to its surface, so that the entire subtree properly inherits opacity.
...@@ -669,9 +670,11 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo ...@@ -669,9 +670,11 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo
MathUtil::flattenTransformTo2d(sublayerMatrix); MathUtil::flattenTransformTo2d(sublayerMatrix);
// Apply the sublayer transform at the center of the layer. // Apply the sublayer transform at the center of the layer.
sublayerMatrix.Translate(0.5 * bounds.width(), 0.5 * bounds.height()); if (!layer->sublayerTransform().IsIdentity()) {
sublayerMatrix.PreconcatTransform(layer->sublayerTransform()); sublayerMatrix.Translate(0.5 * bounds.width(), 0.5 * bounds.height());
sublayerMatrix.Translate(-0.5 * bounds.width(), -0.5 * bounds.height()); sublayerMatrix.PreconcatTransform(layer->sublayerTransform());
sublayerMatrix.Translate(-0.5 * bounds.width(), -0.5 * bounds.height());
}
LayerList& descendants = (layer->renderSurface() ? layer->renderSurface()->layerList() : layerList); LayerList& descendants = (layer->renderSurface() ? layer->renderSurface()->layerList() : layerList);
...@@ -761,8 +764,7 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo ...@@ -761,8 +764,7 @@ static void calculateDrawTransformsInternal(LayerType* layer, const gfx::Transfo
// The owning layer's screenSpaceTransform has a scale from content to layer space which we need to undo and // The owning layer's screenSpaceTransform has a scale from content to layer space which we need to undo and
// replace with a scale from the surface's subtree into layer space. // replace with a scale from the surface's subtree into layer space.
gfx::Transform screenSpaceTransform = layer->screenSpaceTransform(); gfx::Transform screenSpaceTransform = layer->screenSpaceTransform();
screenSpaceTransform.Scale(layer->contentsScaleX(), layer->contentsScaleY()); screenSpaceTransform.Scale(layer->contentsScaleX() / renderSurfaceSublayerScale.x(), layer->contentsScaleY() / renderSurfaceSublayerScale.y());
screenSpaceTransform.Scale(1 / renderSurfaceSublayerScale.x(), 1 / renderSurfaceSublayerScale.y());
renderSurface->setScreenSpaceTransform(screenSpaceTransform); renderSurface->setScreenSpaceTransform(screenSpaceTransform);
if (layer->replicaLayer()) { if (layer->replicaLayer()) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment