OLD | NEW |
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 |
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
56 client)); | 56 client)); |
57 } | 57 } |
58 | 58 |
59 PictureLayerTiling::PictureLayerTiling(float contents_scale, | 59 PictureLayerTiling::PictureLayerTiling(float contents_scale, |
60 const gfx::Size& layer_bounds, | 60 const gfx::Size& layer_bounds, |
61 PictureLayerTilingClient* client) | 61 PictureLayerTilingClient* client) |
62 : contents_scale_(contents_scale), | 62 : contents_scale_(contents_scale), |
63 layer_bounds_(layer_bounds), | 63 layer_bounds_(layer_bounds), |
64 resolution_(NON_IDEAL_RESOLUTION), | 64 resolution_(NON_IDEAL_RESOLUTION), |
65 client_(client), | 65 client_(client), |
66 tiling_data_(gfx::Size(), gfx::Rect(), true), | 66 tiling_data_(gfx::Size(), gfx::Size(), true), |
67 last_impl_frame_time_in_seconds_(0.0), | 67 last_impl_frame_time_in_seconds_(0.0), |
68 eviction_tiles_cache_valid_(false), | 68 eviction_tiles_cache_valid_(false), |
69 eviction_cache_tree_priority_(SAME_PRIORITY_FOR_BOTH_TREES) { | 69 eviction_cache_tree_priority_(SAME_PRIORITY_FOR_BOTH_TREES) { |
70 gfx::Size content_bounds = | 70 gfx::Size content_bounds = |
71 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds, contents_scale)); | 71 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds, contents_scale)); |
72 gfx::Size tile_size = client_->CalculateTileSize(content_bounds); | 72 gfx::Size tile_size = client_->CalculateTileSize(content_bounds); |
73 | 73 |
74 DCHECK(!gfx::ToFlooredSize( | 74 DCHECK(!gfx::ToFlooredSize( |
75 gfx::ScaleSize(layer_bounds, contents_scale)).IsEmpty()) << | 75 gfx::ScaleSize(layer_bounds, contents_scale)).IsEmpty()) << |
76 "Tiling created with scale too small as contents become empty." << | 76 "Tiling created with scale too small as contents become empty." << |
77 " Layer bounds: " << layer_bounds.ToString() << | 77 " Layer bounds: " << layer_bounds.ToString() << |
78 " Contents scale: " << contents_scale; | 78 " Contents scale: " << contents_scale; |
79 | 79 |
80 tiling_data_.SetTilingRect(gfx::Rect(content_bounds)); | 80 tiling_data_.SetTilingSize(content_bounds); |
81 tiling_data_.SetMaxTextureSize(tile_size); | 81 tiling_data_.SetMaxTextureSize(tile_size); |
82 } | 82 } |
83 | 83 |
84 PictureLayerTiling::~PictureLayerTiling() { | 84 PictureLayerTiling::~PictureLayerTiling() { |
85 } | 85 } |
86 | 86 |
87 void PictureLayerTiling::SetClient(PictureLayerTilingClient* client) { | 87 void PictureLayerTiling::SetClient(PictureLayerTilingClient* client) { |
88 client_ = client; | 88 client_ = client; |
89 } | 89 } |
90 | 90 |
91 gfx::Rect PictureLayerTiling::TilingRect() const { | |
92 return tiling_data_.tiling_rect(); | |
93 } | |
94 | |
95 Tile* PictureLayerTiling::CreateTile(int i, | 91 Tile* PictureLayerTiling::CreateTile(int i, |
96 int j, | 92 int j, |
97 const PictureLayerTiling* twin_tiling) { | 93 const PictureLayerTiling* twin_tiling) { |
98 TileMapKey key(i, j); | 94 TileMapKey key(i, j); |
99 DCHECK(tiles_.find(key) == tiles_.end()); | 95 DCHECK(tiles_.find(key) == tiles_.end()); |
100 | 96 |
101 gfx::Rect paint_rect = tiling_data_.TileBoundsWithBorder(i, j); | 97 gfx::Rect paint_rect = tiling_data_.TileBoundsWithBorder(i, j); |
102 gfx::Rect tile_rect = paint_rect; | 98 gfx::Rect tile_rect = paint_rect; |
103 tile_rect.set_size(tiling_data_.max_texture_size()); | 99 tile_rect.set_size(tiling_data_.max_texture_size()); |
104 | 100 |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
147 layer_bounds_ = new_layer_bounds; | 143 layer_bounds_ = new_layer_bounds; |
148 | 144 |
149 gfx::Size content_bounds = | 145 gfx::Size content_bounds = |
150 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds_, contents_scale_)); | 146 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds_, contents_scale_)); |
151 gfx::Size tile_size = tiling_data_.max_texture_size(); | 147 gfx::Size tile_size = tiling_data_.max_texture_size(); |
152 | 148 |
153 if (layer_bounds_ != old_layer_bounds) { | 149 if (layer_bounds_ != old_layer_bounds) { |
154 // Drop tiles outside the new layer bounds if the layer shrank. | 150 // Drop tiles outside the new layer bounds if the layer shrank. |
155 SetLiveTilesRect( | 151 SetLiveTilesRect( |
156 gfx::IntersectRects(live_tiles_rect_, gfx::Rect(content_bounds))); | 152 gfx::IntersectRects(live_tiles_rect_, gfx::Rect(content_bounds))); |
157 tiling_data_.SetTilingRect(gfx::Rect(content_bounds)); | 153 tiling_data_.SetTilingSize(content_bounds); |
158 tile_size = client_->CalculateTileSize(content_bounds); | 154 tile_size = client_->CalculateTileSize(content_bounds); |
159 } | 155 } |
160 | 156 |
161 if (tile_size != tiling_data_.max_texture_size()) { | 157 if (tile_size != tiling_data_.max_texture_size()) { |
162 tiling_data_.SetMaxTextureSize(tile_size); | 158 tiling_data_.SetMaxTextureSize(tile_size); |
163 // When the tile size changes, the TilingData positions no longer work | 159 // When the tile size changes, the TilingData positions no longer work |
164 // as valid keys to the TileMap, so just drop all tiles. | 160 // as valid keys to the TileMap, so just drop all tiles. |
165 Reset(); | 161 Reset(); |
166 } else { | 162 } else { |
167 Invalidate(layer_invalidation); | 163 Invalidate(layer_invalidation); |
(...skipping 72 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
240 return; | 236 return; |
241 | 237 |
242 dest_to_content_scale_ = tiling_->contents_scale_ / dest_scale; | 238 dest_to_content_scale_ = tiling_->contents_scale_ / dest_scale; |
243 | 239 |
244 gfx::Rect content_rect = | 240 gfx::Rect content_rect = |
245 gfx::ScaleToEnclosingRect(dest_rect_, | 241 gfx::ScaleToEnclosingRect(dest_rect_, |
246 dest_to_content_scale_, | 242 dest_to_content_scale_, |
247 dest_to_content_scale_); | 243 dest_to_content_scale_); |
248 // IndexFromSrcCoord clamps to valid tile ranges, so it's necessary to | 244 // IndexFromSrcCoord clamps to valid tile ranges, so it's necessary to |
249 // check for non-intersection first. | 245 // check for non-intersection first. |
250 content_rect.Intersect(tiling_->TilingRect()); | 246 content_rect.Intersect(gfx::Rect(tiling_->tiling_size())); |
251 if (content_rect.IsEmpty()) | 247 if (content_rect.IsEmpty()) |
252 return; | 248 return; |
253 | 249 |
254 left_ = tiling_->tiling_data_.TileXIndexFromSrcCoord(content_rect.x()); | 250 left_ = tiling_->tiling_data_.TileXIndexFromSrcCoord(content_rect.x()); |
255 top_ = tiling_->tiling_data_.TileYIndexFromSrcCoord(content_rect.y()); | 251 top_ = tiling_->tiling_data_.TileYIndexFromSrcCoord(content_rect.y()); |
256 right_ = tiling_->tiling_data_.TileXIndexFromSrcCoord( | 252 right_ = tiling_->tiling_data_.TileXIndexFromSrcCoord( |
257 content_rect.right() - 1); | 253 content_rect.right() - 1); |
258 bottom_ = tiling_->tiling_data_.TileYIndexFromSrcCoord( | 254 bottom_ = tiling_->tiling_data_.TileYIndexFromSrcCoord( |
259 content_rect.bottom() - 1); | 255 content_rect.bottom() - 1); |
260 | 256 |
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
341 } | 337 } |
342 | 338 |
343 gfx::RectF PictureLayerTiling::CoverageIterator::texture_rect() const { | 339 gfx::RectF PictureLayerTiling::CoverageIterator::texture_rect() const { |
344 gfx::PointF tex_origin = | 340 gfx::PointF tex_origin = |
345 tiling_->tiling_data_.TileBoundsWithBorder(tile_i_, tile_j_).origin(); | 341 tiling_->tiling_data_.TileBoundsWithBorder(tile_i_, tile_j_).origin(); |
346 | 342 |
347 // Convert from dest space => content space => texture space. | 343 // Convert from dest space => content space => texture space. |
348 gfx::RectF texture_rect(current_geometry_rect_); | 344 gfx::RectF texture_rect(current_geometry_rect_); |
349 texture_rect.Scale(dest_to_content_scale_, | 345 texture_rect.Scale(dest_to_content_scale_, |
350 dest_to_content_scale_); | 346 dest_to_content_scale_); |
351 texture_rect.Intersect(tiling_->TilingRect()); | 347 texture_rect.Intersect(gfx::Rect(tiling_->tiling_size())); |
352 if (texture_rect.IsEmpty()) | 348 if (texture_rect.IsEmpty()) |
353 return texture_rect; | 349 return texture_rect; |
354 texture_rect.Offset(-tex_origin.OffsetFromOrigin()); | 350 texture_rect.Offset(-tex_origin.OffsetFromOrigin()); |
355 | 351 |
356 return texture_rect; | 352 return texture_rect; |
357 } | 353 } |
358 | 354 |
359 gfx::Size PictureLayerTiling::CoverageIterator::texture_size() const { | 355 gfx::Size PictureLayerTiling::CoverageIterator::texture_size() const { |
360 return tiling_->tiling_data_.max_texture_size(); | 356 return tiling_->tiling_data_.max_texture_size(); |
361 } | 357 } |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
423 const gfx::Transform& draw_transform) { | 419 const gfx::Transform& draw_transform) { |
424 if (!NeedsUpdateForFrameAtTime(current_frame_time_in_seconds)) { | 420 if (!NeedsUpdateForFrameAtTime(current_frame_time_in_seconds)) { |
425 // This should never be zero for the purposes of has_ever_been_updated(). | 421 // This should never be zero for the purposes of has_ever_been_updated(). |
426 DCHECK_NE(current_frame_time_in_seconds, 0.0); | 422 DCHECK_NE(current_frame_time_in_seconds, 0.0); |
427 return; | 423 return; |
428 } | 424 } |
429 | 425 |
430 gfx::Rect visible_rect_in_content_space = | 426 gfx::Rect visible_rect_in_content_space = |
431 gfx::ScaleToEnclosingRect(visible_layer_rect, contents_scale_); | 427 gfx::ScaleToEnclosingRect(visible_layer_rect, contents_scale_); |
432 | 428 |
433 if (TilingRect().IsEmpty()) { | 429 if (tiling_size().IsEmpty()) { |
434 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds; | 430 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds; |
435 last_visible_rect_in_content_space_ = visible_rect_in_content_space; | 431 last_visible_rect_in_content_space_ = visible_rect_in_content_space; |
436 return; | 432 return; |
437 } | 433 } |
438 | 434 |
439 size_t max_tiles_for_interest_area = client_->GetMaxTilesForInterestArea(); | 435 size_t max_tiles_for_interest_area = client_->GetMaxTilesForInterestArea(); |
440 | 436 |
441 gfx::Size tile_size = tiling_data_.max_texture_size(); | 437 gfx::Size tile_size = tiling_data_.max_texture_size(); |
442 int64 eventually_rect_area = | 438 int64 eventually_rect_area = |
443 max_tiles_for_interest_area * tile_size.width() * tile_size.height(); | 439 max_tiles_for_interest_area * tile_size.width() * tile_size.height(); |
444 | 440 |
445 gfx::Rect skewport = ComputeSkewport(current_frame_time_in_seconds, | 441 gfx::Rect skewport = ComputeSkewport(current_frame_time_in_seconds, |
446 visible_rect_in_content_space); | 442 visible_rect_in_content_space); |
447 DCHECK(skewport.Contains(visible_rect_in_content_space)); | 443 DCHECK(skewport.Contains(visible_rect_in_content_space)); |
448 | 444 |
449 gfx::Rect eventually_rect = | 445 gfx::Rect eventually_rect = |
450 ExpandRectEquallyToAreaBoundedBy(visible_rect_in_content_space, | 446 ExpandRectEquallyToAreaBoundedBy(visible_rect_in_content_space, |
451 eventually_rect_area, | 447 eventually_rect_area, |
452 TilingRect(), | 448 gfx::Rect(tiling_size()), |
453 &expansion_cache_); | 449 &expansion_cache_); |
454 | 450 |
455 DCHECK(eventually_rect.IsEmpty() || TilingRect().Contains(eventually_rect)); | 451 DCHECK(eventually_rect.IsEmpty() || |
| 452 gfx::Rect(tiling_size()).Contains(eventually_rect)) |
| 453 << "tiling_size: " << tiling_size().ToString() |
| 454 << " eventually_rect: " << eventually_rect.ToString(); |
456 | 455 |
457 SetLiveTilesRect(eventually_rect); | 456 SetLiveTilesRect(eventually_rect); |
458 | 457 |
459 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds; | 458 last_impl_frame_time_in_seconds_ = current_frame_time_in_seconds; |
460 last_visible_rect_in_content_space_ = visible_rect_in_content_space; | 459 last_visible_rect_in_content_space_ = visible_rect_in_content_space; |
461 | 460 |
462 current_visible_rect_in_content_space_ = visible_rect_in_content_space; | 461 current_visible_rect_in_content_space_ = visible_rect_in_content_space; |
463 current_skewport_ = skewport; | 462 current_skewport_ = skewport; |
464 current_eventually_rect_ = eventually_rect; | 463 current_eventually_rect_ = eventually_rect; |
465 eviction_tiles_cache_valid_ = false; | 464 eviction_tiles_cache_valid_ = false; |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
553 TilePriority priority(resolution_, | 552 TilePriority priority(resolution_, |
554 TilePriority::SOON, | 553 TilePriority::SOON, |
555 tile->priority(tree).distance_to_visible); | 554 tile->priority(tree).distance_to_visible); |
556 tile->SetPriority(tree, priority); | 555 tile->SetPriority(tree, priority); |
557 } | 556 } |
558 } | 557 } |
559 | 558 |
560 void PictureLayerTiling::SetLiveTilesRect( | 559 void PictureLayerTiling::SetLiveTilesRect( |
561 const gfx::Rect& new_live_tiles_rect) { | 560 const gfx::Rect& new_live_tiles_rect) { |
562 DCHECK(new_live_tiles_rect.IsEmpty() || | 561 DCHECK(new_live_tiles_rect.IsEmpty() || |
563 TilingRect().Contains(new_live_tiles_rect)); | 562 gfx::Rect(tiling_size()).Contains(new_live_tiles_rect)) |
| 563 << "tiling_size: " << tiling_size().ToString() |
| 564 << " new_live_tiles_rect: " << new_live_tiles_rect.ToString(); |
564 if (live_tiles_rect_ == new_live_tiles_rect) | 565 if (live_tiles_rect_ == new_live_tiles_rect) |
565 return; | 566 return; |
566 | 567 |
567 // Iterate to delete all tiles outside of our new live_tiles rect. | 568 // Iterate to delete all tiles outside of our new live_tiles rect. |
568 for (TilingData::DifferenceIterator iter(&tiling_data_, | 569 for (TilingData::DifferenceIterator iter(&tiling_data_, |
569 live_tiles_rect_, | 570 live_tiles_rect_, |
570 new_live_tiles_rect); | 571 new_live_tiles_rect); |
571 iter; | 572 iter; |
572 ++iter) { | 573 ++iter) { |
573 TileMapKey key(iter.index()); | 574 TileMapKey key(iter.index()); |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
616 // corresponding PictureLayerImpl and any in flight raster jobs go out of | 617 // corresponding PictureLayerImpl and any in flight raster jobs go out of |
617 // scope. | 618 // scope. |
618 it->second->set_picture_pile(active_pile); | 619 it->second->set_picture_pile(active_pile); |
619 } | 620 } |
620 } | 621 } |
621 | 622 |
622 scoped_ptr<base::Value> PictureLayerTiling::AsValue() const { | 623 scoped_ptr<base::Value> PictureLayerTiling::AsValue() const { |
623 scoped_ptr<base::DictionaryValue> state(new base::DictionaryValue()); | 624 scoped_ptr<base::DictionaryValue> state(new base::DictionaryValue()); |
624 state->SetInteger("num_tiles", tiles_.size()); | 625 state->SetInteger("num_tiles", tiles_.size()); |
625 state->SetDouble("content_scale", contents_scale_); | 626 state->SetDouble("content_scale", contents_scale_); |
626 state->Set("tiling_rect", MathUtil::AsValue(TilingRect()).release()); | 627 state->Set("tiling_size", MathUtil::AsValue(tiling_size()).release()); |
627 return state.PassAs<base::Value>(); | 628 return state.PassAs<base::Value>(); |
628 } | 629 } |
629 | 630 |
630 size_t PictureLayerTiling::GPUMemoryUsageInBytes() const { | 631 size_t PictureLayerTiling::GPUMemoryUsageInBytes() const { |
631 size_t amount = 0; | 632 size_t amount = 0; |
632 for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it) { | 633 for (TileMap::const_iterator it = tiles_.begin(); it != tiles_.end(); ++it) { |
633 const Tile* tile = it->second.get(); | 634 const Tile* tile = it->second.get(); |
634 amount += tile->GPUMemoryUsageInBytes(); | 635 amount += tile->GPUMemoryUsageInBytes(); |
635 } | 636 } |
636 return amount; | 637 return amount; |
(...skipping 326 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
963 tiling_->UpdateEvictionCacheIfNeeded(tree_priority_); | 964 tiling_->UpdateEvictionCacheIfNeeded(tree_priority_); |
964 tile_iterator_ = tiling_->eviction_tiles_cache_.begin(); | 965 tile_iterator_ = tiling_->eviction_tiles_cache_.begin(); |
965 is_valid_ = true; | 966 is_valid_ = true; |
966 if (tile_iterator_ != tiling_->eviction_tiles_cache_.end() && | 967 if (tile_iterator_ != tiling_->eviction_tiles_cache_.end() && |
967 !(*tile_iterator_)->HasResources()) { | 968 !(*tile_iterator_)->HasResources()) { |
968 ++(*this); | 969 ++(*this); |
969 } | 970 } |
970 } | 971 } |
971 | 972 |
972 } // namespace cc | 973 } // namespace cc |
OLD | NEW |