delegated_renderer_layer_impl_unittest.cc revision c2e0dbddbe15c98d52c4786dac06cb8952a8ae6d
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#include "cc/layers/delegated_renderer_layer_impl.h"
6
7#include "cc/base/scoped_ptr_vector.h"
8#include "cc/layers/append_quads_data.h"
9#include "cc/layers/quad_sink.h"
10#include "cc/layers/solid_color_layer_impl.h"
11#include "cc/quads/render_pass_draw_quad.h"
12#include "cc/quads/solid_color_draw_quad.h"
13#include "cc/test/fake_delegated_renderer_layer_impl.h"
14#include "cc/test/fake_layer_tree_host_impl.h"
15#include "cc/test/fake_layer_tree_host_impl_client.h"
16#include "cc/test/fake_output_surface.h"
17#include "cc/test/fake_proxy.h"
18#include "cc/test/fake_rendering_stats_instrumentation.h"
19#include "cc/test/geometry_test_utils.h"
20#include "cc/test/mock_quad_culler.h"
21#include "cc/test/render_pass_test_common.h"
22#include "cc/test/render_pass_test_utils.h"
23#include "cc/test/test_web_graphics_context_3d.h"
24#include "cc/trees/layer_tree_host_impl.h"
25#include "cc/trees/layer_tree_impl.h"
26#include "cc/trees/single_thread_proxy.h"
27#include "testing/gtest/include/gtest/gtest.h"
28#include "ui/gfx/transform.h"
29
30namespace cc {
31namespace {
32
33class DelegatedRendererLayerImplTest : public testing::Test {
34 public:
35  DelegatedRendererLayerImplTest()
36      : proxy_(scoped_ptr<Thread>(NULL)),
37        always_impl_thread_and_main_thread_blocked_(&proxy_) {
38    LayerTreeSettings settings;
39    settings.minimum_occlusion_tracking_size = gfx::Size();
40
41    host_impl_ = LayerTreeHostImpl::Create(settings,
42                                           &client_,
43                                           &proxy_,
44                                           &stats_instrumentation_);
45    host_impl_->InitializeRenderer(CreateFakeOutputSurface());
46    host_impl_->SetViewportSize(gfx::Size(10, 10));
47  }
48
49 protected:
50  FakeProxy proxy_;
51  FakeLayerTreeHostImplClient client_;
52  DebugScopedSetImplThreadAndMainThreadBlocked
53      always_impl_thread_and_main_thread_blocked_;
54  FakeRenderingStatsInstrumentation stats_instrumentation_;
55  scoped_ptr<LayerTreeHostImpl> host_impl_;
56};
57
58class DelegatedRendererLayerImplTestSimple
59    : public DelegatedRendererLayerImplTest {
60 public:
61  DelegatedRendererLayerImplTestSimple()
62      : DelegatedRendererLayerImplTest() {
63    scoped_ptr<LayerImpl> root_layer = SolidColorLayerImpl::Create(
64        host_impl_->active_tree(), 1).PassAs<LayerImpl>();
65    scoped_ptr<LayerImpl> layer_before = SolidColorLayerImpl::Create(
66        host_impl_->active_tree(), 2).PassAs<LayerImpl>();
67    scoped_ptr<LayerImpl> layer_after = SolidColorLayerImpl::Create(
68        host_impl_->active_tree(), 3).PassAs<LayerImpl>();
69    scoped_ptr<FakeDelegatedRendererLayerImpl> delegated_renderer_layer =
70        FakeDelegatedRendererLayerImpl::Create(host_impl_->active_tree(), 4);
71
72    host_impl_->SetViewportSize(gfx::Size(100, 100));
73    root_layer->SetBounds(gfx::Size(100, 100));
74
75    layer_before->SetPosition(gfx::Point(20, 20));
76    layer_before->SetBounds(gfx::Size(14, 14));
77    layer_before->SetContentBounds(gfx::Size(14, 14));
78    layer_before->SetDrawsContent(true);
79    layer_before->SetForceRenderSurface(true);
80
81    layer_after->SetPosition(gfx::Point(5, 5));
82    layer_after->SetBounds(gfx::Size(15, 15));
83    layer_after->SetContentBounds(gfx::Size(15, 15));
84    layer_after->SetDrawsContent(true);
85    layer_after->SetForceRenderSurface(true);
86
87    delegated_renderer_layer->SetPosition(gfx::Point(3, 3));
88    delegated_renderer_layer->SetBounds(gfx::Size(10, 10));
89    delegated_renderer_layer->SetContentBounds(gfx::Size(10, 10));
90    delegated_renderer_layer->SetDrawsContent(true);
91    gfx::Transform transform;
92    transform.Translate(1.0, 1.0);
93    delegated_renderer_layer->SetTransform(transform);
94
95    ScopedPtrVector<RenderPass> delegated_render_passes;
96    TestRenderPass* pass1 = AddRenderPass(
97        &delegated_render_passes,
98        RenderPass::Id(9, 6),
99        gfx::Rect(6, 6, 6, 6),
100        gfx::Transform());
101    AddQuad(pass1, gfx::Rect(0, 0, 6, 6), 33u);
102    TestRenderPass* pass2 = AddRenderPass(
103        &delegated_render_passes,
104        RenderPass::Id(9, 7),
105        gfx::Rect(7, 7, 7, 7),
106        gfx::Transform());
107    AddQuad(pass2, gfx::Rect(0, 0, 7, 7), 22u);
108    AddRenderPassQuad(pass2, pass1);
109    TestRenderPass* pass3 = AddRenderPass(
110        &delegated_render_passes,
111        RenderPass::Id(9, 8),
112        gfx::Rect(0, 0, 8, 8),
113        gfx::Transform());
114    AddRenderPassQuad(pass3, pass2);
115    delegated_renderer_layer->SetFrameDataForRenderPasses(
116        &delegated_render_passes);
117
118    // The RenderPasses should be taken by the layer.
119    EXPECT_EQ(0u, delegated_render_passes.size());
120
121    root_layer_ = root_layer.get();
122    layer_before_ = layer_before.get();
123    layer_after_ = layer_after.get();
124    delegated_renderer_layer_ = delegated_renderer_layer.get();
125
126    // Force the delegated RenderPasses to come before the RenderPass from
127    // layer_after.
128    layer_after->AddChild(delegated_renderer_layer.PassAs<LayerImpl>());
129    root_layer->AddChild(layer_after.Pass());
130
131    // Get the RenderPass generated by layer_before to come before the delegated
132    // RenderPasses.
133    root_layer->AddChild(layer_before.Pass());
134    host_impl_->active_tree()->SetRootLayer(root_layer.Pass());
135  }
136
137 protected:
138  LayerImpl* root_layer_;
139  LayerImpl* layer_before_;
140  LayerImpl* layer_after_;
141  DelegatedRendererLayerImpl* delegated_renderer_layer_;
142};
143
144TEST_F(DelegatedRendererLayerImplTestSimple, AddsContributingRenderPasses) {
145  LayerTreeHostImpl::FrameData frame;
146  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
147
148  // Each non-DelegatedRendererLayer added one RenderPass. The
149  // DelegatedRendererLayer added two contributing passes.
150  ASSERT_EQ(5u, frame.render_passes.size());
151
152  // The DelegatedRendererLayer should have added its contributing RenderPasses
153  // to the frame.
154  EXPECT_EQ(4, frame.render_passes[1]->id.layer_id);
155  EXPECT_EQ(1, frame.render_passes[1]->id.index);
156  EXPECT_EQ(4, frame.render_passes[2]->id.layer_id);
157  EXPECT_EQ(2, frame.render_passes[2]->id.index);
158  // And all other RenderPasses should be non-delegated.
159  EXPECT_NE(4, frame.render_passes[0]->id.layer_id);
160  EXPECT_EQ(0, frame.render_passes[0]->id.index);
161  EXPECT_NE(4, frame.render_passes[3]->id.layer_id);
162  EXPECT_EQ(0, frame.render_passes[3]->id.index);
163  EXPECT_NE(4, frame.render_passes[4]->id.layer_id);
164  EXPECT_EQ(0, frame.render_passes[4]->id.index);
165
166  // The DelegatedRendererLayer should have added its RenderPasses to the frame
167  // in order.
168  EXPECT_EQ(gfx::Rect(6, 6, 6, 6).ToString(),
169            frame.render_passes[1]->output_rect.ToString());
170  EXPECT_EQ(gfx::Rect(7, 7, 7, 7).ToString(),
171            frame.render_passes[2]->output_rect.ToString());
172
173  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
174  host_impl_->DidDrawAllLayers(frame);
175}
176
177TEST_F(DelegatedRendererLayerImplTestSimple,
178       AddsQuadsToContributingRenderPasses) {
179  LayerTreeHostImpl::FrameData frame;
180  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
181
182  // Each non-DelegatedRendererLayer added one RenderPass. The
183  // DelegatedRendererLayer added two contributing passes.
184  ASSERT_EQ(5u, frame.render_passes.size());
185
186  // The DelegatedRendererLayer should have added its contributing RenderPasses
187  // to the frame.
188  EXPECT_EQ(4, frame.render_passes[1]->id.layer_id);
189  EXPECT_EQ(1, frame.render_passes[1]->id.index);
190  EXPECT_EQ(4, frame.render_passes[2]->id.layer_id);
191  EXPECT_EQ(2, frame.render_passes[2]->id.index);
192
193  // The DelegatedRendererLayer should have added copies of its quads to
194  // contributing RenderPasses.
195  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
196  EXPECT_EQ(gfx::Rect(0, 0, 6, 6).ToString(),
197            frame.render_passes[1]->quad_list[0]->rect.ToString());
198
199  // Verify it added the right quads.
200  ASSERT_EQ(2u, frame.render_passes[2]->quad_list.size());
201  EXPECT_EQ(gfx::Rect(0, 0, 7, 7).ToString(),
202            frame.render_passes[2]->quad_list[0]->rect.ToString());
203  EXPECT_EQ(gfx::Rect(6, 6, 6, 6).ToString(),
204            frame.render_passes[2]->quad_list[1]->rect.ToString());
205  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
206  EXPECT_EQ(gfx::Rect(0, 0, 6, 6).ToString(),
207            frame.render_passes[1]->quad_list[0]->rect.ToString());
208
209  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
210  host_impl_->DidDrawAllLayers(frame);
211}
212
213TEST_F(DelegatedRendererLayerImplTestSimple, AddsQuadsToTargetRenderPass) {
214  LayerTreeHostImpl::FrameData frame;
215  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
216
217  // Each non-DelegatedRendererLayer added one RenderPass. The
218  // DelegatedRendererLayer added two contributing passes.
219  ASSERT_EQ(5u, frame.render_passes.size());
220
221  // The layer's target is the RenderPass from layer_after_.
222  EXPECT_EQ(RenderPass::Id(3, 0), frame.render_passes[3]->id);
223
224  // The DelegatedRendererLayer should have added copies of quads in its root
225  // RenderPass to its target RenderPass. The layer_after_ also adds one quad.
226  ASSERT_EQ(2u, frame.render_passes[3]->quad_list.size());
227
228  // Verify it added the right quads.
229  EXPECT_EQ(gfx::Rect(7, 7, 7, 7).ToString(),
230            frame.render_passes[3]->quad_list[0]->rect.ToString());
231
232  // Its target layer should have a quad as well.
233  EXPECT_EQ(gfx::Rect(0, 0, 15, 15).ToString(),
234            frame.render_passes[3]->quad_list[1]->rect.ToString());
235
236  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
237  host_impl_->DidDrawAllLayers(frame);
238}
239
240TEST_F(DelegatedRendererLayerImplTestSimple,
241       QuadsFromRootRenderPassAreModifiedForTheTarget) {
242  LayerTreeHostImpl::FrameData frame;
243  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
244
245  // Each non-DelegatedRendererLayer added one RenderPass. The
246  // DelegatedRendererLayer added two contributing passes.
247  ASSERT_EQ(5u, frame.render_passes.size());
248
249  // The DelegatedRendererLayer is at position 3,3 compared to its target, and
250  // has a translation transform of 1,1. So its root RenderPass' quads should
251  // all be transformed by that combined amount.
252  // The DelegatedRendererLayer has a size of 10x10, but the root delegated
253  // RenderPass has a size of 8x8, so any quads should be scaled by 10/8.
254  gfx::Transform transform;
255  transform.Translate(4.0, 4.0);
256  transform.Scale(10.0 / 8.0, 10.0 / 8.0);
257  EXPECT_TRANSFORMATION_MATRIX_EQ(
258      transform, frame.render_passes[3]->quad_list[0]->quadTransform());
259
260  // Quads from non-root RenderPasses should not be shifted though.
261  ASSERT_EQ(2u, frame.render_passes[2]->quad_list.size());
262  EXPECT_TRANSFORMATION_MATRIX_EQ(
263      gfx::Transform(), frame.render_passes[2]->quad_list[0]->quadTransform());
264  EXPECT_TRANSFORMATION_MATRIX_EQ(
265      gfx::Transform(), frame.render_passes[2]->quad_list[1]->quadTransform());
266  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
267  EXPECT_TRANSFORMATION_MATRIX_EQ(
268      gfx::Transform(), frame.render_passes[1]->quad_list[0]->quadTransform());
269
270  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
271  host_impl_->DidDrawAllLayers(frame);
272}
273
274TEST_F(DelegatedRendererLayerImplTestSimple, DoesNotOwnARenderSurface) {
275  LayerTreeHostImpl::FrameData frame;
276  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
277
278  // If the DelegatedRendererLayer is axis aligned and has opacity 1, then it
279  // has no need to be a RenderSurface for the quads it carries.
280  EXPECT_FALSE(delegated_renderer_layer_->render_surface());
281
282  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
283  host_impl_->DidDrawAllLayers(frame);
284}
285
286TEST_F(DelegatedRendererLayerImplTestSimple, DoesOwnARenderSurfaceForOpacity) {
287  delegated_renderer_layer_->SetOpacity(0.5f);
288
289  LayerTreeHostImpl::FrameData frame;
290  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
291
292  // This test case has quads from multiple layers in the delegated renderer, so
293  // if the DelegatedRendererLayer has opacity < 1, it should end up with a
294  // render surface.
295  EXPECT_TRUE(delegated_renderer_layer_->render_surface());
296
297  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
298  host_impl_->DidDrawAllLayers(frame);
299}
300
301TEST_F(DelegatedRendererLayerImplTestSimple,
302       DoesOwnARenderSurfaceForTransform) {
303  gfx::Transform rotation;
304  rotation.RotateAboutZAxis(30.0);
305  delegated_renderer_layer_->SetTransform(rotation);
306
307  LayerTreeHostImpl::FrameData frame;
308  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
309
310  // This test case has quads from multiple layers in the delegated renderer, so
311  // if the DelegatedRendererLayer has opacity < 1, it should end up with a
312  // render surface.
313  EXPECT_TRUE(delegated_renderer_layer_->render_surface());
314
315  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
316  host_impl_->DidDrawAllLayers(frame);
317}
318
319class DelegatedRendererLayerImplTestOwnSurface
320    : public DelegatedRendererLayerImplTestSimple {
321 public:
322  DelegatedRendererLayerImplTestOwnSurface()
323      : DelegatedRendererLayerImplTestSimple() {
324    delegated_renderer_layer_->SetForceRenderSurface(true);
325  }
326};
327
328TEST_F(DelegatedRendererLayerImplTestOwnSurface, AddsRenderPasses) {
329  LayerTreeHostImpl::FrameData frame;
330  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
331
332  // Each non-DelegatedRendererLayer added one RenderPass. The
333  // DelegatedRendererLayer added two contributing passes and its owned surface
334  // added one pass.
335  ASSERT_EQ(6u, frame.render_passes.size());
336
337  // The DelegatedRendererLayer should have added its contributing RenderPasses
338  // to the frame.
339  EXPECT_EQ(4, frame.render_passes[1]->id.layer_id);
340  EXPECT_EQ(1, frame.render_passes[1]->id.index);
341  EXPECT_EQ(4, frame.render_passes[2]->id.layer_id);
342  EXPECT_EQ(2, frame.render_passes[2]->id.index);
343  // The DelegatedRendererLayer should have added a RenderPass for its surface
344  // to the frame.
345  EXPECT_EQ(4, frame.render_passes[1]->id.layer_id);
346  EXPECT_EQ(0, frame.render_passes[3]->id.index);
347  // And all other RenderPasses should be non-delegated.
348  EXPECT_NE(4, frame.render_passes[0]->id.layer_id);
349  EXPECT_EQ(0, frame.render_passes[0]->id.index);
350  EXPECT_NE(4, frame.render_passes[4]->id.layer_id);
351  EXPECT_EQ(0, frame.render_passes[4]->id.index);
352  EXPECT_NE(4, frame.render_passes[5]->id.layer_id);
353  EXPECT_EQ(0, frame.render_passes[5]->id.index);
354
355  // The DelegatedRendererLayer should have added its RenderPasses to the frame
356  // in order.
357  EXPECT_EQ(gfx::Rect(6, 6, 6, 6).ToString(),
358            frame.render_passes[1]->output_rect.ToString());
359  EXPECT_EQ(gfx::Rect(7, 7, 7, 7).ToString(),
360            frame.render_passes[2]->output_rect.ToString());
361
362  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
363  host_impl_->DidDrawAllLayers(frame);
364}
365
366TEST_F(DelegatedRendererLayerImplTestOwnSurface,
367       AddsQuadsToContributingRenderPasses) {
368  LayerTreeHostImpl::FrameData frame;
369  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
370
371  // Each non-DelegatedRendererLayer added one RenderPass. The
372  // DelegatedRendererLayer added two contributing passes and its owned surface
373  // added one pass.
374  ASSERT_EQ(6u, frame.render_passes.size());
375
376  // The DelegatedRendererLayer should have added its contributing RenderPasses
377  // to the frame.
378  EXPECT_EQ(4, frame.render_passes[1]->id.layer_id);
379  EXPECT_EQ(1, frame.render_passes[1]->id.index);
380  EXPECT_EQ(4, frame.render_passes[2]->id.layer_id);
381  EXPECT_EQ(2, frame.render_passes[2]->id.index);
382
383  // The DelegatedRendererLayer should have added copies of its quads to
384  // contributing RenderPasses.
385  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
386  EXPECT_EQ(gfx::Rect(0, 0, 6, 6).ToString(),
387            frame.render_passes[1]->quad_list[0]->rect.ToString());
388
389  // Verify it added the right quads.
390  ASSERT_EQ(2u, frame.render_passes[2]->quad_list.size());
391  EXPECT_EQ(gfx::Rect(0, 0, 7, 7).ToString(),
392            frame.render_passes[2]->quad_list[0]->rect.ToString());
393  EXPECT_EQ(gfx::Rect(6, 6, 6, 6).ToString(),
394            frame.render_passes[2]->quad_list[1]->rect.ToString());
395  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
396  EXPECT_EQ(gfx::Rect(0, 0, 6, 6).ToString(),
397            frame.render_passes[1]->quad_list[0]->rect.ToString());
398
399  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
400  host_impl_->DidDrawAllLayers(frame);
401}
402
403TEST_F(DelegatedRendererLayerImplTestOwnSurface, AddsQuadsToTargetRenderPass) {
404  LayerTreeHostImpl::FrameData frame;
405  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
406
407  // Each non-DelegatedRendererLayer added one RenderPass. The
408  // DelegatedRendererLayer added two contributing passes and its owned surface
409  // added one pass.
410  ASSERT_EQ(6u, frame.render_passes.size());
411
412  // The layer's target is the RenderPass owned by itself.
413  EXPECT_EQ(RenderPass::Id(4, 0), frame.render_passes[3]->id);
414
415  // The DelegatedRendererLayer should have added copies of quads in its root
416  // RenderPass to its target RenderPass.
417  // The layer_after also adds one quad.
418  ASSERT_EQ(1u, frame.render_passes[3]->quad_list.size());
419
420  // Verify it added the right quads.
421  EXPECT_EQ(gfx::Rect(7, 7, 7, 7).ToString(),
422            frame.render_passes[3]->quad_list[0]->rect.ToString());
423
424  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
425  host_impl_->DidDrawAllLayers(frame);
426}
427
428TEST_F(DelegatedRendererLayerImplTestOwnSurface,
429       QuadsFromRootRenderPassAreNotModifiedForTheTarget) {
430  LayerTreeHostImpl::FrameData frame;
431  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
432
433  // Each non-DelegatedRendererLayer added one RenderPass. The
434  // DelegatedRendererLayer added two contributing passes and its owned surface
435  // added one pass.
436  ASSERT_EQ(6u, frame.render_passes.size());
437
438  // Because the DelegatedRendererLayer owns a RenderSurfaceImpl, its root
439  // RenderPass' quads do not need to be translated at all. However, they are
440  // scaled from the frame's size (8x8) to the layer's bounds (10x10).
441  gfx::Transform transform;
442  transform.Scale(10.0 / 8.0, 10.0 / 8.0);
443  EXPECT_TRANSFORMATION_MATRIX_EQ(
444      transform, frame.render_passes[3]->quad_list[0]->quadTransform());
445
446  // Quads from non-root RenderPasses should not be shifted either.
447  ASSERT_EQ(2u, frame.render_passes[2]->quad_list.size());
448  EXPECT_TRANSFORMATION_MATRIX_EQ(
449      gfx::Transform(), frame.render_passes[2]->quad_list[0]->quadTransform());
450  EXPECT_TRANSFORMATION_MATRIX_EQ(
451      gfx::Transform(), frame.render_passes[2]->quad_list[1]->quadTransform());
452  ASSERT_EQ(1u, frame.render_passes[1]->quad_list.size());
453  EXPECT_TRANSFORMATION_MATRIX_EQ(
454      gfx::Transform(), frame.render_passes[1]->quad_list[0]->quadTransform());
455
456  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
457  host_impl_->DidDrawAllLayers(frame);
458}
459
460class DelegatedRendererLayerImplTestTransform
461    : public DelegatedRendererLayerImplTest {
462 public:
463  void SetUpTest() {
464    scoped_ptr<LayerImpl> root_layer = LayerImpl::Create(
465        host_impl_->active_tree(), 1);
466    scoped_ptr<FakeDelegatedRendererLayerImpl> delegated_renderer_layer =
467        FakeDelegatedRendererLayerImpl::Create(host_impl_->active_tree(), 2);
468
469    host_impl_->SetViewportSize(gfx::Size(100, 100));
470    root_layer->SetBounds(gfx::Size(100, 100));
471
472    delegated_renderer_layer->SetPosition(gfx::Point(20, 20));
473    delegated_renderer_layer->SetBounds(gfx::Size(30, 30));
474    delegated_renderer_layer->SetContentBounds(gfx::Size(30, 30));
475    delegated_renderer_layer->SetDrawsContent(true);
476    gfx::Transform transform;
477    transform.Scale(2.0, 2.0);
478    transform.Translate(8.0, 8.0);
479    delegated_renderer_layer->SetTransform(transform);
480
481    ScopedPtrVector<RenderPass> delegated_render_passes;
482
483    gfx::Size child_pass_content_bounds(7, 7);
484    gfx::Rect child_pass_rect(20, 20, 7, 7);
485    gfx::Transform child_pass_transform;
486    child_pass_transform.Scale(0.8, 0.8);
487    child_pass_transform.Translate(9.0, 9.0);
488    gfx::Rect child_pass_clip_rect(21, 21, 3, 3);
489    bool child_pass_clipped = false;
490
491    {
492      TestRenderPass* pass = AddRenderPass(
493          &delegated_render_passes,
494          RenderPass::Id(10, 7),
495          child_pass_rect,
496          gfx::Transform());
497      MockQuadCuller quad_sink(&pass->quad_list, &pass->shared_quad_state_list);
498      AppendQuadsData data(pass->id);
499      SharedQuadState* shared_quad_state = quad_sink.UseSharedQuadState(
500          SharedQuadState::Create());
501      shared_quad_state->SetAll(
502          child_pass_transform,
503          child_pass_content_bounds,
504          child_pass_rect,
505          child_pass_clip_rect,
506          child_pass_clipped,
507          1.f);
508
509      scoped_ptr<SolidColorDrawQuad> color_quad;
510      color_quad = SolidColorDrawQuad::Create();
511      color_quad->SetNew(shared_quad_state, gfx::Rect(20, 20, 3, 7), 1u, false);
512      quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
513
514      color_quad = SolidColorDrawQuad::Create();
515      color_quad->SetNew(shared_quad_state, gfx::Rect(23, 20, 4, 7), 1u, false);
516      quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
517    }
518
519    gfx::Size root_pass_content_bounds(50, 50);
520    gfx::Rect root_pass_rect(0, 0, 50, 50);
521    gfx::Transform root_pass_transform;
522    root_pass_transform.Scale(1.5, 1.5);
523    root_pass_transform.Translate(7.0, 7.0);
524    gfx::Rect root_pass_clip_rect(10, 10, 35, 35);
525    bool root_pass_clipped = root_delegated_render_pass_is_clipped_;
526
527    TestRenderPass* pass = AddRenderPass(
528        &delegated_render_passes,
529        RenderPass::Id(9, 6),
530        root_pass_rect,
531        gfx::Transform());
532    MockQuadCuller quad_sink(&pass->quad_list, &pass->shared_quad_state_list);
533    AppendQuadsData data(pass->id);
534    SharedQuadState* shared_quad_state =
535        quad_sink.UseSharedQuadState(SharedQuadState::Create());
536    shared_quad_state->SetAll(
537        root_pass_transform,
538        root_pass_content_bounds,
539        root_pass_rect,
540        root_pass_clip_rect,
541        root_pass_clipped,
542        1.f);
543
544    scoped_ptr<RenderPassDrawQuad> render_pass_quad =
545        RenderPassDrawQuad::Create();
546    render_pass_quad->SetNew(
547        shared_quad_state,
548        gfx::Rect(5, 5, 7, 7),  // rect
549        RenderPass::Id(10, 7),  // render_pass_id
550        false,  // is_replica
551        0,  // mask_resource_id
552        child_pass_rect,  // contents_changed_since_last_frame
553        gfx::RectF(),  // mask_uv_rect
554        WebKit::WebFilterOperations(),  // filters
555        skia::RefPtr<SkImageFilter>(),  // filter
556        WebKit::WebFilterOperations());  // background_filters
557    quad_sink.Append(render_pass_quad.PassAs<DrawQuad>(), &data);
558
559    scoped_ptr<SolidColorDrawQuad> color_quad;
560    color_quad = SolidColorDrawQuad::Create();
561    color_quad->SetNew(shared_quad_state, gfx::Rect(0, 0, 10, 10), 1u, false);
562    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
563
564    color_quad = SolidColorDrawQuad::Create();
565    color_quad->SetNew(shared_quad_state, gfx::Rect(0, 10, 10, 10), 2u, false);
566    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
567
568    color_quad = SolidColorDrawQuad::Create();
569    color_quad->SetNew(shared_quad_state, gfx::Rect(10, 0, 10, 10), 3u, false);
570    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
571
572    color_quad = SolidColorDrawQuad::Create();
573    color_quad->SetNew(shared_quad_state, gfx::Rect(10, 10, 10, 10), 4u, false);
574    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
575
576    delegated_renderer_layer->SetFrameDataForRenderPasses(
577        &delegated_render_passes);
578
579    // The RenderPasses should be taken by the layer.
580    EXPECT_EQ(0u, delegated_render_passes.size());
581
582    root_layer_ = root_layer.get();
583    delegated_renderer_layer_ = delegated_renderer_layer.get();
584
585    root_layer->AddChild(delegated_renderer_layer.PassAs<LayerImpl>());
586    host_impl_->active_tree()->SetRootLayer(root_layer.Pass());
587  }
588
589  void VerifyRenderPasses(
590      const LayerTreeHostImpl::FrameData& frame,
591      size_t num_render_passes,
592      const SharedQuadState** root_delegated_shared_quad_state,
593      const SharedQuadState** contrib_delegated_shared_quad_state) {
594    ASSERT_EQ(num_render_passes, frame.render_passes.size());
595    // The contributing render pass in the DelegatedRendererLayer.
596    EXPECT_EQ(2, frame.render_passes[0]->id.layer_id);
597    EXPECT_EQ(1, frame.render_passes[0]->id.index);
598    // The root render pass.
599    EXPECT_EQ(1, frame.render_passes.back()->id.layer_id);
600    EXPECT_EQ(0, frame.render_passes.back()->id.index);
601
602    const QuadList& contrib_delegated_quad_list =
603        frame.render_passes[0]->quad_list;
604    ASSERT_EQ(2u, contrib_delegated_quad_list.size());
605
606    const QuadList& root_delegated_quad_list =
607        frame.render_passes[1]->quad_list;
608    ASSERT_EQ(5u, root_delegated_quad_list.size());
609
610    // All quads in a render pass should share the same state.
611    *contrib_delegated_shared_quad_state =
612        contrib_delegated_quad_list[0]->shared_quad_state;
613    EXPECT_EQ(*contrib_delegated_shared_quad_state,
614              contrib_delegated_quad_list[1]->shared_quad_state);
615
616    *root_delegated_shared_quad_state =
617        root_delegated_quad_list[0]->shared_quad_state;
618    EXPECT_EQ(*root_delegated_shared_quad_state,
619              root_delegated_quad_list[1]->shared_quad_state);
620    EXPECT_EQ(*root_delegated_shared_quad_state,
621              root_delegated_quad_list[2]->shared_quad_state);
622    EXPECT_EQ(*root_delegated_shared_quad_state,
623              root_delegated_quad_list[3]->shared_quad_state);
624    EXPECT_EQ(*root_delegated_shared_quad_state,
625              root_delegated_quad_list[4]->shared_quad_state);
626
627    EXPECT_NE(*contrib_delegated_shared_quad_state,
628              *root_delegated_shared_quad_state);
629  }
630
631 protected:
632  LayerImpl* root_layer_;
633  DelegatedRendererLayerImpl* delegated_renderer_layer_;
634  bool root_delegated_render_pass_is_clipped_;
635};
636
637TEST_F(DelegatedRendererLayerImplTestTransform, QuadsUnclipped_NoSurface) {
638  root_delegated_render_pass_is_clipped_ = false;
639  SetUpTest();
640
641  LayerTreeHostImpl::FrameData frame;
642  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
643
644  const SharedQuadState* root_delegated_shared_quad_state = NULL;
645  const SharedQuadState* contrib_delegated_shared_quad_state = NULL;
646  VerifyRenderPasses(
647      frame,
648      2,
649      &root_delegated_shared_quad_state,
650      &contrib_delegated_shared_quad_state);
651
652  // When the quads don't have a clip of their own, the clip rect is set to
653  // the drawable_content_rect of the delegated renderer layer.
654  EXPECT_EQ(gfx::Rect(21, 21, 60, 60).ToString(),
655            root_delegated_shared_quad_state->clip_rect.ToString());
656
657  // Even though the quads in the root pass have no clip of their own, they
658  // inherit the clip rect from the delegated renderer layer if it does not
659  // own a surface.
660  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
661
662  gfx::Transform expected;
663  // This is the transform from the layer's space to its target.
664  // The position (20) - the width / scale (30 / 2) = 20 - 15 = 5
665  expected.Translate(5.0, 5.0);
666  expected.Scale(2.0, 2.0);
667  expected.Translate(8.0, 8.0);
668  // The frame has size 50x50 but the layer's bounds are 30x30.
669  expected.Scale(30.0 / 50.0, 30.0 / 50.0);
670  // This is the transform within the source frame.
671  expected.Scale(1.5, 1.5);
672  expected.Translate(7.0, 7.0);
673  EXPECT_TRANSFORMATION_MATRIX_EQ(
674      expected, root_delegated_shared_quad_state->content_to_target_transform);
675
676  // The contributing render pass should not be transformed from its input.
677  EXPECT_EQ(gfx::Rect(21, 21, 3, 3).ToString(),
678            contrib_delegated_shared_quad_state->clip_rect.ToString());
679  EXPECT_FALSE(contrib_delegated_shared_quad_state->is_clipped);
680  expected.MakeIdentity();
681  expected.Scale(0.8, 0.8);
682  expected.Translate(9.0, 9.0);
683  EXPECT_TRANSFORMATION_MATRIX_EQ(
684      expected,
685      contrib_delegated_shared_quad_state->content_to_target_transform);
686
687  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
688  host_impl_->DidDrawAllLayers(frame);
689}
690
691TEST_F(DelegatedRendererLayerImplTestTransform, QuadsClipped_NoSurface) {
692  root_delegated_render_pass_is_clipped_ = true;
693  SetUpTest();
694
695  LayerTreeHostImpl::FrameData frame;
696  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
697
698  const SharedQuadState* root_delegated_shared_quad_state = NULL;
699  const SharedQuadState* contrib_delegated_shared_quad_state = NULL;
700  VerifyRenderPasses(
701      frame,
702      2,
703      &root_delegated_shared_quad_state,
704      &contrib_delegated_shared_quad_state);
705
706  // Since the quads have a clip_rect it should be modified by delegated
707  // renderer layer's draw_transform.
708  // The position of the resulting clip_rect is:
709  // (clip rect position (10) * scale to layer (30/50) + translate (8)) *
710  //     layer scale (2) + layer position (20) = 48
711  // But the layer is centered, so: 48 - (width / 2) = 48 - 30 / 2 = 33
712  //
713  // The size is 35x35 scaled to fit inside the layer's bounds at 30x30 from
714  // a frame at 50x50: 35 * 2 (layer's scale) * 30 / 50 = 42.
715  EXPECT_EQ(gfx::Rect(33, 33, 42, 42).ToString(),
716            root_delegated_shared_quad_state->clip_rect.ToString());
717
718  // The quads had a clip and it should be preserved.
719  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
720
721  gfx::Transform expected;
722  // This is the transform from the layer's space to its target.
723  // The position (20) - the width / scale (30 / 2) = 20 - 15 = 5
724  expected.Translate(5.0, 5.0);
725  expected.Scale(2.0, 2.0);
726  expected.Translate(8.0, 8.0);
727  // The frame has size 50x50 but the layer's bounds are 30x30.
728  expected.Scale(30.0 / 50.0, 30.0 / 50.0);
729  // This is the transform within the source frame.
730  expected.Scale(1.5, 1.5);
731  expected.Translate(7.0, 7.0);
732  EXPECT_TRANSFORMATION_MATRIX_EQ(
733      expected, root_delegated_shared_quad_state->content_to_target_transform);
734
735  // The contributing render pass should not be transformed from its input.
736  EXPECT_EQ(gfx::Rect(21, 21, 3, 3).ToString(),
737            contrib_delegated_shared_quad_state->clip_rect.ToString());
738  EXPECT_FALSE(contrib_delegated_shared_quad_state->is_clipped);
739  expected.MakeIdentity();
740  expected.Scale(0.8, 0.8);
741  expected.Translate(9.0, 9.0);
742  EXPECT_TRANSFORMATION_MATRIX_EQ(
743      expected,
744      contrib_delegated_shared_quad_state->content_to_target_transform);
745
746  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
747  host_impl_->DidDrawAllLayers(frame);
748}
749
750TEST_F(DelegatedRendererLayerImplTestTransform, QuadsUnclipped_Surface) {
751  root_delegated_render_pass_is_clipped_ = false;
752  SetUpTest();
753
754  delegated_renderer_layer_->SetForceRenderSurface(true);
755
756  LayerTreeHostImpl::FrameData frame;
757  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
758
759  const SharedQuadState* root_delegated_shared_quad_state = NULL;
760  const SharedQuadState* contrib_delegated_shared_quad_state = NULL;
761  VerifyRenderPasses(
762      frame,
763      3,
764      &root_delegated_shared_quad_state,
765      &contrib_delegated_shared_quad_state);
766
767  // When the layer owns a surface, then its position and translation are not
768  // a part of its draw transform.
769  // The position of the resulting clip_rect is:
770  // (clip rect position (10) * scale to layer (30/50)) * layer scale (2) = 12
771  // The size is 35x35 scaled to fit inside the layer's bounds at 30x30 from
772  // a frame at 50x50: 35 * 2 (layer's scale) * 30 / 50 = 42.
773  EXPECT_EQ(gfx::Rect(12, 12, 42, 42).ToString(),
774            root_delegated_shared_quad_state->clip_rect.ToString());
775
776  // Since the layer owns a surface it doesn't need to clip its quads, so
777  // unclipped quads remain unclipped.
778  EXPECT_FALSE(root_delegated_shared_quad_state->is_clipped);
779
780  gfx::Transform expected;
781  expected.Scale(2.0, 2.0);
782  // The frame has size 50x50 but the layer's bounds are 30x30.
783  expected.Scale(30.0 / 50.0, 30.0 / 50.0);
784  // This is the transform within the source frame.
785  expected.Scale(1.5, 1.5);
786  expected.Translate(7.0, 7.0);
787  EXPECT_TRANSFORMATION_MATRIX_EQ(
788      expected, root_delegated_shared_quad_state->content_to_target_transform);
789
790  // The contributing render pass should not be transformed from its input.
791  EXPECT_EQ(gfx::Rect(21, 21, 3, 3).ToString(),
792            contrib_delegated_shared_quad_state->clip_rect.ToString());
793  EXPECT_FALSE(contrib_delegated_shared_quad_state->is_clipped);
794  expected.MakeIdentity();
795  expected.Scale(0.8, 0.8);
796  expected.Translate(9.0, 9.0);
797  EXPECT_TRANSFORMATION_MATRIX_EQ(
798      expected,
799      contrib_delegated_shared_quad_state->content_to_target_transform);
800
801  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
802  host_impl_->DidDrawAllLayers(frame);
803}
804
805TEST_F(DelegatedRendererLayerImplTestTransform, QuadsClipped_Surface) {
806  root_delegated_render_pass_is_clipped_ = true;
807  SetUpTest();
808
809  delegated_renderer_layer_->SetForceRenderSurface(true);
810
811  LayerTreeHostImpl::FrameData frame;
812  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
813
814  const SharedQuadState* root_delegated_shared_quad_state = NULL;
815  const SharedQuadState* contrib_delegated_shared_quad_state = NULL;
816  VerifyRenderPasses(
817      frame,
818      3,
819      &root_delegated_shared_quad_state,
820      &contrib_delegated_shared_quad_state);
821
822  // When the layer owns a surface, then its position and translation are not
823  // a part of its draw transform.
824  // The position of the resulting clip_rect is:
825  // (clip rect position (10) * scale to layer (30/50)) * layer scale (2) = 12
826  // The size is 35x35 scaled to fit inside the layer's bounds at 30x30 from
827  // a frame at 50x50: 35 * 2 (layer's scale) * 30 / 50 = 42.
828  EXPECT_EQ(gfx::Rect(12, 12, 42, 42).ToString(),
829            root_delegated_shared_quad_state->clip_rect.ToString());
830
831  // The quads had a clip and it should be preserved.
832  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
833
834  gfx::Transform expected;
835  expected.Scale(2.0, 2.0);
836  // The frame has size 50x50 but the layer's bounds are 30x30.
837  expected.Scale(30.0 / 50.0, 30.0 / 50.0);
838  // This is the transform within the source frame.
839  expected.Scale(1.5, 1.5);
840  expected.Translate(7.0, 7.0);
841  EXPECT_TRANSFORMATION_MATRIX_EQ(
842      expected, root_delegated_shared_quad_state->content_to_target_transform);
843
844  // The contributing render pass should not be transformed from its input.
845  EXPECT_EQ(gfx::Rect(21, 21, 3, 3).ToString(),
846            contrib_delegated_shared_quad_state->clip_rect.ToString());
847  EXPECT_FALSE(contrib_delegated_shared_quad_state->is_clipped);
848  expected.MakeIdentity();
849  expected.Scale(0.8, 0.8);
850  expected.Translate(9.0, 9.0);
851  EXPECT_TRANSFORMATION_MATRIX_EQ(
852      expected,
853      contrib_delegated_shared_quad_state->content_to_target_transform);
854
855  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
856  host_impl_->DidDrawAllLayers(frame);
857}
858
859class DelegatedRendererLayerImplTestClip
860    : public DelegatedRendererLayerImplTest {
861 public:
862  void SetUpTest() {
863    scoped_ptr<LayerImpl> root_layer =
864        LayerImpl::Create(host_impl_->active_tree(), 1);
865    scoped_ptr<FakeDelegatedRendererLayerImpl> delegated_renderer_layer =
866        FakeDelegatedRendererLayerImpl::Create(host_impl_->active_tree(), 2);
867    scoped_ptr<LayerImpl> clip_layer =
868        LayerImpl::Create(host_impl_->active_tree(), 3);
869    scoped_ptr<LayerImpl> origin_layer =
870        LayerImpl::Create(host_impl_->active_tree(), 4);
871
872    host_impl_->SetViewportSize(gfx::Size(100, 100));
873    root_layer->SetBounds(gfx::Size(100, 100));
874
875    delegated_renderer_layer->SetPosition(gfx::Point(20, 20));
876    delegated_renderer_layer->SetBounds(gfx::Size(50, 50));
877    delegated_renderer_layer->SetContentBounds(gfx::Size(50, 50));
878    delegated_renderer_layer->SetDrawsContent(true);
879
880    ScopedPtrVector<RenderPass> delegated_render_passes;
881
882    gfx::Size child_pass_content_bounds(7, 7);
883    gfx::Rect child_pass_rect(20, 20, 7, 7);
884    gfx::Transform child_pass_transform;
885    gfx::Rect child_pass_clip_rect(21, 21, 3, 3);
886    bool child_pass_clipped = false;
887
888    {
889      TestRenderPass* pass = AddRenderPass(
890          &delegated_render_passes,
891          RenderPass::Id(10, 7),
892          child_pass_rect,
893          gfx::Transform());
894      MockQuadCuller quad_sink(&pass->quad_list, &pass->shared_quad_state_list);
895      AppendQuadsData data(pass->id);
896      SharedQuadState* shared_quad_state =
897          quad_sink.UseSharedQuadState(SharedQuadState::Create());
898      shared_quad_state->SetAll(
899          child_pass_transform,
900          child_pass_content_bounds,
901          child_pass_rect,
902          child_pass_clip_rect,
903          child_pass_clipped,
904          1.f);
905
906      scoped_ptr<SolidColorDrawQuad> color_quad;
907      color_quad = SolidColorDrawQuad::Create();
908      color_quad->SetNew(shared_quad_state, gfx::Rect(20, 20, 3, 7), 1u, false);
909      quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
910
911      color_quad = SolidColorDrawQuad::Create();
912      color_quad->SetNew(shared_quad_state, gfx::Rect(23, 20, 4, 7), 1u, false);
913      quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
914    }
915
916    gfx::Size root_pass_content_bounds(50, 50);
917    gfx::Rect root_pass_rect(0, 0, 50, 50);
918    gfx::Transform root_pass_transform;
919    gfx::Rect root_pass_clip_rect(5, 5, 40, 40);
920    bool root_pass_clipped = root_delegated_render_pass_is_clipped_;
921
922    TestRenderPass* pass = AddRenderPass(
923        &delegated_render_passes,
924        RenderPass::Id(9, 6),
925        root_pass_rect,
926        gfx::Transform());
927    MockQuadCuller quad_sink(&pass->quad_list, &pass->shared_quad_state_list);
928    AppendQuadsData data(pass->id);
929    SharedQuadState* shared_quad_state =
930        quad_sink.UseSharedQuadState(SharedQuadState::Create());
931    shared_quad_state->SetAll(root_pass_transform,
932                              root_pass_content_bounds,
933                              root_pass_rect,
934                              root_pass_clip_rect,
935                              root_pass_clipped,
936                              1.f);
937
938    scoped_ptr<RenderPassDrawQuad> render_pass_quad =
939        RenderPassDrawQuad::Create();
940    render_pass_quad->SetNew(
941        shared_quad_state,
942        gfx::Rect(5, 5, 7, 7),  // rect
943        RenderPass::Id(10, 7),  // render_pass_id
944        false,  // is_replica
945        0,  // mask_resource_id
946        child_pass_rect,  // contents_changed_since_last_frame
947        gfx::RectF(),  // mask_uv_rect
948        WebKit::WebFilterOperations(),  // filters
949        skia::RefPtr<SkImageFilter>(),  // filter
950        WebKit::WebFilterOperations());  // background_filters
951    quad_sink.Append(render_pass_quad.PassAs<DrawQuad>(), &data);
952
953    scoped_ptr<SolidColorDrawQuad> color_quad;
954    color_quad = SolidColorDrawQuad::Create();
955    color_quad->SetNew(shared_quad_state, gfx::Rect(0, 0, 10, 10), 1u, false);
956    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
957
958    color_quad = SolidColorDrawQuad::Create();
959    color_quad->SetNew(shared_quad_state, gfx::Rect(0, 10, 10, 10), 2u, false);
960    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
961
962    color_quad = SolidColorDrawQuad::Create();
963    color_quad->SetNew(shared_quad_state, gfx::Rect(10, 0, 10, 10), 3u, false);
964    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
965
966    color_quad = SolidColorDrawQuad::Create();
967    color_quad->SetNew(shared_quad_state, gfx::Rect(10, 10, 10, 10), 4u, false);
968    quad_sink.Append(color_quad.PassAs<DrawQuad>(), &data);
969
970    delegated_renderer_layer->SetFrameDataForRenderPasses(
971        &delegated_render_passes);
972
973    // The RenderPasses should be taken by the layer.
974    EXPECT_EQ(0u, delegated_render_passes.size());
975
976    root_layer_ = root_layer.get();
977    delegated_renderer_layer_ = delegated_renderer_layer.get();
978
979    if (clip_delegated_renderer_layer_) {
980      gfx::Rect clip_rect(21, 27, 23, 21);
981
982      clip_layer->SetPosition(clip_rect.origin());
983      clip_layer->SetBounds(clip_rect.size());
984      clip_layer->SetContentBounds(clip_rect.size());
985      clip_layer->SetMasksToBounds(true);
986
987      origin_layer->SetPosition(
988          gfx::PointAtOffsetFromOrigin(-clip_rect.OffsetFromOrigin()));
989
990      origin_layer->AddChild(delegated_renderer_layer.PassAs<LayerImpl>());
991      clip_layer->AddChild(origin_layer.Pass());
992      root_layer->AddChild(clip_layer.Pass());
993    } else {
994      root_layer->AddChild(delegated_renderer_layer.PassAs<LayerImpl>());
995    }
996
997    host_impl_->active_tree()->SetRootLayer(root_layer.Pass());
998  }
999
1000 protected:
1001  LayerImpl* root_layer_;
1002  DelegatedRendererLayerImpl* delegated_renderer_layer_;
1003  bool root_delegated_render_pass_is_clipped_;
1004  bool clip_delegated_renderer_layer_;
1005};
1006
1007TEST_F(DelegatedRendererLayerImplTestClip,
1008       QuadsUnclipped_LayerUnclipped_NoSurface) {
1009  root_delegated_render_pass_is_clipped_ = false;
1010  clip_delegated_renderer_layer_ = false;
1011  SetUpTest();
1012
1013  LayerTreeHostImpl::FrameData frame;
1014  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1015
1016  ASSERT_EQ(2u, frame.render_passes.size());
1017  const QuadList& contrib_delegated_quad_list =
1018      frame.render_passes[0]->quad_list;
1019  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1020  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1021  ASSERT_EQ(5u, root_delegated_quad_list.size());
1022  const SharedQuadState* root_delegated_shared_quad_state =
1023      root_delegated_quad_list[0]->shared_quad_state;
1024
1025  // When the quads don't have a clip of their own, the clip rect is set to
1026  // the drawable_content_rect of the delegated renderer layer.
1027  EXPECT_EQ(gfx::Rect(20, 20, 50, 50).ToString(),
1028            root_delegated_shared_quad_state->clip_rect.ToString());
1029  // Quads are clipped to the delegated renderer layer.
1030  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1031
1032  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1033  host_impl_->DidDrawAllLayers(frame);
1034}
1035
1036TEST_F(DelegatedRendererLayerImplTestClip,
1037       QuadsClipped_LayerUnclipped_NoSurface) {
1038  root_delegated_render_pass_is_clipped_ = true;
1039  clip_delegated_renderer_layer_ = false;
1040  SetUpTest();
1041
1042  LayerTreeHostImpl::FrameData frame;
1043  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1044
1045  ASSERT_EQ(2u, frame.render_passes.size());
1046  const QuadList& contrib_delegated_quad_list =
1047      frame.render_passes[0]->quad_list;
1048  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1049  const QuadList& root_delegated_quad_list =
1050      frame.render_passes[1]->quad_list;
1051  ASSERT_EQ(5u, root_delegated_quad_list.size());
1052  const SharedQuadState* root_delegated_shared_quad_state =
1053      root_delegated_quad_list[0]->shared_quad_state;
1054
1055  // When the quads have a clip of their own, it is used.
1056  EXPECT_EQ(gfx::Rect(25, 25, 40, 40).ToString(),
1057            root_delegated_shared_quad_state->clip_rect.ToString());
1058  // Quads came with a clip rect.
1059  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1060
1061  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1062  host_impl_->DidDrawAllLayers(frame);
1063}
1064
1065TEST_F(DelegatedRendererLayerImplTestClip,
1066       QuadsUnclipped_LayerClipped_NoSurface) {
1067  root_delegated_render_pass_is_clipped_ = false;
1068  clip_delegated_renderer_layer_ = true;
1069  SetUpTest();
1070
1071  LayerTreeHostImpl::FrameData frame;
1072  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1073
1074  ASSERT_EQ(2u, frame.render_passes.size());
1075  const QuadList& contrib_delegated_quad_list =
1076      frame.render_passes[0]->quad_list;
1077  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1078  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1079  ASSERT_EQ(5u, root_delegated_quad_list.size());
1080  const SharedQuadState* root_delegated_shared_quad_state =
1081      root_delegated_quad_list[0]->shared_quad_state;
1082
1083  // When the quads don't have a clip of their own, the clip rect is set to
1084  // the drawable_content_rect of the delegated renderer layer. When the layer
1085  // is clipped, that should be seen in the quads' clip_rect.
1086  EXPECT_EQ(gfx::Rect(21, 27, 23, 21).ToString(),
1087            root_delegated_shared_quad_state->clip_rect.ToString());
1088  // Quads are clipped to the delegated renderer layer.
1089  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1090
1091  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1092  host_impl_->DidDrawAllLayers(frame);
1093}
1094
1095TEST_F(DelegatedRendererLayerImplTestClip,
1096       QuadsClipped_LayerClipped_NoSurface) {
1097  root_delegated_render_pass_is_clipped_ = true;
1098  clip_delegated_renderer_layer_ = true;
1099  SetUpTest();
1100
1101  LayerTreeHostImpl::FrameData frame;
1102  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1103
1104  ASSERT_EQ(2u, frame.render_passes.size());
1105  const QuadList& contrib_delegated_quad_list =
1106      frame.render_passes[0]->quad_list;
1107  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1108  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1109  ASSERT_EQ(5u, root_delegated_quad_list.size());
1110  const SharedQuadState* root_delegated_shared_quad_state =
1111      root_delegated_quad_list[0]->shared_quad_state;
1112
1113  // When the quads have a clip of their own, it is used, but it is
1114  // combined with the clip rect of the delegated renderer layer.
1115  EXPECT_EQ(gfx::Rect(25, 27, 19, 21).ToString(),
1116            root_delegated_shared_quad_state->clip_rect.ToString());
1117  // Quads came with a clip rect.
1118  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1119
1120  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1121  host_impl_->DidDrawAllLayers(frame);
1122}
1123
1124TEST_F(DelegatedRendererLayerImplTestClip,
1125       QuadsUnclipped_LayerUnclipped_Surface) {
1126  root_delegated_render_pass_is_clipped_ = false;
1127  clip_delegated_renderer_layer_ = false;
1128  SetUpTest();
1129
1130  delegated_renderer_layer_->SetForceRenderSurface(true);
1131
1132  LayerTreeHostImpl::FrameData frame;
1133  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1134
1135  ASSERT_EQ(3u, frame.render_passes.size());
1136  const QuadList& contrib_delegated_quad_list =
1137      frame.render_passes[0]->quad_list;
1138  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1139  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1140  ASSERT_EQ(5u, root_delegated_quad_list.size());
1141  const SharedQuadState* root_delegated_shared_quad_state =
1142      root_delegated_quad_list[0]->shared_quad_state;
1143
1144  // When the layer owns a surface, the quads don't need to be clipped
1145  // further than they already specify. If they aren't clipped, then their
1146  // clip rect is ignored, and they are not set as clipped.
1147  EXPECT_FALSE(root_delegated_shared_quad_state->is_clipped);
1148
1149  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1150  host_impl_->DidDrawAllLayers(frame);
1151}
1152
1153TEST_F(DelegatedRendererLayerImplTestClip,
1154       QuadsClipped_LayerUnclipped_Surface) {
1155  root_delegated_render_pass_is_clipped_ = true;
1156  clip_delegated_renderer_layer_ = false;
1157  SetUpTest();
1158
1159  delegated_renderer_layer_->SetForceRenderSurface(true);
1160
1161  LayerTreeHostImpl::FrameData frame;
1162  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1163
1164  ASSERT_EQ(3u, frame.render_passes.size());
1165  const QuadList& contrib_delegated_quad_list =
1166      frame.render_passes[0]->quad_list;
1167  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1168  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1169  ASSERT_EQ(5u, root_delegated_quad_list.size());
1170  const SharedQuadState* root_delegated_shared_quad_state =
1171      root_delegated_quad_list[0]->shared_quad_state;
1172
1173  // When the quads have a clip of their own, it is used.
1174  EXPECT_EQ(gfx::Rect(5, 5, 40, 40).ToString(),
1175            root_delegated_shared_quad_state->clip_rect.ToString());
1176  // Quads came with a clip rect.
1177  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1178
1179  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1180  host_impl_->DidDrawAllLayers(frame);
1181}
1182
1183TEST_F(DelegatedRendererLayerImplTestClip,
1184       QuadsUnclipped_LayerClipped_Surface) {
1185  root_delegated_render_pass_is_clipped_ = false;
1186  clip_delegated_renderer_layer_ = true;
1187  SetUpTest();
1188
1189  delegated_renderer_layer_->SetForceRenderSurface(true);
1190
1191  LayerTreeHostImpl::FrameData frame;
1192  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1193
1194  ASSERT_EQ(3u, frame.render_passes.size());
1195  const QuadList& contrib_delegated_quad_list =
1196      frame.render_passes[0]->quad_list;
1197  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1198  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1199  ASSERT_EQ(5u, root_delegated_quad_list.size());
1200  const SharedQuadState* root_delegated_shared_quad_state =
1201      root_delegated_quad_list[0]->shared_quad_state;
1202
1203  // When the layer owns a surface, the quads don't need to be clipped
1204  // further than they already specify. If they aren't clipped, then their
1205  // clip rect is ignored, and they are not set as clipped.
1206  EXPECT_FALSE(root_delegated_shared_quad_state->is_clipped);
1207
1208  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1209  host_impl_->DidDrawAllLayers(frame);
1210}
1211
1212TEST_F(DelegatedRendererLayerImplTestClip, QuadsClipped_LayerClipped_Surface) {
1213  root_delegated_render_pass_is_clipped_ = true;
1214  clip_delegated_renderer_layer_ = true;
1215  SetUpTest();
1216
1217  delegated_renderer_layer_->SetForceRenderSurface(true);
1218
1219  LayerTreeHostImpl::FrameData frame;
1220  EXPECT_TRUE(host_impl_->PrepareToDraw(&frame, gfx::Rect()));
1221
1222  ASSERT_EQ(3u, frame.render_passes.size());
1223  const QuadList& contrib_delegated_quad_list =
1224      frame.render_passes[0]->quad_list;
1225  ASSERT_EQ(2u, contrib_delegated_quad_list.size());
1226  const QuadList& root_delegated_quad_list = frame.render_passes[1]->quad_list;
1227  ASSERT_EQ(5u, root_delegated_quad_list.size());
1228  const SharedQuadState* root_delegated_shared_quad_state =
1229      root_delegated_quad_list[0]->shared_quad_state;
1230
1231  // When the quads have a clip of their own, it is used, but it is
1232  // combined with the clip rect of the delegated renderer layer. If the
1233  // layer owns a surface, then it does not have a clip rect of its own.
1234  EXPECT_EQ(gfx::Rect(5, 5, 40, 40).ToString(),
1235            root_delegated_shared_quad_state->clip_rect.ToString());
1236  // Quads came with a clip rect.
1237  EXPECT_TRUE(root_delegated_shared_quad_state->is_clipped);
1238
1239  host_impl_->DrawLayers(&frame, base::TimeTicks::Now());
1240  host_impl_->DidDrawAllLayers(frame);
1241}
1242
1243}  // namespace
1244}  // namespace cc
1245