• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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
3 // found in the LICENSE file.
4 
5 #ifndef CC_RESOURCES_PICTURE_LAYER_TILING_H_
6 #define CC_RESOURCES_PICTURE_LAYER_TILING_H_
7 
8 #include <set>
9 #include <utility>
10 #include <vector>
11 
12 #include "base/basictypes.h"
13 #include "base/containers/hash_tables.h"
14 #include "base/memory/scoped_ptr.h"
15 #include "cc/base/cc_export.h"
16 #include "cc/base/region.h"
17 #include "cc/base/tiling_data.h"
18 #include "cc/resources/tile.h"
19 #include "cc/resources/tile_priority.h"
20 #include "ui/gfx/rect.h"
21 
22 namespace cc {
23 
24 class PictureLayerTiling;
25 
26 class CC_EXPORT PictureLayerTilingClient {
27  public:
28   // Create a tile at the given content_rect (in the contents scale of the
29   // tiling) This might return null if the client cannot create such a tile.
30   virtual scoped_refptr<Tile> CreateTile(
31     PictureLayerTiling* tiling,
32     const gfx::Rect& content_rect) = 0;
33   virtual void UpdatePile(Tile* tile) = 0;
34   virtual gfx::Size CalculateTileSize(
35     const gfx::Size& content_bounds) const = 0;
36   virtual const Region* GetInvalidation() = 0;
37   virtual const PictureLayerTiling* GetTwinTiling(
38       const PictureLayerTiling* tiling) const = 0;
39   virtual PictureLayerTiling* GetRecycledTwinTiling(
40       const PictureLayerTiling* tiling) = 0;
41   virtual size_t GetMaxTilesForInterestArea() const = 0;
42   virtual float GetSkewportTargetTimeInSeconds() const = 0;
43   virtual int GetSkewportExtrapolationLimitInContentPixels() const = 0;
44 
45  protected:
~PictureLayerTilingClient()46   virtual ~PictureLayerTilingClient() {}
47 };
48 
49 class CC_EXPORT PictureLayerTiling {
50  public:
51   class CC_EXPORT TilingRasterTileIterator {
52    public:
53     TilingRasterTileIterator();
54     TilingRasterTileIterator(PictureLayerTiling* tiling, WhichTree tree);
55     ~TilingRasterTileIterator();
56 
57     operator bool() const { return !!current_tile_; }
58     Tile* operator*() { return current_tile_; }
get_type()59     TilePriority::PriorityBin get_type() const { return type_; }
60 
61     TilingRasterTileIterator& operator++();
62 
TileBounds()63     gfx::Rect TileBounds() const {
64       DCHECK(*this);
65       if (type_ == TilePriority::NOW) {
66         return tiling_->tiling_data_.TileBounds(visible_iterator_.index_x(),
67                                                 visible_iterator_.index_y());
68       }
69       return tiling_->tiling_data_.TileBounds(spiral_iterator_.index_x(),
70                                               spiral_iterator_.index_y());
71     }
72 
73    private:
74     void AdvancePhase();
TileNeedsRaster(Tile * tile)75     bool TileNeedsRaster(Tile* tile) const {
76       RasterMode mode = tile->DetermineRasterModeForTree(tree_);
77       return tile->NeedsRasterForMode(mode);
78     }
79 
80     PictureLayerTiling* tiling_;
81 
82     TilePriority::PriorityBin type_;
83     gfx::Rect visible_rect_in_content_space_;
84     gfx::Rect skewport_in_content_space_;
85     gfx::Rect eventually_rect_in_content_space_;
86     gfx::Rect soon_border_rect_in_content_space_;
87     WhichTree tree_;
88 
89     Tile* current_tile_;
90     TilingData::Iterator visible_iterator_;
91     TilingData::SpiralDifferenceIterator spiral_iterator_;
92     bool skewport_processed_;
93   };
94 
95   class CC_EXPORT TilingEvictionTileIterator {
96    public:
97     TilingEvictionTileIterator();
98     TilingEvictionTileIterator(PictureLayerTiling* tiling,
99                                TreePriority tree_priority);
100     ~TilingEvictionTileIterator();
101 
102     operator bool();
103     Tile* operator*();
104     TilingEvictionTileIterator& operator++();
get_type()105     TilePriority::PriorityBin get_type() {
106       DCHECK(*this);
107       const TilePriority& priority =
108           (*tile_iterator_)->priority_for_tree_priority(tree_priority_);
109       return priority.priority_bin;
110     }
111 
112    private:
113     void Initialize();
IsValid()114     bool IsValid() const { return is_valid_; }
115 
116     bool is_valid_;
117     PictureLayerTiling* tiling_;
118     TreePriority tree_priority_;
119     std::vector<Tile*>::iterator tile_iterator_;
120   };
121 
122   ~PictureLayerTiling();
123 
124   // Create a tiling with no tiles.  CreateTiles must be called to add some.
125   static scoped_ptr<PictureLayerTiling> Create(
126       float contents_scale,
127       const gfx::Size& layer_bounds,
128       PictureLayerTilingClient* client);
layer_bounds()129   gfx::Size layer_bounds() const { return layer_bounds_; }
130   void SetLayerBounds(const gfx::Size& layer_bounds);
131   void Invalidate(const Region& layer_region);
132   void RemoveTilesInRegion(const Region& layer_region);
133   void CreateMissingTilesInLiveTilesRect();
134 
135   void SetClient(PictureLayerTilingClient* client);
set_resolution(TileResolution resolution)136   void set_resolution(TileResolution resolution) { resolution_ = resolution; }
resolution()137   TileResolution resolution() const { return resolution_; }
138 
139   gfx::Rect TilingRect() const;
live_tiles_rect()140   gfx::Rect live_tiles_rect() const { return live_tiles_rect_; }
tile_size()141   gfx::Size tile_size() const { return tiling_data_.max_texture_size(); }
contents_scale()142   float contents_scale() const { return contents_scale_; }
143 
TileAt(int i,int j)144   Tile* TileAt(int i, int j) const {
145     TileMap::const_iterator iter = tiles_.find(TileMapKey(i, j));
146     return (iter == tiles_.end()) ? NULL : iter->second.get();
147   }
148 
CreateAllTilesForTesting()149   void CreateAllTilesForTesting() {
150     SetLiveTilesRect(tiling_data_.tiling_rect());
151   }
152 
AllTilesForTesting()153   std::vector<Tile*> AllTilesForTesting() const {
154     std::vector<Tile*> all_tiles;
155     for (TileMap::const_iterator it = tiles_.begin();
156          it != tiles_.end(); ++it)
157       all_tiles.push_back(it->second.get());
158     return all_tiles;
159   }
160 
GetCurrentVisibleRectForTesting()161   const gfx::Rect& GetCurrentVisibleRectForTesting() const {
162     return current_visible_rect_in_content_space_;
163   }
164 
165   // Iterate over all tiles to fill content_rect.  Even if tiles are invalid
166   // (i.e. no valid resource) this tiling should still iterate over them.
167   // The union of all geometry_rect calls for each element iterated over should
168   // exactly equal content_rect and no two geometry_rects should intersect.
169   class CC_EXPORT CoverageIterator {
170    public:
171     CoverageIterator();
172     CoverageIterator(const PictureLayerTiling* tiling,
173         float dest_scale,
174         const gfx::Rect& rect);
175     ~CoverageIterator();
176 
177     // Visible rect (no borders), always in the space of content_rect,
178     // regardless of the contents scale of the tiling.
179     gfx::Rect geometry_rect() const;
180     // Texture rect (in texels) for geometry_rect
181     gfx::RectF texture_rect() const;
182     gfx::Size texture_size() const;
183 
184     // Full rect (including borders) of the current tile, always in the space
185     // of content_rect, regardless of the contents scale of the tiling.
186     gfx::Rect full_tile_geometry_rect() const;
187 
188     Tile* operator->() const { return current_tile_; }
189     Tile* operator*() const { return current_tile_; }
190 
191     CoverageIterator& operator++();
192     operator bool() const { return tile_j_ <= bottom_; }
193 
i()194     int i() const { return tile_i_; }
j()195     int j() const { return tile_j_; }
196 
197    private:
198     const PictureLayerTiling* tiling_;
199     gfx::Rect dest_rect_;
200     float dest_to_content_scale_;
201 
202     Tile* current_tile_;
203     gfx::Rect current_geometry_rect_;
204     int tile_i_;
205     int tile_j_;
206     int left_;
207     int top_;
208     int right_;
209     int bottom_;
210 
211     friend class PictureLayerTiling;
212   };
213 
214   void Reset();
215 
216   void UpdateTilePriorities(WhichTree tree,
217                             const gfx::Rect& visible_layer_rect,
218                             float layer_contents_scale,
219                             double current_frame_time_in_seconds);
220 
221   // Copies the src_tree priority into the dst_tree priority for all tiles.
222   // The src_tree priority is reset to the lowest priority possible.  This
223   // also updates the pile on each tile to be the current client's pile.
224   void DidBecomeActive();
225 
226   // Resets the active priority for all tiles in a tiling, when an active
227   // tiling is becoming recycled. This may include some tiles which are
228   // not in the the pending tiling (due to invalidations). This must
229   // be called before DidBecomeActive, as it resets the active priority
230   // while DidBecomeActive promotes pending priority on a similar set of tiles.
231   void DidBecomeRecycled();
232 
233   void UpdateTilesToCurrentPile();
234 
NeedsUpdateForFrameAtTime(double frame_time_in_seconds)235   bool NeedsUpdateForFrameAtTime(double frame_time_in_seconds) {
236     return frame_time_in_seconds != last_impl_frame_time_in_seconds_;
237   }
238 
239   void GetAllTilesForTracing(std::set<const Tile*>* tiles) const;
240   scoped_ptr<base::Value> AsValue() const;
241   size_t GPUMemoryUsageInBytes() const;
242 
243   struct RectExpansionCache {
244     RectExpansionCache();
245 
246     gfx::Rect previous_start;
247     gfx::Rect previous_bounds;
248     gfx::Rect previous_result;
249     int64 previous_target;
250   };
251 
252   static
253   gfx::Rect ExpandRectEquallyToAreaBoundedBy(
254       const gfx::Rect& starting_rect,
255       int64 target_area,
256       const gfx::Rect& bounding_rect,
257       RectExpansionCache* cache);
258 
has_ever_been_updated()259   bool has_ever_been_updated() const {
260     return last_impl_frame_time_in_seconds_ != 0.0;
261   }
262 
263  protected:
264   friend class CoverageIterator;
265   friend class TilingRasterTileIterator;
266   friend class TilingEvictionTileIterator;
267 
268   typedef std::pair<int, int> TileMapKey;
269   typedef base::hash_map<TileMapKey, scoped_refptr<Tile> > TileMap;
270 
271   PictureLayerTiling(float contents_scale,
272                      const gfx::Size& layer_bounds,
273                      PictureLayerTilingClient* client);
274   void SetLiveTilesRect(const gfx::Rect& live_tiles_rect);
275   Tile* CreateTile(int i, int j, const PictureLayerTiling* twin_tiling);
276   void RemoveTileAt(int i, int j);
277 
278   // Computes a skewport. The calculation extrapolates the last visible
279   // rect and the current visible rect to expand the skewport to where it
280   // would be in |skewport_target_time| seconds. Note that the skewport
281   // is guaranteed to contain the current visible rect.
282   gfx::Rect ComputeSkewport(double current_frame_time_in_seconds,
283                             const gfx::Rect& visible_rect_in_content_space)
284       const;
285 
286   void UpdateEvictionCacheIfNeeded(TreePriority tree_priority);
287   void DoInvalidate(const Region& layer_region, bool recreate_tiles);
288 
289   // Given properties.
290   float contents_scale_;
291   gfx::Size layer_bounds_;
292   TileResolution resolution_;
293   PictureLayerTilingClient* client_;
294 
295   // Internal data.
296   TilingData tiling_data_;
297   TileMap tiles_;  // It is not legal to have a NULL tile in the tiles_ map.
298   gfx::Rect live_tiles_rect_;
299 
300   // State saved for computing velocities based upon finite differences.
301   double last_impl_frame_time_in_seconds_;
302   gfx::Rect last_visible_rect_in_content_space_;
303 
304   gfx::Rect current_visible_rect_in_content_space_;
305   gfx::Rect current_skewport_;
306   gfx::Rect current_eventually_rect_;
307   gfx::Rect current_soon_border_rect_;
308 
309   std::vector<Tile*> eviction_tiles_cache_;
310   bool eviction_tiles_cache_valid_;
311   TreePriority eviction_cache_tree_priority_;
312 
313  private:
314   DISALLOW_ASSIGN(PictureLayerTiling);
315 
316   RectExpansionCache expansion_cache_;
317 };
318 
319 }  // namespace cc
320 
321 #endif  // CC_RESOURCES_PICTURE_LAYER_TILING_H_
322