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/layers/scrollbar_layer.h" | 5 #include "cc/layers/scrollbar_layer.h" |
6 | 6 |
| 7 #include "base/containers/hash_tables.h" |
7 #include "cc/animation/scrollbar_animation_controller.h" | 8 #include "cc/animation/scrollbar_animation_controller.h" |
8 #include "cc/debug/test_web_graphics_context_3d.h" | 9 #include "cc/debug/test_web_graphics_context_3d.h" |
9 #include "cc/layers/append_quads_data.h" | 10 #include "cc/layers/append_quads_data.h" |
10 #include "cc/layers/scrollbar_layer_impl.h" | 11 #include "cc/layers/scrollbar_layer_impl.h" |
11 #include "cc/quads/solid_color_draw_quad.h" | 12 #include "cc/quads/solid_color_draw_quad.h" |
12 #include "cc/resources/prioritized_resource_manager.h" | |
13 #include "cc/resources/priority_calculator.h" | |
14 #include "cc/resources/resource_update_queue.h" | 13 #include "cc/resources/resource_update_queue.h" |
15 #include "cc/test/fake_impl_proxy.h" | 14 #include "cc/test/fake_impl_proxy.h" |
16 #include "cc/test/fake_layer_tree_host.h" | 15 #include "cc/test/fake_layer_tree_host.h" |
17 #include "cc/test/fake_layer_tree_host_client.h" | 16 #include "cc/test/fake_layer_tree_host_client.h" |
18 #include "cc/test/fake_layer_tree_host_impl.h" | 17 #include "cc/test/fake_layer_tree_host_impl.h" |
19 #include "cc/test/fake_scrollbar.h" | 18 #include "cc/test/fake_scrollbar.h" |
| 19 #include "cc/test/fake_scrollbar_layer.h" |
20 #include "cc/test/geometry_test_utils.h" | 20 #include "cc/test/geometry_test_utils.h" |
21 #include "cc/test/layer_tree_test.h" | 21 #include "cc/test/layer_tree_test.h" |
22 #include "cc/test/mock_quad_culler.h" | 22 #include "cc/test/mock_quad_culler.h" |
| 23 #include "cc/trees/layer_tree_host.h" |
23 #include "cc/trees/layer_tree_impl.h" | 24 #include "cc/trees/layer_tree_impl.h" |
24 #include "cc/trees/single_thread_proxy.h" | 25 #include "cc/trees/single_thread_proxy.h" |
25 #include "cc/trees/tree_synchronizer.h" | 26 #include "cc/trees/tree_synchronizer.h" |
26 #include "testing/gmock/include/gmock/gmock.h" | 27 #include "testing/gmock/include/gmock/gmock.h" |
27 #include "testing/gtest/include/gtest/gtest.h" | 28 #include "testing/gtest/include/gtest/gtest.h" |
28 | 29 |
29 namespace cc { | 30 namespace cc { |
30 namespace { | 31 namespace { |
31 | 32 |
32 LayerImpl* LayerImplForScrollAreaAndScrollbar( | 33 LayerImpl* LayerImplForScrollAreaAndScrollbar( |
(...skipping 364 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
397 int max_size = 0; | 398 int max_size = 0; |
398 context->getIntegerv(GL_MAX_TEXTURE_SIZE, &max_size); | 399 context->getIntegerv(GL_MAX_TEXTURE_SIZE, &max_size); |
399 SetScrollbarBounds(gfx::Size(max_size + 100, max_size + 100)); | 400 SetScrollbarBounds(gfx::Size(max_size + 100, max_size + 100)); |
400 RunTest(true, true, true); | 401 RunTest(true, true, true); |
401 } | 402 } |
402 | 403 |
403 class MockLayerTreeHost : public LayerTreeHost { | 404 class MockLayerTreeHost : public LayerTreeHost { |
404 public: | 405 public: |
405 MockLayerTreeHost(LayerTreeHostClient* client, | 406 MockLayerTreeHost(LayerTreeHostClient* client, |
406 const LayerTreeSettings& settings) | 407 const LayerTreeSettings& settings) |
407 : LayerTreeHost(client, settings) { | 408 : LayerTreeHost(client, settings), |
| 409 next_id_(1), |
| 410 total_ui_resource_created_(0), |
| 411 total_ui_resource_deleted_(0) { |
408 Initialize(NULL); | 412 Initialize(NULL); |
409 } | 413 } |
| 414 |
| 415 virtual UIResourceId CreateUIResource(UIResourceClient* content) OVERRIDE { |
| 416 total_ui_resource_created_++; |
| 417 UIResourceId nid = next_id_++; |
| 418 ui_resource_bitmap_map_[nid] = content->GetBitmap(nid, false); |
| 419 return nid; |
| 420 } |
| 421 |
| 422 // Deletes a UI resource. May safely be called more than once. |
| 423 virtual void DeleteUIResource(UIResourceId id) OVERRIDE { |
| 424 UIResourceBitmapMap::iterator iter = ui_resource_bitmap_map_.find(id); |
| 425 if (iter != ui_resource_bitmap_map_.end()) { |
| 426 ui_resource_bitmap_map_.erase(iter); |
| 427 total_ui_resource_deleted_++; |
| 428 } |
| 429 } |
| 430 |
| 431 size_t UIResourceCount() { return ui_resource_bitmap_map_.size(); } |
| 432 int TotalUIResourceDeleted() { return total_ui_resource_deleted_; } |
| 433 int TotalUIResourceCreated() { return total_ui_resource_created_; } |
| 434 |
| 435 gfx::Size ui_resource_size(UIResourceId id) { |
| 436 UIResourceBitmapMap::iterator iter = ui_resource_bitmap_map_.find(id); |
| 437 if (iter != ui_resource_bitmap_map_.end() && iter->second.get()) |
| 438 return iter->second->GetSize(); |
| 439 return gfx::Size(); |
| 440 } |
| 441 |
| 442 private: |
| 443 typedef base::hash_map<UIResourceId, scoped_refptr<UIResourceBitmap> > |
| 444 UIResourceBitmapMap; |
| 445 UIResourceBitmapMap ui_resource_bitmap_map_; |
| 446 |
| 447 int next_id_; |
| 448 int total_ui_resource_created_; |
| 449 int total_ui_resource_deleted_; |
410 }; | 450 }; |
411 | 451 |
412 | 452 |
413 class ScrollbarLayerTestResourceCreation : public testing::Test { | 453 class ScrollbarLayerTestResourceCreation : public testing::Test { |
414 public: | 454 public: |
415 ScrollbarLayerTestResourceCreation() | 455 ScrollbarLayerTestResourceCreation() |
416 : fake_client_(FakeLayerTreeHostClient::DIRECT_3D) {} | 456 : fake_client_(FakeLayerTreeHostClient::DIRECT_3D) {} |
417 | 457 |
418 void TestResourceUpload(size_t expected_resources) { | 458 void TestResourceUpload(int num_updates, |
| 459 size_t expected_resources, |
| 460 int expected_created, |
| 461 int expected_deleted) { |
419 layer_tree_host_.reset( | 462 layer_tree_host_.reset( |
420 new MockLayerTreeHost(&fake_client_, layer_tree_settings_)); | 463 new MockLayerTreeHost(&fake_client_, layer_tree_settings_)); |
421 | 464 |
422 scoped_ptr<Scrollbar> scrollbar(new FakeScrollbar(false, true, false)); | 465 scoped_ptr<Scrollbar> scrollbar(new FakeScrollbar(false, true, false)); |
423 scoped_refptr<Layer> layer_tree_root = Layer::Create(); | 466 scoped_refptr<Layer> layer_tree_root = Layer::Create(); |
424 scoped_refptr<Layer> content_layer = Layer::Create(); | 467 scoped_refptr<Layer> content_layer = Layer::Create(); |
425 scoped_refptr<Layer> scrollbar_layer = | 468 scoped_refptr<Layer> scrollbar_layer = |
426 ScrollbarLayer::Create(scrollbar.Pass(), layer_tree_root->id()); | 469 ScrollbarLayer::Create(scrollbar.Pass(), layer_tree_root->id()); |
427 layer_tree_root->AddChild(content_layer); | 470 layer_tree_root->AddChild(content_layer); |
428 layer_tree_root->AddChild(scrollbar_layer); | 471 layer_tree_root->AddChild(scrollbar_layer); |
429 | 472 |
430 layer_tree_host_->InitializeOutputSurfaceIfNeeded(); | 473 layer_tree_host_->InitializeOutputSurfaceIfNeeded(); |
431 layer_tree_host_->contents_texture_manager()-> | |
432 SetMaxMemoryLimitBytes(1024 * 1024); | |
433 layer_tree_host_->SetRootLayer(layer_tree_root); | 474 layer_tree_host_->SetRootLayer(layer_tree_root); |
434 | 475 |
435 scrollbar_layer->SetIsDrawable(true); | 476 scrollbar_layer->SetIsDrawable(true); |
436 scrollbar_layer->SetBounds(gfx::Size(100, 100)); | 477 scrollbar_layer->SetBounds(gfx::Size(100, 100)); |
437 layer_tree_root->SetScrollOffset(gfx::Vector2d(10, 20)); | 478 layer_tree_root->SetScrollOffset(gfx::Vector2d(10, 20)); |
438 layer_tree_root->SetMaxScrollOffset(gfx::Vector2d(30, 50)); | 479 layer_tree_root->SetMaxScrollOffset(gfx::Vector2d(30, 50)); |
439 layer_tree_root->SetBounds(gfx::Size(100, 200)); | 480 layer_tree_root->SetBounds(gfx::Size(100, 200)); |
440 content_layer->SetBounds(gfx::Size(100, 200)); | 481 content_layer->SetBounds(gfx::Size(100, 200)); |
441 scrollbar_layer->draw_properties().content_bounds = gfx::Size(100, 200); | 482 scrollbar_layer->draw_properties().content_bounds = gfx::Size(100, 200); |
442 scrollbar_layer->draw_properties().visible_content_rect = | 483 scrollbar_layer->draw_properties().visible_content_rect = |
443 gfx::Rect(0, 0, 100, 200); | 484 gfx::Rect(0, 0, 100, 200); |
444 scrollbar_layer->CreateRenderSurface(); | 485 scrollbar_layer->CreateRenderSurface(); |
445 scrollbar_layer->draw_properties().render_target = scrollbar_layer.get(); | 486 scrollbar_layer->draw_properties().render_target = scrollbar_layer.get(); |
446 | 487 |
447 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); | 488 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); |
448 EXPECT_EQ(scrollbar_layer->layer_tree_host(), layer_tree_host_.get()); | 489 EXPECT_EQ(scrollbar_layer->layer_tree_host(), layer_tree_host_.get()); |
449 | 490 |
450 PriorityCalculator calculator; | |
451 ResourceUpdateQueue queue; | 491 ResourceUpdateQueue queue; |
452 OcclusionTracker occlusion_tracker(gfx::Rect(), false); | 492 OcclusionTracker occlusion_tracker(gfx::Rect(), false); |
453 | 493 |
454 scrollbar_layer->SavePaintProperties(); | 494 scrollbar_layer->SavePaintProperties(); |
455 scrollbar_layer->SetTexturePriorities(calculator); | 495 for (int update_counter = 0; update_counter < num_updates; update_counter++) |
456 layer_tree_host_->contents_texture_manager()->PrioritizeTextures(); | 496 scrollbar_layer->Update(&queue, &occlusion_tracker); |
457 scrollbar_layer->Update(&queue, &occlusion_tracker); | 497 |
458 EXPECT_EQ(0u, queue.FullUploadSize()); | 498 // A non-solid-color scrollbar should have requested two textures. |
459 EXPECT_EQ(expected_resources, queue.PartialUploadSize()); | 499 EXPECT_EQ(expected_resources, layer_tree_host_->UIResourceCount()); |
| 500 EXPECT_EQ(expected_created, layer_tree_host_->TotalUIResourceCreated()); |
| 501 EXPECT_EQ(expected_deleted, layer_tree_host_->TotalUIResourceDeleted()); |
460 | 502 |
461 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); | 503 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); |
462 | 504 |
463 scrollbar_layer->ClearRenderSurface(); | 505 scrollbar_layer->ClearRenderSurface(); |
464 } | 506 } |
465 | 507 |
466 protected: | 508 protected: |
467 FakeLayerTreeHostClient fake_client_; | 509 FakeLayerTreeHostClient fake_client_; |
468 LayerTreeSettings layer_tree_settings_; | 510 LayerTreeSettings layer_tree_settings_; |
469 scoped_ptr<MockLayerTreeHost> layer_tree_host_; | 511 scoped_ptr<MockLayerTreeHost> layer_tree_host_; |
470 }; | 512 }; |
471 | 513 |
472 TEST_F(ScrollbarLayerTestResourceCreation, ResourceUpload) { | 514 TEST_F(ScrollbarLayerTestResourceCreation, ResourceUpload) { |
473 layer_tree_settings_.solid_color_scrollbars = false; | 515 layer_tree_settings_.solid_color_scrollbars = false; |
474 TestResourceUpload(2); | 516 TestResourceUpload(0, 0, 0, 0); |
| 517 int num_updates[3] = {1, 5, 10}; |
| 518 for (int j = 0; j < 3; j++) { |
| 519 TestResourceUpload( |
| 520 num_updates[j], 2, num_updates[j] * 2, (num_updates[j] - 1) * 2); |
| 521 } |
475 } | 522 } |
476 | 523 |
477 TEST_F(ScrollbarLayerTestResourceCreation, SolidColorNoResourceUpload) { | 524 TEST_F(ScrollbarLayerTestResourceCreation, SolidColorNoResourceUpload) { |
478 layer_tree_settings_.solid_color_scrollbars = true; | 525 layer_tree_settings_.solid_color_scrollbars = true; |
479 TestResourceUpload(0); | 526 TestResourceUpload(0, 0, 0, 0); |
| 527 TestResourceUpload(1, 0, 0, 0); |
480 } | 528 } |
481 | 529 |
482 class ScaledScrollbarLayerTestResourceCreation : public testing::Test { | 530 class ScaledScrollbarLayerTestResourceCreation : public testing::Test { |
483 public: | 531 public: |
484 ScaledScrollbarLayerTestResourceCreation() | 532 ScaledScrollbarLayerTestResourceCreation() |
485 : fake_client_(FakeLayerTreeHostClient::DIRECT_3D) {} | 533 : fake_client_(FakeLayerTreeHostClient::DIRECT_3D) {} |
486 | 534 |
487 void TestResourceUpload(size_t expected_resources, const float test_scale) { | 535 void TestResourceUpload(const float test_scale) { |
488 layer_tree_host_.reset( | 536 layer_tree_host_.reset( |
489 new MockLayerTreeHost(&fake_client_, layer_tree_settings_)); | 537 new MockLayerTreeHost(&fake_client_, layer_tree_settings_)); |
490 | 538 |
491 gfx::Point scrollbar_location(0, 185); | 539 gfx::Point scrollbar_location(0, 185); |
492 scoped_ptr<FakeScrollbar> scrollbar(new FakeScrollbar(false, true, false)); | |
493 scrollbar->set_location(scrollbar_location); | |
494 | |
495 scoped_refptr<Layer> layer_tree_root = Layer::Create(); | 540 scoped_refptr<Layer> layer_tree_root = Layer::Create(); |
496 scoped_refptr<Layer> content_layer = Layer::Create(); | 541 scoped_refptr<Layer> content_layer = Layer::Create(); |
497 scoped_refptr<Layer> scrollbar_layer = | 542 scoped_refptr<FakeScrollbarLayer> scrollbar_layer = |
498 ScrollbarLayer::Create(scrollbar.PassAs<cc::Scrollbar>(), | 543 FakeScrollbarLayer::Create(false, true, layer_tree_root->id()); |
499 layer_tree_root->id()); | 544 |
500 layer_tree_root->AddChild(content_layer); | 545 layer_tree_root->AddChild(content_layer); |
501 layer_tree_root->AddChild(scrollbar_layer); | 546 layer_tree_root->AddChild(scrollbar_layer); |
502 | 547 |
503 layer_tree_host_->InitializeOutputSurfaceIfNeeded(); | 548 layer_tree_host_->InitializeOutputSurfaceIfNeeded(); |
504 layer_tree_host_->contents_texture_manager()-> | |
505 SetMaxMemoryLimitBytes(1024 * 1024); | |
506 layer_tree_host_->SetRootLayer(layer_tree_root); | 549 layer_tree_host_->SetRootLayer(layer_tree_root); |
507 | 550 |
508 scrollbar_layer->SetIsDrawable(true); | 551 scrollbar_layer->SetIsDrawable(true); |
509 scrollbar_layer->SetBounds(gfx::Size(100, 15)); | 552 scrollbar_layer->SetBounds(gfx::Size(100, 15)); |
510 scrollbar_layer->SetPosition(scrollbar_location); | 553 scrollbar_layer->SetPosition(scrollbar_location); |
511 layer_tree_root->SetBounds(gfx::Size(100, 200)); | 554 layer_tree_root->SetBounds(gfx::Size(100, 200)); |
512 content_layer->SetBounds(gfx::Size(100, 200)); | 555 content_layer->SetBounds(gfx::Size(100, 200)); |
513 gfx::SizeF scaled_size = | 556 gfx::SizeF scaled_size = |
514 gfx::ScaleSize(scrollbar_layer->bounds(), test_scale, test_scale); | 557 gfx::ScaleSize(scrollbar_layer->bounds(), test_scale, test_scale); |
515 gfx::PointF scaled_location = | 558 gfx::PointF scaled_location = |
516 gfx::ScalePoint(scrollbar_layer->position(), test_scale, test_scale); | 559 gfx::ScalePoint(scrollbar_layer->position(), test_scale, test_scale); |
517 scrollbar_layer->draw_properties().content_bounds = | 560 scrollbar_layer->draw_properties().content_bounds = |
518 gfx::Size(scaled_size.width(), scaled_size.height()); | 561 gfx::Size(scaled_size.width(), scaled_size.height()); |
519 scrollbar_layer->draw_properties().contents_scale_x = test_scale; | 562 scrollbar_layer->draw_properties().contents_scale_x = test_scale; |
520 scrollbar_layer->draw_properties().contents_scale_y = test_scale; | 563 scrollbar_layer->draw_properties().contents_scale_y = test_scale; |
521 scrollbar_layer->draw_properties().visible_content_rect = | 564 scrollbar_layer->draw_properties().visible_content_rect = |
522 gfx::Rect(scaled_location.x(), | 565 gfx::Rect(scaled_location.x(), |
523 scaled_location.y(), | 566 scaled_location.y(), |
524 scaled_size.width(), | 567 scaled_size.width(), |
525 scaled_size.height()); | 568 scaled_size.height()); |
526 scrollbar_layer->CreateRenderSurface(); | 569 scrollbar_layer->CreateRenderSurface(); |
527 scrollbar_layer->draw_properties().render_target = scrollbar_layer.get(); | 570 scrollbar_layer->draw_properties().render_target = scrollbar_layer.get(); |
528 | 571 |
529 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); | 572 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); |
530 EXPECT_EQ(scrollbar_layer->layer_tree_host(), layer_tree_host_.get()); | 573 EXPECT_EQ(scrollbar_layer->layer_tree_host(), layer_tree_host_.get()); |
531 | 574 |
532 PriorityCalculator calculator; | |
533 ResourceUpdateQueue queue; | 575 ResourceUpdateQueue queue; |
534 OcclusionTracker occlusion_tracker(gfx::Rect(), false); | 576 OcclusionTracker occlusion_tracker(gfx::Rect(), false); |
535 | |
536 scrollbar_layer->SavePaintProperties(); | 577 scrollbar_layer->SavePaintProperties(); |
537 scrollbar_layer->SetTexturePriorities(calculator); | |
538 layer_tree_host_->contents_texture_manager()->PrioritizeTextures(); | |
539 scrollbar_layer->Update(&queue, &occlusion_tracker); | 578 scrollbar_layer->Update(&queue, &occlusion_tracker); |
540 EXPECT_EQ(expected_resources, queue.PartialUploadSize()); | |
541 | 579 |
542 // Verify that we have not generated any content uploads that are larger | 580 // Verify that we have not generated any content uploads that are larger |
543 // than their destination textures. | 581 // than their destination textures. |
544 while (queue.HasMoreUpdates()) { | |
545 ResourceUpdate update = queue.TakeFirstPartialUpload(); | |
546 EXPECT_LE(update.texture->size().width(), | |
547 scrollbar_layer->content_bounds().width()); | |
548 EXPECT_LE(update.texture->size().height(), | |
549 scrollbar_layer->content_bounds().height()); | |
550 | 582 |
551 EXPECT_LE(update.dest_offset.x() + update.content_rect.width(), | 583 gfx::Size track_size = layer_tree_host_->ui_resource_size( |
552 update.texture->size().width()); | 584 scrollbar_layer->track_resource_id()); |
553 EXPECT_LE(update.dest_offset.y() + update.content_rect.height(), | 585 gfx::Size thumb_size = layer_tree_host_->ui_resource_size( |
554 update.texture->size().height()); | 586 scrollbar_layer->thumb_resource_id()); |
555 } | 587 |
| 588 EXPECT_LE(track_size.width(), scrollbar_layer->content_bounds().width()); |
| 589 EXPECT_LE(track_size.height(), scrollbar_layer->content_bounds().height()); |
| 590 EXPECT_LE(thumb_size.width(), scrollbar_layer->content_bounds().width()); |
| 591 EXPECT_LE(thumb_size.height(), scrollbar_layer->content_bounds().height()); |
556 | 592 |
557 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); | 593 testing::Mock::VerifyAndClearExpectations(layer_tree_host_.get()); |
558 | 594 |
559 scrollbar_layer->ClearRenderSurface(); | 595 scrollbar_layer->ClearRenderSurface(); |
560 } | 596 } |
561 | 597 |
562 protected: | 598 protected: |
563 FakeLayerTreeHostClient fake_client_; | 599 FakeLayerTreeHostClient fake_client_; |
564 LayerTreeSettings layer_tree_settings_; | 600 LayerTreeSettings layer_tree_settings_; |
565 scoped_ptr<MockLayerTreeHost> layer_tree_host_; | 601 scoped_ptr<MockLayerTreeHost> layer_tree_host_; |
566 }; | 602 }; |
567 | 603 |
568 TEST_F(ScaledScrollbarLayerTestResourceCreation, ScaledResourceUpload) { | 604 TEST_F(ScaledScrollbarLayerTestResourceCreation, ScaledResourceUpload) { |
569 layer_tree_settings_.solid_color_scrollbars = false; | 605 layer_tree_settings_.solid_color_scrollbars = false; |
570 // Pick a test scale that moves the scrollbar's (non-zero) position to | 606 // Pick a test scale that moves the scrollbar's (non-zero) position to |
571 // a non-pixel-aligned location. | 607 // a non-pixel-aligned location. |
572 TestResourceUpload(2, 1.41f); | 608 TestResourceUpload(.041f); |
| 609 TestResourceUpload(1.41f); |
| 610 TestResourceUpload(4.1f); |
573 } | 611 } |
574 | 612 |
575 } // namespace | 613 } // namespace |
576 } // namespace cc | 614 } // namespace cc |
OLD | NEW |