123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264 |
- // Copyright 2011 The Chromium Authors. All rights reserved.
- // Use of this source code is governed by a BSD-style license that can be
- // found in the LICENSE file.
- #include "cc/layers/append_quads_data.h"
- #include "cc/layers/layer_impl.h"
- #include "cc/layers/render_surface_impl.h"
- #include "cc/test/fake_impl_task_runner_provider.h"
- #include "cc/test/fake_layer_tree_frame_sink.h"
- #include "cc/test/fake_layer_tree_host_impl.h"
- #include "cc/test/fake_picture_layer_impl.h"
- #include "cc/test/layer_tree_impl_test_base.h"
- #include "cc/test/mock_occlusion_tracker.h"
- #include "cc/test/test_task_graph_runner.h"
- #include "cc/trees/layer_tree_impl.h"
- #include "cc/trees/single_thread_proxy.h"
- #include "components/viz/common/quads/shared_quad_state.h"
- #include "components/viz/common/quads/tile_draw_quad.h"
- #include "testing/gmock/include/gmock/gmock.h"
- #include "testing/gtest/include/gtest/gtest.h"
- #include "ui/gfx/geometry/transform.h"
- #include "base/memory/ptr_util.h"
- #include "cc/test/fake_raster_source.h"
- namespace cc {
- namespace {
- #define EXECUTE_AND_VERIFY_SURFACE_CHANGED(code_to_test) \
- render_surface->ResetPropertyChangedFlags(); \
- code_to_test; \
- EXPECT_TRUE(render_surface->SurfacePropertyChanged())
- #define EXECUTE_AND_VERIFY_SURFACE_DID_NOT_CHANGE(code_to_test) \
- render_surface->ResetPropertyChangedFlags(); \
- code_to_test; \
- EXPECT_FALSE(render_surface->SurfacePropertyChanged())
- // The AppendQuads method of this class generates multiple quads and one of them
- // does not intersect with visible_layer_rect.
- class FakePictureLayerImplForRenderSurfaceTest : public FakePictureLayerImpl {
- public:
- static std::unique_ptr<FakePictureLayerImplForRenderSurfaceTest> Create(
- LayerTreeImpl* tree_impl,
- int id) {
- return base::WrapUnique(
- new FakePictureLayerImplForRenderSurfaceTest(tree_impl, id));
- }
- std::unique_ptr<LayerImpl> CreateLayerImpl(
- LayerTreeImpl* tree_impl) const override {
- return base::WrapUnique(
- new FakePictureLayerImplForRenderSurfaceTest(tree_impl, id()));
- }
- void SetQuadRectsForTesting(std::vector<gfx::Rect> quad_rects) {
- quad_rects_ = quad_rects;
- }
- bool HasValidTilePriorities() const override { return false; }
- void AppendQuads(viz::CompositorRenderPass* render_pass,
- AppendQuadsData* append_quads_data) override {
- viz::SharedQuadState* shared_quad_state =
- render_pass->CreateAndAppendSharedQuadState();
- float max_contents_scale = 1.f;
- PopulateScaledSharedQuadState(shared_quad_state, max_contents_scale,
- contents_opaque());
- bool needs_blending = false;
- for (const auto& rect : quad_rects_) {
- auto* quad = render_pass->CreateAndAppendDrawQuad<viz::TileDrawQuad>();
- quad->SetNew(shared_quad_state, rect, rect, needs_blending,
- viz::kInvalidResourceId, gfx::RectF(rect), bounds(), false,
- false, false);
- }
- }
- protected:
- FakePictureLayerImplForRenderSurfaceTest(LayerTreeImpl* tree_impl, int id)
- : FakePictureLayerImpl(tree_impl, id) {}
- std::vector<gfx::Rect> quad_rects_;
- };
- TEST(RenderSurfaceTest, VerifySurfaceChangesAreTrackedProperly) {
- //
- // This test checks that SurfacePropertyChanged() has the correct behavior.
- //
- LayerTreeImplTestBase impl;
- LayerImpl* root = impl.root_layer();
- LayerTreeImpl* active_tree = impl.host_impl()->active_tree();
- LayerImpl* layer = impl.AddLayer<LayerImpl>();
- CopyProperties(root, layer);
- CreateEffectNode(layer).render_surface_reason = RenderSurfaceReason::kTest;
- UpdateDrawProperties(active_tree);
- gfx::Rect test_rect(3, 4, 5, 6);
- active_tree->ResetAllChangeTracking();
- RenderSurfaceImpl* render_surface = GetRenderSurface(layer);
- ASSERT_TRUE(render_surface);
- // Currently, the content_rect, clip_rect, and
- // owning_layer->layerPropertyChanged() are the only sources of change.
- EXECUTE_AND_VERIFY_SURFACE_CHANGED(render_surface->SetClipRect(test_rect));
- EXECUTE_AND_VERIFY_SURFACE_CHANGED(
- render_surface->SetContentRectForTesting(test_rect));
- active_tree->SetOpacityMutated(root->element_id(), 0.5f);
- EXPECT_TRUE(render_surface->SurfacePropertyChanged());
- active_tree->ResetAllChangeTracking();
- // Setting the surface properties to the same values again should not be
- // considered "change".
- EXECUTE_AND_VERIFY_SURFACE_DID_NOT_CHANGE(
- render_surface->SetClipRect(test_rect));
- EXECUTE_AND_VERIFY_SURFACE_DID_NOT_CHANGE(
- render_surface->SetContentRectForTesting(test_rect));
- constexpr int kArbitraryLayerId = 200;
- std::unique_ptr<LayerImpl> dummy_mask =
- LayerImpl::Create(active_tree, kArbitraryLayerId);
- gfx::Transform dummy_matrix;
- dummy_matrix.Translate(1.0, 2.0);
- // The rest of the surface properties are either internal and should not cause
- // change, or they are already accounted for by the
- // owninglayer->layerPropertyChanged().
- EXECUTE_AND_VERIFY_SURFACE_DID_NOT_CHANGE(
- render_surface->SetDrawOpacity(0.5f));
- EXECUTE_AND_VERIFY_SURFACE_DID_NOT_CHANGE(
- render_surface->SetDrawTransform(dummy_matrix));
- }
- TEST(RenderSurfaceTest, SanityCheckSurfaceCreatesCorrectSharedQuadState) {
- LayerTreeImplTestBase impl;
- LayerImpl* root = impl.root_layer();
- LayerImpl* layer = impl.AddLayer<LayerImpl>();
- CopyProperties(root, layer);
- auto& effect_node = CreateEffectNode(layer);
- effect_node.render_surface_reason = RenderSurfaceReason::kBlendMode;
- SkBlendMode blend_mode = SkBlendMode::kSoftLight;
- effect_node.blend_mode = blend_mode;
- UpdateDrawProperties(impl.host_impl()->active_tree());
- RenderSurfaceImpl* render_surface = GetRenderSurface(layer);
- ASSERT_TRUE(render_surface);
- gfx::Rect content_rect(0, 0, 50, 50);
- gfx::Rect clip_rect(5, 5, 40, 40);
- gfx::Transform origin;
- origin.Translate(30, 40);
- render_surface->SetContentRectForTesting(content_rect);
- render_surface->SetClipRect(clip_rect);
- render_surface->SetDrawOpacity(1.f);
- render_surface->SetDrawTransform(origin);
- auto render_pass = viz::CompositorRenderPass::Create();
- AppendQuadsData append_quads_data;
- render_surface->AppendQuads(DRAW_MODE_HARDWARE, render_pass.get(),
- &append_quads_data);
- ASSERT_EQ(1u, render_pass->shared_quad_state_list.size());
- viz::SharedQuadState* shared_quad_state =
- render_pass->shared_quad_state_list.front();
- EXPECT_EQ(30.0,
- shared_quad_state->quad_to_target_transform.matrix().rc(0, 3));
- EXPECT_EQ(40.0,
- shared_quad_state->quad_to_target_transform.matrix().rc(1, 3));
- EXPECT_EQ(content_rect,
- gfx::Rect(shared_quad_state->visible_quad_layer_rect));
- EXPECT_EQ(1.f, shared_quad_state->opacity);
- EXPECT_EQ(blend_mode, shared_quad_state->blend_mode);
- }
- TEST(RenderSurfaceTest, SanityCheckSurfaceCreatesCorrectRenderPass) {
- LayerTreeImplTestBase impl;
- LayerImpl* root = impl.root_layer();
- LayerImpl* layer = impl.AddLayer<LayerImpl>();
- CopyProperties(root, layer);
- auto& effect_node = CreateEffectNode(layer);
- effect_node.render_surface_reason = RenderSurfaceReason::kTest;
- UpdateDrawProperties(impl.host_impl()->active_tree());
- RenderSurfaceImpl* render_surface = GetRenderSurface(layer);
- ASSERT_TRUE(render_surface);
- gfx::Rect content_rect(0, 0, 50, 50);
- gfx::Transform origin;
- origin.Translate(30.0, 40.0);
- render_surface->SetScreenSpaceTransform(origin);
- render_surface->SetContentRectForTesting(content_rect);
- auto pass = render_surface->CreateRenderPass();
- EXPECT_EQ(viz::CompositorRenderPassId{2}, pass->id);
- EXPECT_EQ(content_rect, pass->output_rect);
- EXPECT_EQ(origin, pass->transform_to_root_target);
- }
- TEST(RenderSurfaceTest, SanityCheckSurfaceIgnoreMaskLayerOcclusion) {
- LayerTreeImplTestBase impl;
- LayerImpl* root = impl.root_layer();
- // Set a big enough viewport to show the entire render pass.
- impl.host_impl()->active_tree()->SetDeviceViewportRect(gfx::Rect(1000, 1000));
- auto* layer = impl.AddLayer<LayerImpl>();
- layer->SetBounds(gfx::Size(200, 100));
- layer->SetDrawsContent(true);
- CopyProperties(root, layer);
- CreateEffectNode(layer);
- auto* mask_layer = impl.AddLayer<FakePictureLayerImplForRenderSurfaceTest>();
- scoped_refptr<FakeRasterSource> raster_source(
- FakeRasterSource::CreateFilled(mask_layer->bounds()));
- mask_layer->SetRasterSource(raster_source, Region());
- std::vector<gfx::Rect> quad_rects;
- quad_rects.push_back(gfx::Rect(0, 0, 100, 100));
- quad_rects.push_back(gfx::Rect(100, 0, 100, 100));
- mask_layer->SetQuadRectsForTesting(quad_rects);
- SetupMaskProperties(layer, mask_layer);
- UpdateDrawProperties(impl.host_impl()->active_tree());
- RenderSurfaceImpl* render_surface = GetRenderSurface(layer);
- ASSERT_TRUE(render_surface);
- gfx::Rect content_rect(0, 0, 200, 100);
- gfx::Rect occluded(0, 0, 200, 100);
- render_surface->SetContentRectForTesting(content_rect);
- mask_layer->draw_properties().occlusion_in_content_space =
- Occlusion(gfx::Transform(), SimpleEnclosedRegion(occluded),
- SimpleEnclosedRegion(occluded));
- auto render_pass = viz::CompositorRenderPass::Create();
- AppendQuadsData append_quads_data;
- render_surface->AppendQuads(DRAW_MODE_HARDWARE, render_pass.get(),
- &append_quads_data);
- ASSERT_EQ(1u, render_pass->shared_quad_state_list.size());
- viz::SharedQuadState* shared_quad_state =
- render_pass->shared_quad_state_list.front();
- EXPECT_EQ(content_rect,
- gfx::Rect(shared_quad_state->visible_quad_layer_rect));
- ASSERT_EQ(1u, render_pass->quad_list.size());
- EXPECT_EQ(gfx::Rect(0, 0, 200, 100).ToString(),
- render_pass->quad_list.front()->rect.ToString());
- }
- } // namespace
- } // namespace cc
|