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

Unified Diff: cc/tiles/checker_image_tracker.cc

Issue 2668873002: cc: Add checker-imaging support to TileManager. (Closed)
Patch Set: Created 3 years, 11 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: cc/tiles/checker_image_tracker.cc
diff --git a/cc/tiles/checker_image_tracker.cc b/cc/tiles/checker_image_tracker.cc
new file mode 100644
index 0000000000000000000000000000000000000000..79ba7494292879edb8e923cedb7d74caf0989b53
--- /dev/null
+++ b/cc/tiles/checker_image_tracker.cc
@@ -0,0 +1,157 @@
+// Copyright 2016 The Chromium Authors. All rights reserved.
vmpstr 2017/02/03 23:42:32 2017
Khushal 2017/02/07 00:25:32 Done.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "cc/tiles/checker_image_tracker.h"
+
+#include "base/bind.h"
+#include "cc/playback/raster_source.h"
+#include "cc/tiles/picture_layer_tiling.h"
+#include "cc/tiles/prioritized_tile.h"
+#include "cc/tiles/tile.h"
+#include "cc/trees/layer_tree_impl.h"
+
+namespace cc {
+namespace {
+// The minimum size of an image that we should consider checkering.
+size_t kMinImageSizeToCheckerBytes = 512 * 1024;
+} // namespace
+
+CheckerImageTracker::CheckerImageTracker(ImageController* image_controller,
+ CheckerImageTrackerClient* client,
+ bool enable_checker_imaging)
+ : image_controller_(image_controller),
+ client_(client),
+ enable_checker_imaging_(enable_checker_imaging),
+ weak_factory_(this) {}
+
+CheckerImageTracker::~CheckerImageTracker() {
+ // Unlock all images pending decode requests.
+ for (auto it : image_id_to_decode_request_id_) {
vmpstr 2017/02/03 23:42:32 nit: no braces
Khushal 2017/02/07 00:25:32 Done.
+ image_controller_->UnlockImageDecode(it.second);
+ }
+}
+
+void CheckerImageTracker::FilterImagesForCheckeringForTile(
+ const PrioritizedTile& prioritized_tile,
vmpstr 2017/02/03 23:42:32 I'd prefer if we don't expose prioritized tile her
Khushal 2017/02/07 00:25:32 Awesome suggestion, eliminating all of these makes
+ std::vector<DrawImage>* images,
+ std::unordered_set<ImageId>* checkered_images) {
+ DCHECK(images->empty());
+ DCHECK(checkered_images->empty());
+
+ Tile* tile = prioritized_tile.tile();
+ prioritized_tile.raster_source()->GetDiscardableImagesInRect(
+ tile->enclosing_layer_rect(), tile->contents_scale(), images);
+ WhichTree tree = tile->tiling()->tree();
+
+ for (std::vector<DrawImage>::iterator it = images->begin();
+ it != images->end();) {
+ const sk_sp<const SkImage> image = it->image();
+ if (AnalyzeImageForCheckeringAndScheduleDecodeIfNecessary(image, tree)) {
+ checkered_images->insert(image->uniqueID());
+ it = images->erase(it);
+ } else {
+ ++it;
+ }
+ }
+}
+
+void CheckerImageTracker::AddInvalidationForCheckerImages(
vmpstr 2017/02/03 23:42:32 I think this should be something like Region Take
Khushal 2017/02/07 00:25:32 Great suggestion. Can't return the region since on
+ LayerTreeImpl* sync_tree) {
+ DCHECK(images_invalidated_on_current_sync_tree_.empty())
+ << "Can not invalidate again on the sync tree";
+
+ sync_tree->InvalidateRegionForImages(images_pending_invalidation_);
+ images_invalidated_on_current_sync_tree_.swap(images_pending_invalidation_);
vmpstr 2017/02/03 23:42:32 Should images_pending_invalidation_ be cleared her
Khushal 2017/02/07 00:25:32 Hmmm, there is a DCHECK above to assert that |imag
+}
+
+void CheckerImageTracker::DidActivateSyncTree() {
+ for (auto image_id : images_invalidated_on_current_sync_tree_) {
+ auto it = image_id_to_decode_request_id_.find(image_id);
+ image_controller_->UnlockImageDecode(it->second);
+ image_id_to_decode_request_id_.erase(it);
+ }
+
+ images_invalidated_on_current_sync_tree_.clear();
+}
+
+void CheckerImageTracker::DidFinishImageDecode(
+ ImageId image_id,
+ ImageController::ImageDecodeRequestId request_id) {
+ TRACE_EVENT_ASYNC_END0("cc", "CheckerImageTracker::DeferImageDecode",
+ image_id);
+
+ auto it = pending_image_decodes_.find(image_id);
+ DCHECK(it != pending_image_decodes_.end());
+ pending_image_decodes_.erase(it);
vmpstr 2017/02/03 23:42:32 We typically write this type of pattern as: DCHEC
Khushal 2017/02/07 00:25:32 Done.
+
+ images_decoded_once_.insert(image_id);
+ images_pending_invalidation_.insert(image_id);
+ client_->NeedsInvalidationForCheckerImagedTiles();
+}
+
+bool CheckerImageTracker::AnalyzeImageForCheckeringAndScheduleDecodeIfNecessary(
vmpstr 2017/02/03 23:42:32 I think this name makes it clear that this should
Khushal 2017/02/07 00:25:32 Done.
+ const sk_sp<const SkImage> image,
+ WhichTree tree) {
+ TRACE_EVENT1("cc", "CheckerImageTracker::AnalyzeImageForCheckering",
+ "image_id", image->uniqueID());
+ if (!enable_checker_imaging_) {
vmpstr 2017/02/03 23:42:32 nit (here and elsewhere), remove braces from singl
Khushal 2017/02/07 00:25:32 Done.
+ return false;
+ }
+
+ // If the image doesn't need to be decoded.
+ if (!image->isLazyGenerated()) {
vmpstr 2017/02/03 23:42:32 If this is coming from discardable image map, then
Khushal 2017/02/07 00:25:32 Done.
+ return false;
+ }
+
+ // If a decode request is pending for this image, continue checkering it.
+ if (pending_image_decodes_.find(image->uniqueID()) !=
+ pending_image_decodes_.end()) {
+ return true;
+ }
+
+ // If the image is pending invalidation, continue checkering it. All tiles
+ // for these images will be invalidated on the next pending tree.
+ if (images_pending_invalidation_.find(image->uniqueID()) !=
+ images_pending_invalidation_.end()) {
+ return true;
+ }
+
+ // If the image was invalidated on the current sync tree and the tile is
+ // for the active tree, continue checkering it on the active tree to ensure
+ // the image update is atomic for the frame.
+ if (images_invalidated_on_current_sync_tree_.count(image->uniqueID()) != 0 &&
+ tree == WhichTree::ACTIVE_TREE) {
vmpstr 2017/02/03 23:42:32 Check the tree first, since it's much quicker.
Khushal 2017/02/07 00:25:32 Done.
+ return true;
+ }
+
+ // If the image has been decoded once before, don't checker it again.
+ if (images_decoded_once_.find(image->uniqueID()) !=
+ images_decoded_once_.end()) {
+ return false;
+ }
+
+ base::CheckedNumeric<size_t> checked_size = 4;
+ checked_size *= image->width();
+ checked_size *= image->height();
+ size_t image_size =
+ checked_size.ValueOrDefault(std::numeric_limits<size_t>::max());
+ bool defer_image_decode = image_size >= kMinImageSizeToCheckerBytes;
+
+ if (defer_image_decode) {
vmpstr 2017/02/03 23:42:32 if (!defer_image_decode) return false; ...
Khushal 2017/02/07 00:25:32 Simpler now?
+ ImageId image_id = image->uniqueID();
+ TRACE_EVENT_ASYNC_BEGIN0("cc", "CheckerImageTracker::DeferImageDecode",
+ image_id);
+ DCHECK_EQ(image_id_to_decode_request_id_.count(image_id), 0U);
+
+ image_id_to_decode_request_id_[image_id] =
+ image_controller_->QueueImageDecode(
+ image, base::Bind(&CheckerImageTracker::DidFinishImageDecode,
+ weak_factory_.GetWeakPtr(), image_id));
+ pending_image_decodes_.insert(image_id);
+ }
+
+ return defer_image_decode;
+}
+
+} // namespace cc

Powered by Google App Engine
This is Rietveld 408576698