summaryrefslogtreecommitdiffstats
path: root/cc/resources
diff options
context:
space:
mode:
authorschenney <schenney@chromium.org>2015-03-12 10:58:11 -0700
committerCommit bot <commit-bot@chromium.org>2015-03-12 17:58:48 +0000
commit5a685845ab0da9c089bce7caaafdc4339beb6d7c (patch)
tree373a9400cb6c061cb785b442c4c1de8a2bf14e34 /cc/resources
parentf9459bbef7b9817d9c0a69aa34501f85f174ddea (diff)
downloadchromium_src-5a685845ab0da9c089bce7caaafdc4339beb6d7c.zip
chromium_src-5a685845ab0da9c089bce7caaafdc4339beb6d7c.tar.gz
chromium_src-5a685845ab0da9c089bce7caaafdc4339beb6d7c.tar.bz2
Raster into an SkPicture before rendering a DisplayList.
Rasterizing a display list is more than 2x slower than rasterizing in the existing architecture. This is due to recording more with a display list and we have no bounding hierarchy to cull content quickly. We can address this by creating an SkPicture from the list, with a bounding hierarchy, and rasterizing that instead. The result is slightly faster than the non-S.P. pipeline but uses 2x more memory. Identical patch to https://codereview.chromium.org/966443003/. Committing TBR thanks to previous LGTM for exact same patch. Expectations have been updated. TBR=chrishtr,ajuma BUG=464738 Review URL: https://codereview.chromium.org/1004753002 Cr-Commit-Position: refs/heads/master@{#320317}
Diffstat (limited to 'cc/resources')
-rw-r--r--cc/resources/display_item_list.cc51
-rw-r--r--cc/resources/display_item_list.h6
-rw-r--r--cc/resources/display_list_recording_source.cc3
3 files changed, 55 insertions, 5 deletions
diff --git a/cc/resources/display_item_list.cc b/cc/resources/display_item_list.cc
index ac6ab57..48f8c66 100644
--- a/cc/resources/display_item_list.cc
+++ b/cc/resources/display_item_list.cc
@@ -10,8 +10,12 @@
#include "base/trace_event/trace_event_argument.h"
#include "cc/base/math_util.h"
#include "cc/debug/picture_debug_util.h"
+#include "cc/debug/traced_picture.h"
+#include "cc/debug/traced_value.h"
#include "third_party/skia/include/core/SkCanvas.h"
+#include "third_party/skia/include/core/SkDrawPictureCallback.h"
#include "third_party/skia/include/core/SkPictureRecorder.h"
+#include "third_party/skia/include/utils/SkPictureUtils.h"
#include "ui/gfx/skia_util.h"
namespace cc {
@@ -30,12 +34,46 @@ DisplayItemList::~DisplayItemList() {
void DisplayItemList::Raster(SkCanvas* canvas,
SkDrawPictureCallback* callback,
float contents_scale) const {
- canvas->save();
- canvas->scale(contents_scale, contents_scale);
- for (size_t i = 0; i < items_.size(); ++i) {
- items_[i]->Raster(canvas, callback);
+ if (!picture_) {
+ canvas->save();
+ canvas->scale(contents_scale, contents_scale);
+ for (size_t i = 0; i < items_.size(); ++i) {
+ items_[i]->Raster(canvas, callback);
+ }
+ canvas->restore();
+ } else {
+ DCHECK(picture_);
+
+ canvas->save();
+ canvas->scale(contents_scale, contents_scale);
+ if (callback) {
+ // If we have a callback, we need to call |draw()|, |drawPicture()|
+ // doesn't take a callback. This is used by |AnalysisCanvas| to early
+ // out.
+ picture_->playback(canvas, callback);
+ } else {
+ // Prefer to call |drawPicture()| on the canvas since it could place the
+ // entire picture on the canvas instead of parsing the skia operations.
+ canvas->drawPicture(picture_.get());
+ }
+ canvas->restore();
}
- canvas->restore();
+}
+
+void DisplayItemList::CreateAndCacheSkPicture() {
+ // Convert to an SkPicture for faster rasterization. Code is identical to
+ // that in Picture::Record.
+ SkRTreeFactory factory;
+ SkPictureRecorder recorder;
+ skia::RefPtr<SkCanvas> canvas;
+ canvas = skia::SharePtr(recorder.beginRecording(
+ layer_rect_.width(), layer_rect_.height(), &factory));
+ canvas->translate(-layer_rect_.x(), -layer_rect_.y());
+ canvas->clipRect(gfx::RectToSkRect(layer_rect_));
+ for (size_t i = 0; i < items_.size(); ++i)
+ items_[i]->Raster(canvas.get(), NULL);
+ picture_ = skia::AdoptRef(recorder.endRecording());
+ DCHECK(picture_);
}
void DisplayItemList::AppendItem(scoped_ptr<DisplayItem> item) {
@@ -62,6 +100,9 @@ size_t DisplayItemList::PictureMemoryUsage() const {
total_size += item->PictureMemoryUsage();
}
+ if (picture_)
+ total_size += SkPictureUtils::ApproximateBytesUsed(picture_.get());
+
return total_size;
}
diff --git a/cc/resources/display_item_list.h b/cc/resources/display_item_list.h
index e16b8b8..39694d7 100644
--- a/cc/resources/display_item_list.h
+++ b/cc/resources/display_item_list.h
@@ -11,6 +11,8 @@
#include "cc/base/cc_export.h"
#include "cc/base/scoped_ptr_vector.h"
#include "cc/resources/display_item.h"
+#include "skia/ext/refptr.h"
+#include "third_party/skia/include/core/SkPicture.h"
#include "ui/gfx/geometry/rect.h"
class SkCanvas;
@@ -32,6 +34,8 @@ class CC_EXPORT DisplayItemList
void set_layer_rect(gfx::Rect layer_rect) { layer_rect_ = layer_rect; }
gfx::Rect layer_rect() const { return layer_rect_; }
+ void CreateAndCacheSkPicture();
+
bool IsSuitableForGpuRasterization() const;
int ApproximateOpCount() const;
size_t PictureMemoryUsage() const;
@@ -44,6 +48,8 @@ class CC_EXPORT DisplayItemList
DisplayItemList();
~DisplayItemList();
ScopedPtrVector<DisplayItem> items_;
+ skia::RefPtr<SkPicture> picture_;
+
gfx::Rect layer_rect_;
bool is_suitable_for_gpu_rasterization_;
int approximate_op_count_;
diff --git a/cc/resources/display_list_recording_source.cc b/cc/resources/display_list_recording_source.cc
index 8d2dc3e..367b23d 100644
--- a/cc/resources/display_list_recording_source.cc
+++ b/cc/resources/display_list_recording_source.cc
@@ -112,6 +112,9 @@ bool DisplayListRecordingSource::UpdateAndExpandInvalidation(
DetermineIfSolidColor();
display_list_->EmitTraceSnapshot();
+
+ display_list_->CreateAndCacheSkPicture();
+
return true;
}