layer_tree_test.h revision cedac228d2dd51db4b79ea1e72c7f249408ee061
1// Copyright 2011 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#ifndef CC_TEST_LAYER_TREE_TEST_H_
6#define CC_TEST_LAYER_TREE_TEST_H_
7
8#include "base/memory/ref_counted.h"
9#include "base/threading/thread.h"
10#include "cc/animation/animation_delegate.h"
11#include "cc/trees/layer_tree_host.h"
12#include "cc/trees/layer_tree_host_impl.h"
13#include "testing/gtest/include/gtest/gtest.h"
14
15namespace Webkit {
16class WebGraphicsContext3D;
17}
18
19namespace cc {
20class FakeLayerTreeHostClient;
21class FakeOutputSurface;
22class LayerImpl;
23class LayerTreeHost;
24class LayerTreeHostClient;
25class LayerTreeHostImpl;
26class TestContextProvider;
27class TestWebGraphicsContext3D;
28
29// Used by test stubs to notify the test when something interesting happens.
30class TestHooks : public AnimationDelegate {
31 public:
32  TestHooks();
33  virtual ~TestHooks();
34
35  void ReadSettings(const LayerTreeSettings& settings);
36
37  virtual void WillBeginImplFrameOnThread(LayerTreeHostImpl* host_impl,
38                                          const BeginFrameArgs& args) {}
39  virtual void BeginMainFrameAbortedOnThread(LayerTreeHostImpl* host_impl,
40                                             bool did_handle) {}
41  virtual void BeginCommitOnThread(LayerTreeHostImpl* host_impl) {}
42  virtual void CommitCompleteOnThread(LayerTreeHostImpl* host_impl) {}
43  virtual void WillActivateTreeOnThread(LayerTreeHostImpl* host_impl) {}
44  virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) {}
45  virtual void InitializedRendererOnThread(LayerTreeHostImpl* host_impl,
46                                           bool success) {}
47  virtual DrawResult PrepareToDrawOnThread(
48      LayerTreeHostImpl* host_impl,
49      LayerTreeHostImpl::FrameData* frame_data,
50      DrawResult draw_result);
51  virtual void DrawLayersOnThread(LayerTreeHostImpl* host_impl) {}
52  virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, bool result) {}
53  virtual void SwapBuffersCompleteOnThread(LayerTreeHostImpl* host_impl) {}
54  virtual void UpdateVisibleTilesOnThread(LayerTreeHostImpl* host_impl) {}
55  virtual void AnimateLayers(LayerTreeHostImpl* host_impl,
56                             base::TimeTicks monotonic_time) {}
57  virtual void UpdateAnimationState(LayerTreeHostImpl* host_impl,
58                                    bool has_unfinished_animation) {}
59  virtual void WillAnimateLayers(LayerTreeHostImpl* host_impl,
60                                 base::TimeTicks monotonic_time) {}
61  virtual void ApplyScrollAndScale(const gfx::Vector2d& scroll_delta,
62                                   float scale) {}
63  virtual void Animate(base::TimeTicks monotonic_time) {}
64  virtual void WillBeginMainFrame() {}
65  virtual void DidBeginMainFrame() {}
66  virtual void Layout() {}
67  virtual void DidInitializeOutputSurface() {}
68  virtual void DidFailToInitializeOutputSurface() {}
69  virtual void DidAddAnimation() {}
70  virtual void WillCommit() {}
71  virtual void DidCommit() {}
72  virtual void DidCommitAndDrawFrame() {}
73  virtual void DidCompleteSwapBuffers() {}
74  virtual void ScheduleComposite() {}
75  virtual void ScheduleAnimation() {}
76  virtual void DidDeferCommit() {}
77  virtual void DidSetVisibleOnImplTree(LayerTreeHostImpl* host_impl,
78                                       bool visible) {}
79  virtual base::TimeDelta LowFrequencyAnimationInterval() const;
80
81  // Hooks for SchedulerClient.
82  virtual void ScheduledActionBeginOutputSurfaceCreation() {}
83  virtual void ScheduledActionSendBeginMainFrame() {}
84  virtual void ScheduledActionCommit() {}
85  virtual void ScheduledActionDrawAndSwapIfPossible() {}
86
87  // Implementation of AnimationDelegate:
88  virtual void NotifyAnimationStarted(base::TimeTicks monotonic_time,
89                                      Animation::TargetProperty target_property)
90      OVERRIDE {}
91  virtual void NotifyAnimationFinished(
92      base::TimeTicks monotonic_time,
93      Animation::TargetProperty target_property) OVERRIDE {}
94
95  virtual scoped_ptr<OutputSurface> CreateOutputSurface(bool fallback) = 0;
96};
97
98class BeginTask;
99class LayerTreeHostClientForTesting;
100class TimeoutTask;
101
102// The LayerTreeTests runs with the main loop running. It instantiates a single
103// LayerTreeHostForTesting and associated LayerTreeHostImplForTesting and
104// LayerTreeHostClientForTesting.
105//
106// BeginTest() is called once the main message loop is running and the layer
107// tree host is initialized.
108//
109// Key stages of the drawing loop, e.g. drawing or commiting, redirect to
110// LayerTreeTest methods of similar names. To track the commit process, override
111// these functions.
112//
113// The test continues until someone calls EndTest. EndTest can be called on any
114// thread, but be aware that ending the test is an asynchronous process.
115class LayerTreeTest : public testing::Test, public TestHooks {
116 public:
117  virtual ~LayerTreeTest();
118
119  virtual void EndTest();
120  void EndTestAfterDelay(int delay_milliseconds);
121
122  void PostAddAnimationToMainThread(Layer* layer_to_receive_animation);
123  void PostAddInstantAnimationToMainThread(Layer* layer_to_receive_animation);
124  void PostAddLongAnimationToMainThread(Layer* layer_to_receive_animation);
125  void PostSetNeedsCommitToMainThread();
126  void PostSetNeedsUpdateLayersToMainThread();
127  void PostSetNeedsRedrawToMainThread();
128  void PostSetNeedsRedrawRectToMainThread(const gfx::Rect& damage_rect);
129  void PostSetVisibleToMainThread(bool visible);
130  void PostSetNextCommitForcesRedrawToMainThread();
131
132  void DoBeginTest();
133  void Timeout();
134
135 protected:
136  LayerTreeTest();
137
138  virtual void InitializeSettings(LayerTreeSettings* settings) {}
139
140  virtual void ScheduleComposite() OVERRIDE;
141
142  void RealEndTest();
143
144  virtual void DispatchAddAnimation(Layer* layer_to_receive_animation,
145                                    double animation_duration);
146  void DispatchSetNeedsCommit();
147  void DispatchSetNeedsUpdateLayers();
148  void DispatchSetNeedsRedraw();
149  void DispatchSetNeedsRedrawRect(const gfx::Rect& damage_rect);
150  void DispatchSetVisible(bool visible);
151  void DispatchSetNextCommitForcesRedraw();
152  void DispatchComposite();
153  void DispatchDidAddAnimation();
154
155  virtual void AfterTest() = 0;
156  virtual void WillBeginTest();
157  virtual void BeginTest() = 0;
158  virtual void SetupTree();
159
160  virtual void RunTest(bool threaded,
161                       bool delegating_renderer,
162                       bool impl_side_painting);
163  virtual void RunTestWithImplSidePainting();
164
165  bool HasImplThread() { return proxy() ? proxy()->HasImplThread() : false; }
166  base::SingleThreadTaskRunner* ImplThreadTaskRunner() {
167    DCHECK(proxy());
168    return proxy()->ImplThreadTaskRunner() ? proxy()->ImplThreadTaskRunner()
169                                           : main_task_runner_.get();
170  }
171  base::SingleThreadTaskRunner* MainThreadTaskRunner() {
172    return main_task_runner_.get();
173  }
174  Proxy* proxy() const {
175    return layer_tree_host_ ? layer_tree_host_->proxy() : NULL;
176  }
177
178  bool TestEnded() const { return ended_; }
179
180  LayerTreeHost* layer_tree_host() { return layer_tree_host_.get(); }
181  bool delegating_renderer() const { return delegating_renderer_; }
182  FakeOutputSurface* output_surface() { return output_surface_; }
183  int LastCommittedSourceFrameNumber(LayerTreeHostImpl* impl) const;
184
185  void DestroyLayerTreeHost();
186
187  // Override this for pixel tests, where you need a real output surface.
188  virtual scoped_ptr<OutputSurface> CreateOutputSurface(bool fallback) OVERRIDE;
189  // Override this for unit tests, which should not produce pixel output.
190  virtual scoped_ptr<FakeOutputSurface> CreateFakeOutputSurface(bool fallback);
191
192  TestWebGraphicsContext3D* TestContext();
193
194
195 private:
196  LayerTreeSettings settings_;
197  scoped_ptr<LayerTreeHostClientForTesting> client_;
198  scoped_ptr<LayerTreeHost> layer_tree_host_;
199  FakeOutputSurface* output_surface_;
200
201  bool beginning_;
202  bool end_when_begin_returns_;
203  bool timed_out_;
204  bool scheduled_;
205  bool schedule_when_set_visible_true_;
206  bool started_;
207  bool ended_;
208  bool delegating_renderer_;
209
210  int timeout_seconds_;
211
212  scoped_refptr<base::SingleThreadTaskRunner> main_task_runner_;
213  scoped_ptr<base::Thread> impl_thread_;
214  base::CancelableClosure timeout_;
215  scoped_refptr<TestContextProvider> compositor_contexts_;
216  base::WeakPtr<LayerTreeTest> main_thread_weak_ptr_;
217  base::WeakPtrFactory<LayerTreeTest> weak_factory_;
218};
219
220}  // namespace cc
221
222#define SINGLE_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME) \
223  TEST_F(TEST_FIXTURE_NAME, RunSingleThread_DirectRenderer) {   \
224    RunTest(false, false, false);                               \
225  }                                                             \
226  class SingleThreadDirectNeedsSemicolon##TEST_FIXTURE_NAME {}
227
228#define SINGLE_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME) \
229  TEST_F(TEST_FIXTURE_NAME, RunSingleThread_DelegatingRenderer) {   \
230    RunTest(false, true, false);                                    \
231  }                                                                 \
232  class SingleThreadDelegatingNeedsSemicolon##TEST_FIXTURE_NAME {}
233
234#define SINGLE_THREAD_TEST_F(TEST_FIXTURE_NAME)            \
235  SINGLE_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME); \
236  SINGLE_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME)
237
238#define MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)        \
239  TEST_F(TEST_FIXTURE_NAME, RunMultiThread_DirectRenderer_MainThreadPaint) { \
240    RunTest(true, false, false);                                             \
241  }
242
243#define MULTI_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME)                 \
244  MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)                \
245      TEST_F(TEST_FIXTURE_NAME, RunMultiThread_DirectRenderer_ImplSidePaint) { \
246    RunTest(true, false, true);                                                \
247  }                                                                            \
248  class MultiThreadDirectNeedsSemicolon##TEST_FIXTURE_NAME {}
249
250#define MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME) \
251  TEST_F(TEST_FIXTURE_NAME,                                               \
252         RunMultiThread_DelegatingRenderer_MainThreadPaint) {             \
253    RunTest(true, true, false);                                           \
254  }
255
256#define MULTI_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME)          \
257  MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME) TEST_F( \
258      TEST_FIXTURE_NAME, RunMultiThread_DelegatingRenderer_ImplSidePaint) { \
259    RunTest(true, true, true);                                              \
260  }                                                                         \
261  class MultiThreadDelegatingNeedsSemicolon##TEST_FIXTURE_NAME {}
262
263#define MULTI_THREAD_NOIMPL_TEST_F(TEST_FIXTURE_NAME)            \
264  MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME); \
265  MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)
266
267#define MULTI_THREAD_TEST_F(TEST_FIXTURE_NAME)            \
268  MULTI_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME); \
269  MULTI_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME)
270
271#define SINGLE_AND_MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F( \
272    TEST_FIXTURE_NAME)                                         \
273  SINGLE_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME);     \
274  MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)
275
276#define SINGLE_AND_MULTI_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME) \
277  SINGLE_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME);                \
278  MULTI_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME)
279
280#define SINGLE_AND_MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F( \
281    TEST_FIXTURE_NAME)                                             \
282  SINGLE_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME);     \
283  MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)
284
285#define SINGLE_AND_MULTI_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME) \
286  SINGLE_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME);                \
287  MULTI_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME)
288
289#define SINGLE_AND_MULTI_THREAD_NOIMPL_TEST_F(TEST_FIXTURE_NAME)            \
290  SINGLE_AND_MULTI_THREAD_DIRECT_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME); \
291  SINGLE_AND_MULTI_THREAD_DELEGATING_RENDERER_NOIMPL_TEST_F(TEST_FIXTURE_NAME)
292
293#define SINGLE_AND_MULTI_THREAD_TEST_F(TEST_FIXTURE_NAME)            \
294  SINGLE_AND_MULTI_THREAD_DIRECT_RENDERER_TEST_F(TEST_FIXTURE_NAME); \
295  SINGLE_AND_MULTI_THREAD_DELEGATING_RENDERER_TEST_F(TEST_FIXTURE_NAME)
296
297#endif  // CC_TEST_LAYER_TREE_TEST_H_
298