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

Side by Side Diff: cc/resources/picture_layer_tiling.cc

Issue 183663003: cc: Add tiling raster tile iterators. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 9 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 unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « cc/resources/picture_layer_tiling.h ('k') | cc/resources/picture_layer_tiling_perftest.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 The Chromium Authors. All rights reserved. 1 // Copyright 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "cc/resources/picture_layer_tiling.h" 5 #include "cc/resources/picture_layer_tiling.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <cmath> 8 #include <cmath>
9 #include <limits> 9 #include <limits>
10 10
11 #include "base/debug/trace_event.h" 11 #include "base/debug/trace_event.h"
12 #include "cc/base/math_util.h" 12 #include "cc/base/math_util.h"
13 #include "cc/resources/tile.h"
14 #include "cc/resources/tile_priority.h"
13 #include "ui/gfx/point_conversions.h" 15 #include "ui/gfx/point_conversions.h"
14 #include "ui/gfx/rect_conversions.h" 16 #include "ui/gfx/rect_conversions.h"
15 #include "ui/gfx/safe_integer_conversions.h" 17 #include "ui/gfx/safe_integer_conversions.h"
16 #include "ui/gfx/size_conversions.h" 18 #include "ui/gfx/size_conversions.h"
17 19
18 namespace cc { 20 namespace cc {
21 namespace {
22
23 class HighPriorityFirstOrder {
24 public:
25 explicit HighPriorityFirstOrder(WhichTree tree) : tree_(tree) {}
26 ~HighPriorityFirstOrder() {}
27
28 bool operator()(const Tile* a, const Tile* b) const {
29 const TilePriority& a_priority = a->priority(tree_);
30 const TilePriority& b_priority = b->priority(tree_);
31
32 return (a_priority.priority_bin < b_priority.priority_bin) ||
33 (a_priority.priority_bin == b_priority.priority_bin &&
34 a_priority.distance_to_visible < b_priority.distance_to_visible);
35 }
36
37 private:
38 WhichTree tree_;
39 };
40
41 class LowPriorityFirstOrder {
42 public:
43 explicit LowPriorityFirstOrder(WhichTree tree) : tree_(tree) {}
44 ~LowPriorityFirstOrder() {}
45
46 bool operator()(const Tile* a, const Tile* b) const {
47 const TilePriority& a_priority = a->priority(tree_);
48 const TilePriority& b_priority = b->priority(tree_);
49
50 return (a_priority.priority_bin > b_priority.priority_bin) ||
51 (a_priority.priority_bin == b_priority.priority_bin &&
52 a_priority.distance_to_visible > b_priority.distance_to_visible);
53 }
54
55 private:
56 WhichTree tree_;
57 };
58
59 } // namespace
19 60
20 scoped_ptr<PictureLayerTiling> PictureLayerTiling::Create( 61 scoped_ptr<PictureLayerTiling> PictureLayerTiling::Create(
21 float contents_scale, 62 float contents_scale,
22 const gfx::Size& layer_bounds, 63 const gfx::Size& layer_bounds,
23 PictureLayerTilingClient* client) { 64 PictureLayerTilingClient* client) {
24 return make_scoped_ptr(new PictureLayerTiling(contents_scale, 65 return make_scoped_ptr(new PictureLayerTiling(contents_scale,
25 layer_bounds, 66 layer_bounds,
26 client)); 67 client));
27 } 68 }
28 69
(...skipping 28 matching lines...) Expand all
57 } 98 }
58 99
59 gfx::Rect PictureLayerTiling::ContentRect() const { 100 gfx::Rect PictureLayerTiling::ContentRect() const {
60 return gfx::Rect(tiling_data_.total_size()); 101 return gfx::Rect(tiling_data_.total_size());
61 } 102 }
62 103
63 gfx::SizeF PictureLayerTiling::ContentSizeF() const { 104 gfx::SizeF PictureLayerTiling::ContentSizeF() const {
64 return gfx::ScaleSize(layer_bounds_, contents_scale_); 105 return gfx::ScaleSize(layer_bounds_, contents_scale_);
65 } 106 }
66 107
108 bool PictureLayerTiling::HasVisibleTilesAtOrAfterPriority(size_t priority_index)
109 const {
110 return priority_index < visible_tiles_.size();
111 }
112
113 Tile* PictureLayerTiling::RasterTileForPriority(size_t priority_index) {
114 // First, return visible tiles.
115 if (priority_index < visible_tiles_.size())
116 return visible_tiles_[priority_index];
117 priority_index -= visible_tiles_.size();
118
119 // Next, return skewport tiles.
120 if (priority_index < skewport_tiles_.size()) {
121 if (!skewport_tiles_sorted_) {
122 std::sort(skewport_tiles_.begin(),
123 skewport_tiles_.end(),
124 HighPriorityFirstOrder(last_update_tree_));
125 skewport_tiles_sorted_ = true;
126 }
127 return skewport_tiles_[priority_index];
128 }
129 priority_index -= skewport_tiles_.size();
130
131 // Next, return eventually tiles.
132 if (priority_index < eventually_tiles_.size()) {
133 if (!eventually_tiles_sorted_) {
134 std::sort(eventually_tiles_.begin(),
135 eventually_tiles_.end(),
136 HighPriorityFirstOrder(last_update_tree_));
137 eventually_tiles_sorted_ = true;
138 }
139 return eventually_tiles_[priority_index];
140 }
141
142 // If we got here, that means we're out of tiles that need raster.
143 return NULL;
144 }
145
146 Tile* PictureLayerTiling::EvictionTileForPriority(size_t priority_index) {
147 if (priority_index < eviction_tiles_.size()) {
148 if (!eviction_tiles_sorted_) {
149 std::sort(eviction_tiles_.begin(),
150 eviction_tiles_.end(),
151 LowPriorityFirstOrder(last_update_tree_));
152 eviction_tiles_sorted_ = true;
153 }
154 return eviction_tiles_[priority_index];
155 }
156
157 // No more eviction tiles present.
158 return NULL;
159 }
160
67 Tile* PictureLayerTiling::TileAt(int i, int j) const { 161 Tile* PictureLayerTiling::TileAt(int i, int j) const {
68 TileMap::const_iterator iter = tiles_.find(TileMapKey(i, j)); 162 TileMap::const_iterator iter = tiles_.find(TileMapKey(i, j));
69 if (iter == tiles_.end()) 163 if (iter == tiles_.end())
70 return NULL; 164 return NULL;
71 return iter->second.get(); 165 return iter->second.get();
72 } 166 }
73 167
74 void PictureLayerTiling::CreateTile(int i, 168 void PictureLayerTiling::CreateTile(int i,
75 int j, 169 int j,
76 const PictureLayerTiling* twin_tiling) { 170 const PictureLayerTiling* twin_tiling) {
(...skipping 346 matching lines...) Expand 10 before | Expand all | Expand 10 after
423 ContentRect(), 517 ContentRect(),
424 &expansion_cache_); 518 &expansion_cache_);
425 519
426 DCHECK(eventually_rect.IsEmpty() || ContentRect().Contains(eventually_rect)); 520 DCHECK(eventually_rect.IsEmpty() || ContentRect().Contains(eventually_rect));
427 521
428 SetLiveTilesRect(eventually_rect); 522 SetLiveTilesRect(eventually_rect);
429 523
430 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds; 524 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds;
431 last_visible_rect_in_content_space_ = visible_rect_in_content_space; 525 last_visible_rect_in_content_space_ = visible_rect_in_content_space;
432 526
527 visible_tiles_.clear();
528 skewport_tiles_.clear();
529 skewport_tiles_sorted_ = false;
530 eventually_tiles_.clear();
531 eventually_tiles_sorted_ = false;
532 eviction_tiles_.clear();
533 eviction_tiles_sorted_ = false;
534
433 // Assign now priority to all visible tiles. 535 // Assign now priority to all visible tiles.
434 TilePriority now_priority(resolution_, TilePriority::NOW, 0); 536 TilePriority now_priority(resolution_, TilePriority::NOW, 0);
435 for (TilingData::Iterator iter(&tiling_data_, visible_rect_in_content_space); 537 for (TilingData::Iterator iter(&tiling_data_, visible_rect_in_content_space);
436 iter; 538 iter;
437 ++iter) { 539 ++iter) {
438 TileMap::iterator find = tiles_.find(iter.index()); 540 TileMap::iterator find = tiles_.find(iter.index());
439 if (find == tiles_.end()) 541 if (find == tiles_.end())
440 continue; 542 continue;
441 Tile* tile = find->second.get(); 543 Tile* tile = find->second.get();
442 544
443 tile->SetPriority(tree, now_priority); 545 tile->SetPriority(tree, now_priority);
546 visible_tiles_.push_back(tile);
vmpstr 2014/02/27 21:18:34 Doing conditional pushes here (if it actually need
547 eviction_tiles_.push_back(tile);
444 } 548 }
445 549
446 // Assign soon priority to all tiles in the skewport that are not visible. 550 // Assign soon priority to all tiles in the skewport that are not visible.
447 float content_to_screen_scale = 551 float content_to_screen_scale =
448 1.0f / (contents_scale_ * layer_contents_scale); 552 1.0f / (contents_scale_ * layer_contents_scale);
553
449 for (TilingData::DifferenceIterator iter( 554 for (TilingData::DifferenceIterator iter(
450 &tiling_data_, skewport, visible_rect_in_content_space); 555 &tiling_data_, skewport, visible_rect_in_content_space);
451 iter; 556 iter;
452 ++iter) { 557 ++iter) {
453 TileMap::iterator find = tiles_.find(iter.index()); 558 TileMap::iterator find = tiles_.find(iter.index());
454 if (find == tiles_.end()) 559 if (find == tiles_.end())
455 continue; 560 continue;
456 Tile* tile = find->second.get(); 561 Tile* tile = find->second.get();
457 562
458 gfx::Rect tile_bounds = 563 gfx::Rect tile_bounds =
459 tiling_data_.TileBounds(iter.index_x(), iter.index_y()); 564 tiling_data_.TileBounds(iter.index_x(), iter.index_y());
460 565
461 float distance_to_visible = 566 float distance_to_visible =
462 visible_rect_in_content_space.ManhattanInternalDistance(tile_bounds) * 567 visible_rect_in_content_space.ManhattanInternalDistance(tile_bounds) *
463 content_to_screen_scale; 568 content_to_screen_scale;
464 569
465 TilePriority priority(resolution_, TilePriority::SOON, distance_to_visible); 570 TilePriority priority(resolution_, TilePriority::SOON, distance_to_visible);
466 tile->SetPriority(tree, priority); 571 tile->SetPriority(tree, priority);
572 skewport_tiles_.push_back(tile);
573 eviction_tiles_.push_back(tile);
467 } 574 }
468 575
469 // Assign eventually priority to all tiles in the eventually rect that are not 576 // Assign eventually priority to all tiles in the eventually rect that are not
470 // in the skewport. 577 // in the skewport.
471 for (TilingData::DifferenceIterator iter( 578 for (TilingData::DifferenceIterator iter(
472 &tiling_data_, eventually_rect, skewport); 579 &tiling_data_, eventually_rect, skewport);
473 iter; 580 iter;
474 ++iter) { 581 ++iter) {
475 TileMap::iterator find = tiles_.find(iter.index()); 582 TileMap::iterator find = tiles_.find(iter.index());
476 if (find == tiles_.end()) 583 if (find == tiles_.end())
477 continue; 584 continue;
478 Tile* tile = find->second.get(); 585 Tile* tile = find->second.get();
479 586
480 gfx::Rect tile_bounds = 587 gfx::Rect tile_bounds =
481 tiling_data_.TileBounds(iter.index_x(), iter.index_y()); 588 tiling_data_.TileBounds(iter.index_x(), iter.index_y());
482 589
483 float distance_to_visible = 590 float distance_to_visible =
484 visible_rect_in_content_space.ManhattanInternalDistance(tile_bounds) * 591 visible_rect_in_content_space.ManhattanInternalDistance(tile_bounds) *
485 content_to_screen_scale; 592 content_to_screen_scale;
486 TilePriority priority( 593 TilePriority priority(
487 resolution_, TilePriority::EVENTUALLY, distance_to_visible); 594 resolution_, TilePriority::EVENTUALLY, distance_to_visible);
488 tile->SetPriority(tree, priority); 595 tile->SetPriority(tree, priority);
596 eventually_tiles_.push_back(tile);
597 eviction_tiles_.push_back(tile);
489 } 598 }
599
600 last_update_tree_ = tree;
490 } 601 }
491 602
492 void PictureLayerTiling::SetLiveTilesRect( 603 void PictureLayerTiling::SetLiveTilesRect(
493 const gfx::Rect& new_live_tiles_rect) { 604 const gfx::Rect& new_live_tiles_rect) {
494 DCHECK(new_live_tiles_rect.IsEmpty() || 605 DCHECK(new_live_tiles_rect.IsEmpty() ||
495 ContentRect().Contains(new_live_tiles_rect)); 606 ContentRect().Contains(new_live_tiles_rect));
496 if (live_tiles_rect_ == new_live_tiles_rect) 607 if (live_tiles_rect_ == new_live_tiles_rect)
497 return; 608 return;
498 609
499 // Iterate to delete all tiles outside of our new live_tiles rect. 610 // Iterate to delete all tiles outside of our new live_tiles rect.
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
549 client_->UpdatePile(it->second.get()); 660 client_->UpdatePile(it->second.get());
550 } 661 }
551 } 662 }
552 663
553 void PictureLayerTiling::UpdateTilesToCurrentPile() { 664 void PictureLayerTiling::UpdateTilesToCurrentPile() {
554 for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it) { 665 for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it) {
555 client_->UpdatePile(it->second.get()); 666 client_->UpdatePile(it->second.get());
556 } 667 }
557 } 668 }
558 669
670 size_t PictureLayerTiling::RequiredGPUMemoryInBytes() const {
671 size_t amount = 0;
672 for (TilingData::Iterator iter(&tiling_data_,
673 last_visible_rect_in_content_space_);
674 iter;
675 ++iter) {
676 TileMap::const_iterator find = tiles_.find(iter.index());
677 if (find == tiles_.end())
678 continue;
679 Tile* tile = find->second.get();
680 amount += tile->GPUMemoryUsageInBytes();
681 }
682 return amount;
683 }
684
559 scoped_ptr<base::Value> PictureLayerTiling::AsValue() const { 685 scoped_ptr<base::Value> PictureLayerTiling::AsValue() const {
560 scoped_ptr<base::DictionaryValue> state(new base::DictionaryValue()); 686 scoped_ptr<base::DictionaryValue> state(new base::DictionaryValue());
561 state->SetInteger("num_tiles", tiles_.size()); 687 state->SetInteger("num_tiles", tiles_.size());
562 state->SetDouble("content_scale", contents_scale_); 688 state->SetDouble("content_scale", contents_scale_);
563 state->Set("content_bounds", 689 state->Set("content_bounds",
564 MathUtil::AsValue(ContentRect().size()).release()); 690 MathUtil::AsValue(ContentRect().size()).release());
565 return state.PassAs<base::Value>(); 691 return state.PassAs<base::Value>();
566 } 692 }
567 693
568 size_t PictureLayerTiling::GPUMemoryUsageInBytes() const { 694 size_t PictureLayerTiling::GPUMemoryUsageInBytes() const {
(...skipping 147 matching lines...) Expand 10 before | Expand all | Expand 10 after
716 if (delta < event.distance) 842 if (delta < event.distance)
717 break; 843 break;
718 } 844 }
719 845
720 gfx::Rect result(origin_x, origin_y, width, height); 846 gfx::Rect result(origin_x, origin_y, width, height);
721 if (cache) 847 if (cache)
722 cache->previous_result = result; 848 cache->previous_result = result;
723 return result; 849 return result;
724 } 850 }
725 851
852 PictureLayerTiling::TilingRasterTileIterator::TilingRasterTileIterator()
853 : tiling_(NULL), current_index_(0) {}
854
855 PictureLayerTiling::TilingRasterTileIterator::TilingRasterTileIterator(
856 PictureLayerTiling* tiling)
857 : tiling_(tiling), current_index_(0) {
858 Tile* tile = tiling_->RasterTileForPriority(current_index_);
859 if (!tile)
860 return;
861
862 RasterMode raster_mode =
863 tile->DetermineRasterModeForTree(tiling_->last_update_tree_);
864 if (!tile->NeedsRasterForMode(raster_mode))
865 ++(*this);
866 }
867
868 PictureLayerTiling::TilingRasterTileIterator::~TilingRasterTileIterator() {}
869
870 void PictureLayerTiling::TilingRasterTileIterator::operator++() {
871 DCHECK(*this);
872 while (true) {
873 ++current_index_;
874
875 Tile* tile = tiling_->RasterTileForPriority(current_index_);
876 if (!tile)
877 break;
878
879 RasterMode raster_mode =
880 tile->DetermineRasterModeForTree(tiling_->last_update_tree_);
881 if (tile->NeedsRasterForMode(raster_mode))
882 break;
883 }
884 }
885
886 PictureLayerTiling::TilingEvictionTileIterator::TilingEvictionTileIterator()
887 : tiling_(NULL), current_index_(0) {}
888
889 PictureLayerTiling::TilingEvictionTileIterator::TilingEvictionTileIterator(
890 PictureLayerTiling* tiling)
891 : tiling_(tiling), current_index_(0) {
892 Tile* tile = tiling_->EvictionTileForPriority(current_index_);
893 if (!tile)
894 return;
895
896 if (!tile->HasResources())
897 ++(*this);
898 }
899
900 PictureLayerTiling::TilingEvictionTileIterator::~TilingEvictionTileIterator() {}
901
902 void PictureLayerTiling::TilingEvictionTileIterator::operator++() {
903 DCHECK(*this);
904 while (true) {
905 ++current_index_;
906
907 Tile* tile = tiling_->EvictionTileForPriority(current_index_);
908 if (!tile || tile->HasResources())
909 break;
910 }
911 }
912
726 } // namespace cc 913 } // namespace cc
OLDNEW
« no previous file with comments | « cc/resources/picture_layer_tiling.h ('k') | cc/resources/picture_layer_tiling_perftest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698