1 // Copyright 2013 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.h"
7 #include "base/memory/ref_counted.h"
8 #include "base/memory/scoped_ptr.h"
9 #include "base/values.h"
10 #include "cc/test/fake_content_layer_client.h"
11 #include "cc/test/skia_common.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13 #include "third_party/skia/include/core/SkBBHFactory.h"
14 #include "third_party/skia/include/core/SkCanvas.h"
15 #include "third_party/skia/include/core/SkGraphics.h"
16 #include "third_party/skia/include/core/SkPixelRef.h"
17 #include "ui/gfx/rect.h"
18 #include "ui/gfx/skia_util.h"
23 TEST(PictureTest
, AsBase64String
) {
26 gfx::Rect
layer_rect(100, 100);
28 SkTileGridFactory::TileGridInfo tile_grid_info
;
29 tile_grid_info
.fTileInterval
= SkISize::Make(100, 100);
30 tile_grid_info
.fMargin
.setEmpty();
31 tile_grid_info
.fOffset
.setZero();
33 FakeContentLayerClient content_layer_client
;
35 scoped_ptr
<base::Value
> tmp
;
38 red_paint
.setColor(SkColorSetARGB(255, 255, 0, 0));
40 green_paint
.setColor(SkColorSetARGB(255, 0, 255, 0));
42 // Invalid picture (not a dict).
43 tmp
.reset(new base::StringValue("abc!@#$%"));
44 scoped_refptr
<Picture
> invalid_picture
=
45 Picture::CreateFromValue(tmp
.get());
46 EXPECT_FALSE(invalid_picture
.get());
48 Picture::RecordingMode kRecordingModes
[] = {Picture::RECORD_NORMALLY
,
49 Picture::RECORD_WITH_SKRECORD
};
51 // Single full-size rect picture.
52 content_layer_client
.add_draw_rect(layer_rect
, red_paint
);
54 for (size_t i
= 0; i
< arraysize(kRecordingModes
); ++i
) {
55 scoped_refptr
<Picture
> one_rect_picture
=
56 Picture::Create(layer_rect
,
57 &content_layer_client
,
62 scoped_ptr
<base::Value
> serialized_one_rect(one_rect_picture
->AsValue());
64 // Reconstruct the picture.
65 scoped_refptr
<Picture
> one_rect_picture_check
=
66 Picture::CreateFromValue(serialized_one_rect
.get());
67 EXPECT_TRUE(!!one_rect_picture_check
.get());
69 // Check for equivalence.
70 unsigned char one_rect_buffer
[4 * 100 * 100] = {0};
71 DrawPicture(one_rect_buffer
, layer_rect
, one_rect_picture
);
72 unsigned char one_rect_buffer_check
[4 * 100 * 100] = {0};
73 DrawPicture(one_rect_buffer_check
, layer_rect
, one_rect_picture_check
);
75 EXPECT_EQ(one_rect_picture
->LayerRect(),
76 one_rect_picture_check
->LayerRect());
77 EXPECT_EQ(one_rect_picture
->OpaqueRect(),
78 one_rect_picture_check
->OpaqueRect());
79 EXPECT_TRUE(memcmp(one_rect_buffer
, one_rect_buffer_check
, 4 * 100 * 100) ==
84 content_layer_client
.add_draw_rect(gfx::Rect(25, 25, 50, 50), green_paint
);
86 for (size_t i
= 0; i
< arraysize(kRecordingModes
); ++i
) {
87 scoped_refptr
<Picture
> two_rect_picture
=
88 Picture::Create(layer_rect
,
89 &content_layer_client
,
93 Picture::RECORD_NORMALLY
);
95 scoped_ptr
<base::Value
> serialized_two_rect(two_rect_picture
->AsValue());
97 // Reconstruct the picture.
98 scoped_refptr
<Picture
> two_rect_picture_check
=
99 Picture::CreateFromValue(serialized_two_rect
.get());
100 EXPECT_TRUE(!!two_rect_picture_check
.get());
102 // Check for equivalence.
103 unsigned char two_rect_buffer
[4 * 100 * 100] = {0};
104 DrawPicture(two_rect_buffer
, layer_rect
, two_rect_picture
);
105 unsigned char two_rect_buffer_check
[4 * 100 * 100] = {0};
106 DrawPicture(two_rect_buffer_check
, layer_rect
, two_rect_picture_check
);
108 EXPECT_EQ(two_rect_picture
->LayerRect(),
109 two_rect_picture_check
->LayerRect());
110 EXPECT_EQ(two_rect_picture
->OpaqueRect(),
111 two_rect_picture_check
->OpaqueRect());
112 EXPECT_TRUE(memcmp(two_rect_buffer
, two_rect_buffer_check
, 4 * 100 * 100) ==
117 TEST(PictureTest
, PixelRefIterator
) {
118 gfx::Rect
layer_rect(2048, 2048);
120 SkTileGridFactory::TileGridInfo tile_grid_info
;
121 tile_grid_info
.fTileInterval
= SkISize::Make(512, 512);
122 tile_grid_info
.fMargin
.setEmpty();
123 tile_grid_info
.fOffset
.setZero();
125 FakeContentLayerClient content_layer_client
;
127 // Discardable pixel refs are found in the following grids:
137 SkBitmap discardable_bitmap
[4][4];
138 for (int y
= 0; y
< 4; ++y
) {
139 for (int x
= 0; x
< 4; ++x
) {
142 gfx::Size(500, 500), "discardable", &discardable_bitmap
[y
][x
]);
144 content_layer_client
.add_draw_bitmap(
145 discardable_bitmap
[y
][x
],
146 gfx::Point(x
* 512 + 6, y
* 512 + 6), paint
);
151 scoped_refptr
<Picture
> picture
= Picture::Create(layer_rect
,
152 &content_layer_client
,
156 Picture::RECORD_NORMALLY
);
158 // Default iterator does not have any pixel refs
160 Picture::PixelRefIterator iterator
;
161 EXPECT_FALSE(iterator
);
163 for (int y
= 0; y
< 4; ++y
) {
164 for (int x
= 0; x
< 4; ++x
) {
165 Picture::PixelRefIterator
iterator(gfx::Rect(x
* 512, y
* 512, 500, 500),
168 EXPECT_TRUE(iterator
) << x
<< " " << y
;
169 EXPECT_TRUE(*iterator
== discardable_bitmap
[y
][x
].pixelRef()) << x
<<
171 EXPECT_FALSE(++iterator
) << x
<< " " << y
;
173 EXPECT_FALSE(iterator
) << x
<< " " << y
;
177 // Capture 4 pixel refs.
179 Picture::PixelRefIterator
iterator(gfx::Rect(512, 512, 2048, 2048),
181 EXPECT_TRUE(iterator
);
182 EXPECT_TRUE(*iterator
== discardable_bitmap
[1][2].pixelRef());
183 EXPECT_TRUE(++iterator
);
184 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][1].pixelRef());
185 EXPECT_TRUE(++iterator
);
186 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][3].pixelRef());
187 EXPECT_TRUE(++iterator
);
188 EXPECT_TRUE(*iterator
== discardable_bitmap
[3][2].pixelRef());
189 EXPECT_FALSE(++iterator
);
193 Picture::PixelRefIterator
iterator(gfx::Rect(512, 512, 2048, 2048),
195 EXPECT_TRUE(iterator
);
196 EXPECT_TRUE(*iterator
== discardable_bitmap
[1][2].pixelRef());
197 EXPECT_TRUE(++iterator
);
198 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][1].pixelRef());
200 // copy now points to the same spot as iterator,
201 // but both can be incremented independently.
202 Picture::PixelRefIterator copy
= iterator
;
203 EXPECT_TRUE(++iterator
);
204 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][3].pixelRef());
205 EXPECT_TRUE(++iterator
);
206 EXPECT_TRUE(*iterator
== discardable_bitmap
[3][2].pixelRef());
207 EXPECT_FALSE(++iterator
);
210 EXPECT_TRUE(*copy
== discardable_bitmap
[2][1].pixelRef());
212 EXPECT_TRUE(*copy
== discardable_bitmap
[2][3].pixelRef());
214 EXPECT_TRUE(*copy
== discardable_bitmap
[3][2].pixelRef());
215 EXPECT_FALSE(++copy
);
218 TEST(PictureTest
, PixelRefIteratorNonZeroLayer
) {
219 gfx::Rect
layer_rect(1024, 0, 2048, 2048);
221 SkTileGridFactory::TileGridInfo tile_grid_info
;
222 tile_grid_info
.fTileInterval
= SkISize::Make(512, 512);
223 tile_grid_info
.fMargin
.setEmpty();
224 tile_grid_info
.fOffset
.setZero();
226 FakeContentLayerClient content_layer_client
;
228 // Discardable pixel refs are found in the following grids:
238 SkBitmap discardable_bitmap
[4][4];
239 for (int y
= 0; y
< 4; ++y
) {
240 for (int x
= 0; x
< 4; ++x
) {
243 gfx::Size(500, 500), "discardable", &discardable_bitmap
[y
][x
]);
245 content_layer_client
.add_draw_bitmap(
246 discardable_bitmap
[y
][x
],
247 gfx::Point(1024 + x
* 512 + 6, y
* 512 + 6), paint
);
252 scoped_refptr
<Picture
> picture
= Picture::Create(layer_rect
,
253 &content_layer_client
,
257 Picture::RECORD_NORMALLY
);
259 // Default iterator does not have any pixel refs
261 Picture::PixelRefIterator iterator
;
262 EXPECT_FALSE(iterator
);
264 for (int y
= 0; y
< 4; ++y
) {
265 for (int x
= 0; x
< 4; ++x
) {
266 Picture::PixelRefIterator
iterator(
267 gfx::Rect(1024 + x
* 512, y
* 512, 500, 500), picture
.get());
269 EXPECT_TRUE(iterator
) << x
<< " " << y
;
270 EXPECT_TRUE(*iterator
== discardable_bitmap
[y
][x
].pixelRef());
271 EXPECT_FALSE(++iterator
) << x
<< " " << y
;
273 EXPECT_FALSE(iterator
) << x
<< " " << y
;
277 // Capture 4 pixel refs.
279 Picture::PixelRefIterator
iterator(gfx::Rect(1024 + 512, 512, 2048, 2048),
281 EXPECT_TRUE(iterator
);
282 EXPECT_TRUE(*iterator
== discardable_bitmap
[1][2].pixelRef());
283 EXPECT_TRUE(++iterator
);
284 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][1].pixelRef());
285 EXPECT_TRUE(++iterator
);
286 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][3].pixelRef());
287 EXPECT_TRUE(++iterator
);
288 EXPECT_TRUE(*iterator
== discardable_bitmap
[3][2].pixelRef());
289 EXPECT_FALSE(++iterator
);
294 Picture::PixelRefIterator
iterator(gfx::Rect(1024 + 512, 512, 2048, 2048),
296 EXPECT_TRUE(iterator
);
297 EXPECT_TRUE(*iterator
== discardable_bitmap
[1][2].pixelRef());
298 EXPECT_TRUE(++iterator
);
299 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][1].pixelRef());
301 // copy now points to the same spot as iterator,
302 // but both can be incremented independently.
303 Picture::PixelRefIterator copy
= iterator
;
304 EXPECT_TRUE(++iterator
);
305 EXPECT_TRUE(*iterator
== discardable_bitmap
[2][3].pixelRef());
306 EXPECT_TRUE(++iterator
);
307 EXPECT_TRUE(*iterator
== discardable_bitmap
[3][2].pixelRef());
308 EXPECT_FALSE(++iterator
);
311 EXPECT_TRUE(*copy
== discardable_bitmap
[2][1].pixelRef());
313 EXPECT_TRUE(*copy
== discardable_bitmap
[2][3].pixelRef());
315 EXPECT_TRUE(*copy
== discardable_bitmap
[3][2].pixelRef());
316 EXPECT_FALSE(++copy
);
319 // Non intersecting rects
321 Picture::PixelRefIterator
iterator(gfx::Rect(0, 0, 1000, 1000),
323 EXPECT_FALSE(iterator
);
326 Picture::PixelRefIterator
iterator(gfx::Rect(3500, 0, 1000, 1000),
328 EXPECT_FALSE(iterator
);
331 Picture::PixelRefIterator
iterator(gfx::Rect(0, 1100, 1000, 1000),
333 EXPECT_FALSE(iterator
);
336 Picture::PixelRefIterator
iterator(gfx::Rect(3500, 1100, 1000, 1000),
338 EXPECT_FALSE(iterator
);
342 TEST(PictureTest
, PixelRefIteratorOnePixelQuery
) {
343 gfx::Rect
layer_rect(2048, 2048);
345 SkTileGridFactory::TileGridInfo tile_grid_info
;
346 tile_grid_info
.fTileInterval
= SkISize::Make(512, 512);
347 tile_grid_info
.fMargin
.setEmpty();
348 tile_grid_info
.fOffset
.setZero();
350 FakeContentLayerClient content_layer_client
;
352 // Discardable pixel refs are found in the following grids:
362 SkBitmap discardable_bitmap
[4][4];
363 for (int y
= 0; y
< 4; ++y
) {
364 for (int x
= 0; x
< 4; ++x
) {
367 gfx::Size(500, 500), "discardable", &discardable_bitmap
[y
][x
]);
369 content_layer_client
.add_draw_bitmap(
370 discardable_bitmap
[y
][x
],
371 gfx::Point(x
* 512 + 6, y
* 512 + 6), paint
);
376 scoped_refptr
<Picture
> picture
= Picture::Create(layer_rect
,
377 &content_layer_client
,
381 Picture::RECORD_NORMALLY
);
383 for (int y
= 0; y
< 4; ++y
) {
384 for (int x
= 0; x
< 4; ++x
) {
385 Picture::PixelRefIterator
iterator(
386 gfx::Rect(x
* 512, y
* 512 + 256, 1, 1), picture
.get());
388 EXPECT_TRUE(iterator
) << x
<< " " << y
;
389 EXPECT_TRUE(*iterator
== discardable_bitmap
[y
][x
].pixelRef());
390 EXPECT_FALSE(++iterator
) << x
<< " " << y
;
392 EXPECT_FALSE(iterator
) << x
<< " " << y
;
398 TEST(PictureTest
, CreateFromSkpValue
) {
401 gfx::Rect
layer_rect(100, 200);
403 SkTileGridFactory::TileGridInfo tile_grid_info
;
404 tile_grid_info
.fTileInterval
= SkISize::Make(100, 200);
405 tile_grid_info
.fMargin
.setEmpty();
406 tile_grid_info
.fOffset
.setZero();
408 FakeContentLayerClient content_layer_client
;
410 scoped_ptr
<base::Value
> tmp
;
413 red_paint
.setColor(SkColorSetARGB(255, 255, 0, 0));
415 green_paint
.setColor(SkColorSetARGB(255, 0, 255, 0));
417 // Invalid picture (not a dict).
418 tmp
.reset(new base::StringValue("abc!@#$%"));
419 scoped_refptr
<Picture
> invalid_picture
=
420 Picture::CreateFromSkpValue(tmp
.get());
421 EXPECT_TRUE(!invalid_picture
.get());
423 // Single full-size rect picture.
424 content_layer_client
.add_draw_rect(layer_rect
, red_paint
);
425 scoped_refptr
<Picture
> one_rect_picture
=
426 Picture::Create(layer_rect
,
427 &content_layer_client
,
431 Picture::RECORD_NORMALLY
);
432 scoped_ptr
<base::Value
> serialized_one_rect(
433 one_rect_picture
->AsValue());
435 const base::DictionaryValue
* value
= NULL
;
436 EXPECT_TRUE(serialized_one_rect
->GetAsDictionary(&value
));
438 // Decode the picture from base64.
439 const base::Value
* skp_value
;
440 EXPECT_TRUE(value
->Get("skp64", &skp_value
));
442 // Reconstruct the picture.
443 scoped_refptr
<Picture
> one_rect_picture_check
=
444 Picture::CreateFromSkpValue(skp_value
);
445 EXPECT_TRUE(!!one_rect_picture_check
.get());
447 EXPECT_EQ(100, one_rect_picture_check
->LayerRect().width());
448 EXPECT_EQ(200, one_rect_picture_check
->LayerRect().height());
449 EXPECT_EQ(100, one_rect_picture_check
->OpaqueRect().width());
450 EXPECT_EQ(200, one_rect_picture_check
->OpaqueRect().height());
453 TEST(PictureTest
, RecordingModes
) {
456 gfx::Rect
layer_rect(100, 200);
458 SkTileGridFactory::TileGridInfo tile_grid_info
;
459 tile_grid_info
.fTileInterval
= SkISize::Make(100, 200);
460 tile_grid_info
.fMargin
.setEmpty();
461 tile_grid_info
.fOffset
.setZero();
463 FakeContentLayerClient content_layer_client
;
464 EXPECT_EQ(NULL
, content_layer_client
.last_canvas());
466 scoped_refptr
<Picture
> picture
= Picture::Create(layer_rect
,
467 &content_layer_client
,
471 Picture::RECORD_NORMALLY
);
472 EXPECT_TRUE(content_layer_client
.last_canvas() != NULL
);
473 EXPECT_EQ(ContentLayerClient::GRAPHICS_CONTEXT_ENABLED
,
474 content_layer_client
.last_context_status());
475 EXPECT_TRUE(picture
);
477 picture
= Picture::Create(layer_rect
,
478 &content_layer_client
,
482 Picture::RECORD_WITH_SK_NULL_CANVAS
);
483 EXPECT_TRUE(content_layer_client
.last_canvas() != NULL
);
484 EXPECT_EQ(ContentLayerClient::GRAPHICS_CONTEXT_ENABLED
,
485 content_layer_client
.last_context_status());
486 EXPECT_TRUE(picture
);
488 picture
= Picture::Create(layer_rect
,
489 &content_layer_client
,
493 Picture::RECORD_WITH_PAINTING_DISABLED
);
494 EXPECT_TRUE(content_layer_client
.last_canvas() != NULL
);
495 EXPECT_EQ(ContentLayerClient::GRAPHICS_CONTEXT_DISABLED
,
496 content_layer_client
.last_context_status());
497 EXPECT_TRUE(picture
);
499 picture
= Picture::Create(layer_rect
,
500 &content_layer_client
,
504 Picture::RECORD_WITH_SKRECORD
);
505 EXPECT_TRUE(content_layer_client
.last_canvas() != NULL
);
506 EXPECT_TRUE(picture
);
508 EXPECT_EQ(4, Picture::RECORDING_MODE_COUNT
);