Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(244)

Unified Diff: third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp

Issue 2345233004: Reuse cc::PictureLayers when possible for SPv2. (Closed)
Patch Set: none Created 4 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp
diff --git a/third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp b/third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp
index d503ab78d171498ea369f6223c85306be250f9db..66421648902b45dc5f1a67c783995b67aa30177e 100644
--- a/third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp
+++ b/third_party/WebKit/Source/platform/graphics/compositing/PaintArtifactCompositor.cpp
@@ -50,8 +50,13 @@ class PaintArtifactCompositor::ContentLayerClientImpl : public cc::ContentLayerC
WTF_MAKE_NONCOPYABLE(ContentLayerClientImpl);
USING_FAST_MALLOC(ContentLayerClientImpl);
public:
- ContentLayerClientImpl(scoped_refptr<cc::DisplayItemList> list, const gfx::Rect& paintableRegion)
- : m_ccDisplayItemList(std::move(list)), m_paintableRegion(paintableRegion) { }
+ ContentLayerClientImpl(Optional<DisplayItem::Id> paintChunkId)
+ : m_id(paintChunkId), m_ccPictureLayer(cc::PictureLayer::Create(this))
+ {
+ }
+
+ void SetDisplayList(scoped_refptr<cc::DisplayItemList> ccDisplayItemList) { m_ccDisplayItemList = std::move(ccDisplayItemList); }
+ void SetPaintableRegion(gfx::Rect region) { m_paintableRegion = region; }
// cc::ContentLayerClient
gfx::Rect PaintableRegion() override { return m_paintableRegion; }
@@ -66,7 +71,16 @@ public:
return 0;
}
+ scoped_refptr<cc::PictureLayer> ccPictureLayer() { return m_ccPictureLayer; }
+
+ bool matches(const PaintChunk& paintChunk)
+ {
+ return m_id && paintChunk.id && *m_id == *paintChunk.id;
+ }
+
private:
+ Optional<PaintChunk::Id> m_id;
+ scoped_refptr<cc::PictureLayer> m_ccPictureLayer;
scoped_refptr<cc::DisplayItemList> m_ccDisplayItemList;
gfx::Rect m_paintableRegion;
};
@@ -186,6 +200,17 @@ void setMinimalPropertyTrees(cc::PropertyTrees* propertyTrees, int ownerId)
} // namespace
+std::unique_ptr<PaintArtifactCompositor::ContentLayerClientImpl> PaintArtifactCompositor::clientForPaintChunk(const PaintChunk& paintChunk)
+{
+ // TODO(chrishtr): for now, just using a linear walk. In the future we can optimize this by using the same techniques used in
+ // PaintController for display lists.
+ for (auto& client : m_currentContentLayerClients) {
+ if (client && client->matches(paintChunk))
+ return std::move(client);
+ }
+ return wrapUnique(new ContentLayerClientImpl(paintChunk.id));
+}
+
scoped_refptr<cc::Layer> PaintArtifactCompositor::layerForPaintChunk(const PaintArtifact& paintArtifact, const PaintChunk& paintChunk, gfx::Vector2dF& layerOffset)
{
DCHECK(paintChunk.size());
@@ -194,20 +219,30 @@ scoped_refptr<cc::Layer> PaintArtifactCompositor::layerForPaintChunk(const Paint
if (scoped_refptr<cc::Layer> foreignLayer = foreignLayerForPaintChunk(paintArtifact, paintChunk, layerOffset))
return foreignLayer;
- // The common case: create a layer for painted content.
+ // The common case: create or reuse a PictureLayer for painted content.
+ std::unique_ptr<ContentLayerClientImpl> contentLayerClient = clientForPaintChunk(paintChunk);
+
gfx::Rect combinedBounds = enclosingIntRect(paintChunk.bounds);
scoped_refptr<cc::DisplayItemList> displayList = recordPaintChunk(paintArtifact, paintChunk, combinedBounds);
- std::unique_ptr<ContentLayerClientImpl> contentLayerClient = wrapUnique(
- new ContentLayerClientImpl(std::move(displayList), gfx::Rect(combinedBounds.size())));
+ contentLayerClient->SetDisplayList(std::move(displayList));
+ contentLayerClient->SetPaintableRegion(gfx::Rect(combinedBounds.size()));
pdr. 2016/09/21 02:46:13 Can the combined bounds grow?
chrishtr 2016/09/21 22:34:41 Yes.
layerOffset = combinedBounds.OffsetFromOrigin();
- scoped_refptr<cc::PictureLayer> layer = cc::PictureLayer::Create(contentLayerClient.get());
- layer->SetBounds(combinedBounds.size());
- layer->SetIsDrawable(true);
+ scoped_refptr<cc::PictureLayer> ccPictureLayer = contentLayerClient->ccPictureLayer();
+ ccPictureLayer->SetBounds(combinedBounds.size());
+ ccPictureLayer->SetIsDrawable(true);
if (paintChunk.knownToBeOpaque)
- layer->SetContentsOpaque(true);
- m_contentLayerClients.append(std::move(contentLayerClient));
- return layer;
+ ccPictureLayer->SetContentsOpaque(true);
+ for (auto& invalidation : paintChunk.rasterInvalidationRects) {
+ IntRect rect(enclosingIntRect(invalidation));
+ gfx::Rect ccInvalidationRect(rect.x(), rect.y(), std::max(0, rect.width()), std::max(0, rect.height()));
+ // Raster paintChunk.rasterInvalidationRects is in the space of the containing transform node, so need to subtract off the layer offset.
+ ccInvalidationRect.Offset(-combinedBounds.OffsetFromOrigin());
+ ccPictureLayer->SetNeedsDisplayRect(ccInvalidationRect);
+ }
+
+ m_newContentLayerClients.append(std::move(contentLayerClient));
+ return ccPictureLayer;
}
namespace {
@@ -516,8 +551,7 @@ void PaintArtifactCompositor::update(const PaintArtifact& paintArtifact)
PropertyTreeManager propertyTreeManager(*layerTree->property_trees(), m_rootLayer.get());
propertyTreeManager.setDeviceScaleFactor(layerTree->device_scale_factor());
pdr. 2016/09/21 02:46:13 DCHECK above that m_newContentLayerClients is empt
chrishtr 2016/09/21 22:34:41 Now unnecessary due to the below suggestion.
- m_contentLayerClients.clear();
- m_contentLayerClients.reserveCapacity(paintArtifact.paintChunks().size());
+ m_newContentLayerClients.reserveCapacity(paintArtifact.paintChunks().size());
for (const PaintChunk& paintChunk : paintArtifact.paintChunks()) {
gfx::Vector2dF layerOffset;
scoped_refptr<cc::Layer> layer = layerForPaintChunk(paintArtifact, paintChunk, layerOffset);
pdr. 2016/09/21 02:46:13 Do we need the m_newContentLayerClients member sin
chrishtr 2016/09/21 22:34:41 Done.
@@ -547,6 +581,8 @@ void PaintArtifactCompositor::update(const PaintArtifact& paintArtifact)
if (m_extraDataForTestingEnabled)
m_extraDataForTesting->contentLayers.append(layer);
}
+ m_currentContentLayerClients.clear();
+ m_currentContentLayerClients.swap(m_newContentLayerClients);
// Mark the property trees as having been rebuilt.
layerTree->property_trees()->sequence_number = kPropertyTreeSequenceNumber;

Powered by Google App Engine
This is Rietveld 408576698