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.
5 #include "cc/resources/picture_layer_tiling_set.h"
10 #include "cc/resources/resource_pool.h"
11 #include "cc/resources/resource_provider.h"
12 #include "cc/test/fake_output_surface.h"
13 #include "cc/test/fake_output_surface_client.h"
14 #include "cc/test/fake_picture_layer_tiling_client.h"
15 #include "cc/test/fake_tile_manager_client.h"
16 #include "cc/test/test_shared_bitmap_manager.h"
17 #include "testing/gtest/include/gtest/gtest.h"
18 #include "ui/gfx/size_conversions.h"
23 TEST(PictureLayerTilingSetTest
, NoResources
) {
24 FakePictureLayerTilingClient client
;
25 gfx::Size
layer_bounds(1000, 800);
26 PictureLayerTilingSet
set(&client
, layer_bounds
);
27 client
.SetTileSize(gfx::Size(256, 256));
33 float contents_scale
= 2.0;
34 gfx::Size
content_bounds(
35 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds
, contents_scale
)));
36 gfx::Rect
content_rect(content_bounds
);
38 Region
remaining(content_rect
);
39 PictureLayerTilingSet::CoverageIterator
iter(
44 for (; iter
; ++iter
) {
45 gfx::Rect geometry_rect
= iter
.geometry_rect();
46 EXPECT_TRUE(content_rect
.Contains(geometry_rect
));
47 ASSERT_TRUE(remaining
.Contains(geometry_rect
));
48 remaining
.Subtract(geometry_rect
);
50 // No tiles have resources, so no iter represents a real tile.
53 EXPECT_TRUE(remaining
.IsEmpty());
56 class PictureLayerTilingSetTestWithResources
: public testing::Test
{
61 float scale_increment
,
62 float ideal_contents_scale
,
63 float expected_scale
) {
64 FakeOutputSurfaceClient output_surface_client
;
65 scoped_ptr
<FakeOutputSurface
> output_surface
=
66 FakeOutputSurface::Create3d();
67 CHECK(output_surface
->BindToClient(&output_surface_client
));
69 scoped_ptr
<SharedBitmapManager
> shared_bitmap_manager(
70 new TestSharedBitmapManager());
71 scoped_ptr
<ResourceProvider
> resource_provider
= ResourceProvider::Create(
72 output_surface
.get(), shared_bitmap_manager
.get(), 0, false, 1, false);
74 FakePictureLayerTilingClient
client(resource_provider
.get());
75 client
.SetTileSize(gfx::Size(256, 256));
76 gfx::Size
layer_bounds(1000, 800);
77 PictureLayerTilingSet
set(&client
, layer_bounds
);
79 float scale
= min_scale
;
80 for (int i
= 0; i
< num_tilings
; ++i
, scale
+= scale_increment
) {
81 PictureLayerTiling
* tiling
= set
.AddTiling(scale
);
82 tiling
->CreateAllTilesForTesting();
83 std::vector
<Tile
*> tiles
= tiling
->AllTilesForTesting();
84 client
.tile_manager()->InitializeTilesWithResourcesForTesting(tiles
);
87 float max_contents_scale
= scale
;
88 gfx::Size
content_bounds(
89 gfx::ToCeiledSize(gfx::ScaleSize(layer_bounds
, max_contents_scale
)));
90 gfx::Rect
content_rect(content_bounds
);
92 Region
remaining(content_rect
);
93 PictureLayerTilingSet::CoverageIterator
iter(
97 ideal_contents_scale
);
98 for (; iter
; ++iter
) {
99 gfx::Rect geometry_rect
= iter
.geometry_rect();
100 EXPECT_TRUE(content_rect
.Contains(geometry_rect
));
101 ASSERT_TRUE(remaining
.Contains(geometry_rect
));
102 remaining
.Subtract(geometry_rect
);
104 float scale
= iter
.CurrentTiling()->contents_scale();
105 EXPECT_EQ(expected_scale
, scale
);
112 EXPECT_TRUE(remaining
.IsEmpty());
116 TEST_F(PictureLayerTilingSetTestWithResources
, NoTilings
) {
117 runTest(0, 0.f
, 0.f
, 2.f
, 0.f
);
119 TEST_F(PictureLayerTilingSetTestWithResources
, OneTiling_Smaller
) {
120 runTest(1, 1.f
, 0.f
, 2.f
, 1.f
);
122 TEST_F(PictureLayerTilingSetTestWithResources
, OneTiling_Larger
) {
123 runTest(1, 3.f
, 0.f
, 2.f
, 3.f
);
125 TEST_F(PictureLayerTilingSetTestWithResources
, TwoTilings_Smaller
) {
126 runTest(2, 1.f
, 1.f
, 3.f
, 2.f
);
129 TEST_F(PictureLayerTilingSetTestWithResources
, TwoTilings_SmallerEqual
) {
130 runTest(2, 1.f
, 1.f
, 2.f
, 2.f
);
133 TEST_F(PictureLayerTilingSetTestWithResources
, TwoTilings_LargerEqual
) {
134 runTest(2, 1.f
, 1.f
, 1.f
, 1.f
);
137 TEST_F(PictureLayerTilingSetTestWithResources
, TwoTilings_Larger
) {
138 runTest(2, 2.f
, 8.f
, 1.f
, 2.f
);
141 TEST_F(PictureLayerTilingSetTestWithResources
, ManyTilings_Equal
) {
142 runTest(10, 1.f
, 1.f
, 5.f
, 5.f
);
145 TEST_F(PictureLayerTilingSetTestWithResources
, ManyTilings_NotEqual
) {
146 runTest(10, 1.f
, 1.f
, 4.5f
, 5.f
);
149 class PictureLayerTilingSetSyncTest
: public testing::Test
{
151 PictureLayerTilingSetSyncTest()
152 : tile_size_(gfx::Size(10, 10)),
153 source_bounds_(gfx::Size(30, 20)),
154 target_bounds_(gfx::Size(30, 30)) {
155 source_client_
.SetTileSize(tile_size_
);
156 target_client_
.SetTileSize(tile_size_
);
157 source_
.reset(new PictureLayerTilingSet(&source_client_
, source_bounds_
));
158 target_
.reset(new PictureLayerTilingSet(&target_client_
, target_bounds_
));
161 // Sync from source to target.
162 void SyncTilings(const gfx::Size
& new_bounds
,
163 const Region
& invalidation
,
164 float minimum_scale
) {
165 for (size_t i
= 0; i
< source_
->num_tilings(); ++i
)
166 source_
->tiling_at(i
)->CreateAllTilesForTesting();
167 for (size_t i
= 0; i
< target_
->num_tilings(); ++i
)
168 target_
->tiling_at(i
)->CreateAllTilesForTesting();
170 target_
->SyncTilings(
171 *source_
.get(), new_bounds
, invalidation
, minimum_scale
);
173 void SyncTilings(const gfx::Size
& new_bounds
) {
175 SyncTilings(new_bounds
, invalidation
, 0.f
);
177 void SyncTilings(const gfx::Size
& new_bounds
, const Region
& invalidation
) {
178 SyncTilings(new_bounds
, invalidation
, 0.f
);
180 void SyncTilings(const gfx::Size
& new_bounds
, float minimum_scale
) {
182 SyncTilings(new_bounds
, invalidation
, minimum_scale
);
185 void VerifyTargetEqualsSource(const gfx::Size
& new_bounds
) {
186 ASSERT_FALSE(new_bounds
.IsEmpty());
187 EXPECT_EQ(target_
->num_tilings(), source_
->num_tilings());
188 EXPECT_EQ(target_
->layer_bounds().ToString(), new_bounds
.ToString());
190 for (size_t i
= 0; i
< target_
->num_tilings(); ++i
) {
191 ASSERT_GT(source_
->num_tilings(), i
);
192 const PictureLayerTiling
* source_tiling
= source_
->tiling_at(i
);
193 const PictureLayerTiling
* target_tiling
= target_
->tiling_at(i
);
194 EXPECT_EQ(target_tiling
->layer_bounds().ToString(),
195 new_bounds
.ToString());
196 EXPECT_EQ(source_tiling
->contents_scale(),
197 target_tiling
->contents_scale());
200 EXPECT_EQ(source_
->client(), &source_client_
);
201 EXPECT_EQ(target_
->client(), &target_client_
);
202 ValidateTargetTilingSet();
205 void ValidateTargetTilingSet() {
206 // Tilings should be sorted largest to smallest.
207 if (target_
->num_tilings() > 0) {
208 float last_scale
= target_
->tiling_at(0)->contents_scale();
209 for (size_t i
= 1; i
< target_
->num_tilings(); ++i
) {
210 const PictureLayerTiling
* target_tiling
= target_
->tiling_at(i
);
211 EXPECT_LT(target_tiling
->contents_scale(), last_scale
);
212 last_scale
= target_tiling
->contents_scale();
216 for (size_t i
= 0; i
< target_
->num_tilings(); ++i
)
217 ValidateTiling(target_
->tiling_at(i
), target_client_
.GetPile());
220 void ValidateTiling(const PictureLayerTiling
* tiling
,
221 const PicturePileImpl
* pile
) {
222 if (tiling
->tiling_size().IsEmpty()) {
223 EXPECT_TRUE(tiling
->live_tiles_rect().IsEmpty());
224 } else if (!tiling
->live_tiles_rect().IsEmpty()) {
225 gfx::Rect
tiling_rect(tiling
->tiling_size());
226 EXPECT_TRUE(tiling_rect
.Contains(tiling
->live_tiles_rect()));
229 std::vector
<Tile
*> tiles
= tiling
->AllTilesForTesting();
230 for (size_t i
= 0; i
< tiles
.size(); ++i
) {
231 const Tile
* tile
= tiles
[i
];
233 EXPECT_EQ(tile
->picture_pile(), pile
);
234 EXPECT_TRUE(tile
->content_rect().Intersects(tiling
->live_tiles_rect()))
235 << "All tiles must be inside the live tiles rect."
236 << " Tile rect: " << tile
->content_rect().ToString()
237 << " Live rect: " << tiling
->live_tiles_rect().ToString()
238 << " Scale: " << tiling
->contents_scale();
241 for (PictureLayerTiling::CoverageIterator
iter(
242 tiling
, tiling
->contents_scale(), tiling
->live_tiles_rect());
245 EXPECT_TRUE(*iter
) << "The live tiles rect must be full.";
249 gfx::Size tile_size_
;
251 FakePictureLayerTilingClient source_client_
;
252 gfx::Size source_bounds_
;
253 scoped_ptr
<PictureLayerTilingSet
> source_
;
255 FakePictureLayerTilingClient target_client_
;
256 gfx::Size target_bounds_
;
257 scoped_ptr
<PictureLayerTilingSet
> target_
;
260 TEST_F(PictureLayerTilingSetSyncTest
, EmptyBounds
) {
261 float source_scales
[] = {1.f
, 1.2f
};
262 for (size_t i
= 0; i
< arraysize(source_scales
); ++i
)
263 source_
->AddTiling(source_scales
[i
]);
265 gfx::Size new_bounds
;
266 SyncTilings(new_bounds
);
267 EXPECT_EQ(target_
->num_tilings(), 0u);
268 EXPECT_EQ(target_
->layer_bounds().ToString(), new_bounds
.ToString());
271 TEST_F(PictureLayerTilingSetSyncTest
, AllNew
) {
272 float source_scales
[] = {0.5f
, 1.f
, 1.2f
};
273 for (size_t i
= 0; i
< arraysize(source_scales
); ++i
)
274 source_
->AddTiling(source_scales
[i
]);
275 float target_scales
[] = {0.75f
, 1.4f
, 3.f
};
276 for (size_t i
= 0; i
< arraysize(target_scales
); ++i
)
277 target_
->AddTiling(target_scales
[i
]);
279 gfx::Size
new_bounds(15, 40);
280 SyncTilings(new_bounds
);
281 VerifyTargetEqualsSource(new_bounds
);
284 Tile
* FindTileAtOrigin(PictureLayerTiling
* tiling
) {
285 std::vector
<Tile
*> tiles
= tiling
->AllTilesForTesting();
286 for (size_t i
= 0; i
< tiles
.size(); ++i
) {
287 if (tiles
[i
]->content_rect().origin() == gfx::Point())
293 TEST_F(PictureLayerTilingSetSyncTest
, KeepExisting
) {
294 float source_scales
[] = {0.7f
, 1.f
, 1.1f
, 2.f
};
295 for (size_t i
= 0; i
< arraysize(source_scales
); ++i
)
296 source_
->AddTiling(source_scales
[i
]);
297 float target_scales
[] = {0.5f
, 1.f
, 2.f
};
298 for (size_t i
= 0; i
< arraysize(target_scales
); ++i
)
299 target_
->AddTiling(target_scales
[i
]);
301 PictureLayerTiling
* tiling1
= source_
->TilingAtScale(1.f
);
302 ASSERT_TRUE(tiling1
);
303 tiling1
->CreateAllTilesForTesting();
304 EXPECT_EQ(tiling1
->contents_scale(), 1.f
);
305 Tile
* tile1
= FindTileAtOrigin(tiling1
);
308 PictureLayerTiling
* tiling2
= source_
->TilingAtScale(2.f
);
309 tiling2
->CreateAllTilesForTesting();
310 ASSERT_TRUE(tiling2
);
311 EXPECT_EQ(tiling2
->contents_scale(), 2.f
);
312 Tile
* tile2
= FindTileAtOrigin(tiling2
);
315 gfx::Size
new_bounds(15, 40);
316 SyncTilings(new_bounds
);
317 VerifyTargetEqualsSource(new_bounds
);
319 EXPECT_EQ(tiling1
, source_
->TilingAtScale(1.f
));
320 EXPECT_EQ(tile1
, FindTileAtOrigin(tiling1
));
321 EXPECT_FALSE(tiling1
->live_tiles_rect().IsEmpty());
323 EXPECT_EQ(tiling2
, source_
->TilingAtScale(2.f
));
324 EXPECT_EQ(tile2
, FindTileAtOrigin(tiling2
));
325 EXPECT_FALSE(tiling2
->live_tiles_rect().IsEmpty());
328 TEST_F(PictureLayerTilingSetSyncTest
, EmptySet
) {
329 float target_scales
[] = {0.2f
, 1.f
};
330 for (size_t i
= 0; i
< arraysize(target_scales
); ++i
)
331 target_
->AddTiling(target_scales
[i
]);
333 gfx::Size
new_bounds(15, 40);
334 SyncTilings(new_bounds
);
335 VerifyTargetEqualsSource(new_bounds
);
338 TEST_F(PictureLayerTilingSetSyncTest
, MinimumScale
) {
339 float source_scales
[] = {0.7f
, 1.f
, 1.1f
, 2.f
};
340 for (size_t i
= 0; i
< arraysize(source_scales
); ++i
)
341 source_
->AddTiling(source_scales
[i
]);
342 float target_scales
[] = {0.5f
, 0.7f
, 1.f
, 1.1f
, 2.f
};
343 for (size_t i
= 0; i
< arraysize(target_scales
); ++i
)
344 target_
->AddTiling(target_scales
[i
]);
346 gfx::Size
new_bounds(15, 40);
347 float minimum_scale
= 1.5f
;
348 SyncTilings(new_bounds
, minimum_scale
);
350 EXPECT_EQ(target_
->num_tilings(), 1u);
351 EXPECT_EQ(target_
->tiling_at(0)->contents_scale(), 2.f
);
352 ValidateTargetTilingSet();
355 TEST_F(PictureLayerTilingSetSyncTest
, Invalidation
) {
356 source_
->AddTiling(2.f
);
357 target_
->AddTiling(2.f
);
358 target_
->tiling_at(0)->CreateAllTilesForTesting();
360 Region layer_invalidation
;
361 layer_invalidation
.Union(gfx::Rect(0, 0, 1, 1));
362 layer_invalidation
.Union(gfx::Rect(0, 15, 1, 1));
363 // Out of bounds layer_invalidation.
364 layer_invalidation
.Union(gfx::Rect(100, 100, 1, 1));
366 Region content_invalidation
;
367 for (Region::Iterator
iter(layer_invalidation
); iter
.has_rect();
369 gfx::Rect content_rect
= gfx::ScaleToEnclosingRect(iter
.rect(), 2.f
);
370 content_invalidation
.Union(content_rect
);
373 std::vector
<Tile
*> old_tiles
= target_
->tiling_at(0)->AllTilesForTesting();
374 std::map
<gfx::Point
, scoped_refptr
<Tile
> > old_tile_map
;
375 for (size_t i
= 0; i
< old_tiles
.size(); ++i
)
376 old_tile_map
[old_tiles
[i
]->content_rect().origin()] = old_tiles
[i
];
378 SyncTilings(target_bounds_
, layer_invalidation
);
379 VerifyTargetEqualsSource(target_bounds_
);
381 std::vector
<Tile
*> new_tiles
= target_
->tiling_at(0)->AllTilesForTesting();
382 for (size_t i
= 0; i
< new_tiles
.size(); ++i
) {
383 const Tile
* tile
= new_tiles
[i
];
384 std::map
<gfx::Point
, scoped_refptr
<Tile
> >::iterator find
=
385 old_tile_map
.find(tile
->content_rect().origin());
386 if (content_invalidation
.Intersects(tile
->content_rect()))
387 EXPECT_NE(tile
, find
->second
.get());
389 EXPECT_EQ(tile
, find
->second
.get());
393 TEST_F(PictureLayerTilingSetSyncTest
, TileSizeChange
) {
394 source_
->AddTiling(1.f
);
395 target_
->AddTiling(1.f
);
397 target_
->tiling_at(0)->CreateAllTilesForTesting();
398 std::vector
<Tile
*> original_tiles
=
399 target_
->tiling_at(0)->AllTilesForTesting();
400 EXPECT_GT(original_tiles
.size(), 0u);
401 gfx::Size
new_tile_size(100, 100);
402 target_client_
.SetTileSize(new_tile_size
);
403 EXPECT_NE(target_
->tiling_at(0)->tile_size().ToString(),
404 new_tile_size
.ToString());
406 gfx::Size
new_bounds(15, 40);
407 SyncTilings(new_bounds
);
408 VerifyTargetEqualsSource(new_bounds
);
410 EXPECT_EQ(target_
->tiling_at(0)->tile_size().ToString(),
411 new_tile_size
.ToString());
413 // All old tiles should not be present in new tiles.
414 std::vector
<Tile
*> new_tiles
= target_
->tiling_at(0)->AllTilesForTesting();
415 for (size_t i
= 0; i
< original_tiles
.size(); ++i
) {
416 std::vector
<Tile
*>::iterator find
=
417 std::find(new_tiles
.begin(), new_tiles
.end(), original_tiles
[i
]);
418 EXPECT_TRUE(find
== new_tiles
.end());