Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / cc / trees / layer_tree_host_unittest_animation.cc
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/trees/layer_tree_host.h"
6
7 #include "cc/animation/animation_curve.h"
8 #include "cc/animation/layer_animation_controller.h"
9 #include "cc/animation/scroll_offset_animation_curve.h"
10 #include "cc/animation/timing_function.h"
11 #include "cc/layers/layer.h"
12 #include "cc/layers/layer_impl.h"
13 #include "cc/test/animation_test_common.h"
14 #include "cc/test/fake_content_layer.h"
15 #include "cc/test/fake_content_layer_client.h"
16 #include "cc/test/layer_tree_test.h"
17 #include "cc/trees/layer_tree_impl.h"
18
19 namespace cc {
20 namespace {
21
22 class LayerTreeHostAnimationTest : public LayerTreeTest {
23  public:
24   virtual void SetupTree() OVERRIDE {
25     LayerTreeTest::SetupTree();
26     layer_tree_host()->root_layer()->set_layer_animation_delegate(this);
27   }
28 };
29
30 // Makes sure that SetNeedsAnimate does not cause the CommitRequested() state to
31 // be set.
32 class LayerTreeHostAnimationTestSetNeedsAnimateShouldNotSetCommitRequested
33     : public LayerTreeHostAnimationTest {
34  public:
35   LayerTreeHostAnimationTestSetNeedsAnimateShouldNotSetCommitRequested()
36       : num_commits_(0) {}
37
38   virtual void BeginTest() OVERRIDE {
39     PostSetNeedsCommitToMainThread();
40   }
41
42   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
43     // We skip the first commit because its the commit that populates the
44     // impl thread with a tree. After the second commit, the test is done.
45     if (num_commits_ != 1)
46       return;
47
48     layer_tree_host()->SetNeedsAnimate();
49     // Right now, CommitRequested is going to be true, because during
50     // BeginFrame, we force CommitRequested to true to prevent requests from
51     // hitting the impl thread. But, when the next DidCommit happens, we should
52     // verify that CommitRequested has gone back to false.
53   }
54
55   virtual void DidCommit() OVERRIDE {
56     if (!num_commits_) {
57       EXPECT_FALSE(layer_tree_host()->CommitRequested());
58       layer_tree_host()->SetNeedsAnimate();
59       EXPECT_FALSE(layer_tree_host()->CommitRequested());
60     }
61
62     // Verifies that the SetNeedsAnimate we made in ::Animate did not
63     // trigger CommitRequested.
64     EXPECT_FALSE(layer_tree_host()->CommitRequested());
65     EndTest();
66     num_commits_++;
67   }
68
69   virtual void AfterTest() OVERRIDE {}
70
71  private:
72   int num_commits_;
73 };
74
75 MULTI_THREAD_TEST_F(
76     LayerTreeHostAnimationTestSetNeedsAnimateShouldNotSetCommitRequested);
77
78 // Trigger a frame with SetNeedsCommit. Then, inside the resulting animate
79 // callback, request another frame using SetNeedsAnimate. End the test when
80 // animate gets called yet-again, indicating that the proxy is correctly
81 // handling the case where SetNeedsAnimate() is called inside the BeginFrame
82 // flow.
83 class LayerTreeHostAnimationTestSetNeedsAnimateInsideAnimationCallback
84     : public LayerTreeHostAnimationTest {
85  public:
86   LayerTreeHostAnimationTestSetNeedsAnimateInsideAnimationCallback()
87       : num_begin_frames_(0) {}
88
89   virtual void BeginTest() OVERRIDE {
90     PostSetNeedsCommitToMainThread();
91   }
92
93   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
94     if (!num_begin_frames_) {
95       layer_tree_host()->SetNeedsAnimate();
96       num_begin_frames_++;
97       return;
98     }
99     EndTest();
100   }
101
102   virtual void AfterTest() OVERRIDE {}
103
104  private:
105   int num_begin_frames_;
106 };
107
108 MULTI_THREAD_TEST_F(
109     LayerTreeHostAnimationTestSetNeedsAnimateInsideAnimationCallback);
110
111 // Add a layer animation and confirm that
112 // LayerTreeHostImpl::updateAnimationState does get called and continues to
113 // get called.
114 class LayerTreeHostAnimationTestAddAnimation
115     : public LayerTreeHostAnimationTest {
116  public:
117   LayerTreeHostAnimationTestAddAnimation()
118       : num_begin_frames_(0), received_animation_started_notification_(false) {}
119
120   virtual void BeginTest() OVERRIDE {
121     PostAddInstantAnimationToMainThread(layer_tree_host()->root_layer());
122   }
123
124   virtual void UpdateAnimationState(
125       LayerTreeHostImpl* host_impl,
126       bool has_unfinished_animation) OVERRIDE {
127     if (!num_begin_frames_) {
128       // The animation had zero duration so LayerTreeHostImpl should no
129       // longer need to animate its layers.
130       EXPECT_FALSE(has_unfinished_animation);
131       num_begin_frames_++;
132       return;
133     }
134
135     if (received_animation_started_notification_) {
136       EXPECT_LT(base::TimeTicks(), start_time_);
137
138       LayerAnimationController* controller_impl =
139           host_impl->active_tree()->root_layer()->layer_animation_controller();
140       Animation* animation_impl =
141           controller_impl->GetAnimation(Animation::Opacity);
142       if (animation_impl)
143         controller_impl->RemoveAnimation(animation_impl->id());
144
145       EndTest();
146     }
147   }
148
149   virtual void NotifyAnimationStarted(
150       base::TimeTicks monotonic_time,
151       Animation::TargetProperty target_property) OVERRIDE {
152     received_animation_started_notification_ = true;
153     start_time_ = monotonic_time;
154     if (num_begin_frames_) {
155       EXPECT_LT(base::TimeTicks(), start_time_);
156
157       LayerAnimationController* controller =
158           layer_tree_host()->root_layer()->layer_animation_controller();
159       Animation* animation =
160           controller->GetAnimation(Animation::Opacity);
161       if (animation)
162         controller->RemoveAnimation(animation->id());
163
164       EndTest();
165     }
166   }
167
168   virtual void AfterTest() OVERRIDE {}
169
170  private:
171   int num_begin_frames_;
172   bool received_animation_started_notification_;
173   base::TimeTicks start_time_;
174 };
175
176 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestAddAnimation);
177
178 // Add a layer animation to a layer, but continually fail to draw. Confirm that
179 // after a while, we do eventually force a draw.
180 class LayerTreeHostAnimationTestCheckerboardDoesNotStarveDraws
181     : public LayerTreeHostAnimationTest {
182  public:
183   LayerTreeHostAnimationTestCheckerboardDoesNotStarveDraws()
184       : started_animating_(false) {}
185
186   virtual void BeginTest() OVERRIDE {
187     PostAddAnimationToMainThread(layer_tree_host()->root_layer());
188   }
189
190   virtual void AnimateLayers(
191       LayerTreeHostImpl* host_impl,
192       base::TimeTicks monotonic_time) OVERRIDE {
193     started_animating_ = true;
194   }
195
196   virtual void DrawLayersOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
197     if (started_animating_)
198       EndTest();
199   }
200
201   virtual DrawResult PrepareToDrawOnThread(
202       LayerTreeHostImpl* host_impl,
203       LayerTreeHostImpl::FrameData* frame,
204       DrawResult draw_result) OVERRIDE {
205     return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
206   }
207
208   virtual void AfterTest() OVERRIDE { }
209
210  private:
211   bool started_animating_;
212 };
213
214 // Starvation can only be an issue with the MT compositor.
215 MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestCheckerboardDoesNotStarveDraws);
216
217 // Ensures that animations eventually get deleted.
218 class LayerTreeHostAnimationTestAnimationsGetDeleted
219     : public LayerTreeHostAnimationTest {
220  public:
221   LayerTreeHostAnimationTestAnimationsGetDeleted()
222       : started_animating_(false) {}
223
224   virtual void BeginTest() OVERRIDE {
225     PostAddAnimationToMainThread(layer_tree_host()->root_layer());
226   }
227
228   virtual void AnimateLayers(
229       LayerTreeHostImpl* host_impl,
230       base::TimeTicks monotonic_time) OVERRIDE {
231     bool have_animations = !host_impl->animation_registrar()->
232         active_animation_controllers().empty();
233     if (!started_animating_ && have_animations) {
234       started_animating_ = true;
235       return;
236     }
237
238     if (started_animating_ && !have_animations)
239       EndTest();
240   }
241
242   virtual void NotifyAnimationFinished(
243       base::TimeTicks monotonic_time,
244       Animation::TargetProperty target_property) OVERRIDE {
245     // Animations on the impl-side controller only get deleted during a commit,
246     // so we need to schedule a commit.
247     layer_tree_host()->SetNeedsCommit();
248   }
249
250   virtual void AfterTest() OVERRIDE {}
251
252  private:
253   bool started_animating_;
254 };
255
256 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestAnimationsGetDeleted);
257
258 // Ensures that animations continue to be ticked when we are backgrounded.
259 class LayerTreeHostAnimationTestTickAnimationWhileBackgrounded
260     : public LayerTreeHostAnimationTest {
261  public:
262   LayerTreeHostAnimationTestTickAnimationWhileBackgrounded()
263       : num_begin_frames_(0) {}
264
265   virtual void BeginTest() OVERRIDE {
266     PostAddLongAnimationToMainThread(layer_tree_host()->root_layer());
267   }
268
269   // Use WillAnimateLayers to set visible false before the animation runs and
270   // causes a commit, so we block the second visible animate in single-thread
271   // mode.
272   virtual void WillAnimateLayers(
273       LayerTreeHostImpl* host_impl,
274       base::TimeTicks monotonic_time) OVERRIDE {
275     // Verify that the host can draw, it's just not visible.
276     EXPECT_TRUE(host_impl->CanDraw());
277     if (num_begin_frames_ < 2) {
278       if (!num_begin_frames_) {
279         // We have a long animation running. It should continue to tick even
280         // if we are not visible.
281         PostSetVisibleToMainThread(false);
282       }
283       num_begin_frames_++;
284       return;
285     }
286     EndTest();
287   }
288
289   virtual void AfterTest() OVERRIDE {}
290
291  private:
292   int num_begin_frames_;
293 };
294
295 SINGLE_AND_MULTI_THREAD_TEST_F(
296     LayerTreeHostAnimationTestTickAnimationWhileBackgrounded);
297
298 // Ensures that animation time remains monotonic when we switch from foreground
299 // to background ticking and back, even if we're skipping draws due to
300 // checkerboarding when in the foreground.
301 class LayerTreeHostAnimationTestAnimationTickTimeIsMonotonic
302     : public LayerTreeHostAnimationTest {
303  public:
304   LayerTreeHostAnimationTestAnimationTickTimeIsMonotonic()
305       : has_background_ticked_(false), num_foreground_animates_(0) {}
306
307   virtual void InitializeSettings(LayerTreeSettings* settings) OVERRIDE {
308     // Make sure that drawing many times doesn't cause a checkerboarded
309     // animation to start so we avoid flake in this test.
310     settings->timeout_and_draw_when_animation_checkerboards = false;
311   }
312
313   virtual void BeginTest() OVERRIDE {
314     PostAddLongAnimationToMainThread(layer_tree_host()->root_layer());
315   }
316
317   virtual void AnimateLayers(LayerTreeHostImpl* host_impl,
318                              base::TimeTicks monotonic_time) OVERRIDE {
319     EXPECT_GE(monotonic_time, last_tick_time_);
320     last_tick_time_ = monotonic_time;
321     if (host_impl->visible()) {
322       num_foreground_animates_++;
323       if (num_foreground_animates_ > 1 && !has_background_ticked_)
324         PostSetVisibleToMainThread(false);
325       else if (has_background_ticked_)
326         EndTest();
327     } else {
328       has_background_ticked_ = true;
329       PostSetVisibleToMainThread(true);
330     }
331   }
332
333   virtual DrawResult PrepareToDrawOnThread(
334       LayerTreeHostImpl* host_impl,
335       LayerTreeHostImpl::FrameData* frame,
336       DrawResult draw_result) OVERRIDE {
337     if (TestEnded())
338       return draw_result;
339     return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
340   }
341
342   virtual void AfterTest() OVERRIDE {}
343
344  private:
345   bool has_background_ticked_;
346   int num_foreground_animates_;
347   base::TimeTicks last_tick_time_;
348 };
349
350 SINGLE_AND_MULTI_THREAD_TEST_F(
351     LayerTreeHostAnimationTestAnimationTickTimeIsMonotonic);
352
353 // Ensures that animations do not tick when we are backgrounded and
354 // and we have an empty active tree.
355 class LayerTreeHostAnimationTestNoBackgroundTickingWithoutActiveTree
356     : public LayerTreeHostAnimationTest {
357  protected:
358   LayerTreeHostAnimationTestNoBackgroundTickingWithoutActiveTree()
359       : active_tree_was_animated_(false) {}
360
361   virtual base::TimeDelta LowFrequencyAnimationInterval() const OVERRIDE {
362     return base::TimeDelta::FromMilliseconds(4);
363   }
364
365   virtual void BeginTest() OVERRIDE {
366     PostAddAnimationToMainThread(layer_tree_host()->root_layer());
367   }
368
369   virtual void NotifyAnimationFinished(
370       base::TimeTicks monotonic_time,
371       Animation::TargetProperty target_property) OVERRIDE {
372     // Replace animated commits with an empty tree.
373     layer_tree_host()->SetRootLayer(make_scoped_refptr<Layer>(NULL));
374   }
375
376   virtual void DidCommit() OVERRIDE {
377     // This alternates setting an empty tree and a non-empty tree with an
378     // animation.
379     switch (layer_tree_host()->source_frame_number()) {
380       case 1:
381         // Wait for NotifyAnimationFinished to commit an empty tree.
382         break;
383       case 2:
384         SetupTree();
385         AddOpacityTransitionToLayer(
386             layer_tree_host()->root_layer(), 0.000001, 0, 0.5, true);
387         break;
388       case 3:
389         // Wait for NotifyAnimationFinished to commit an empty tree.
390         break;
391       case 4:
392         EndTest();
393         break;
394     }
395   }
396
397   virtual void BeginCommitOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
398     // At the start of every commit, block activations and make sure
399     // we are backgrounded.
400     host_impl->BlockNotifyReadyToActivateForTesting(true);
401     PostSetVisibleToMainThread(false);
402   }
403
404   virtual void CommitCompleteOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
405     if (!host_impl->settings().impl_side_painting) {
406       // There are no activations to block if we're not impl-side-painting,
407       // so just advance the test immediately.
408       if (host_impl->active_tree()->source_frame_number() < 3)
409         UnblockActivations(host_impl);
410       return;
411     }
412
413     // We block activation for several ticks to make sure that, even though
414     // there is a pending tree with animations, we still do not background
415     // tick if the active tree is empty.
416     if (host_impl->pending_tree()->source_frame_number() < 3) {
417       base::MessageLoopProxy::current()->PostDelayedTask(
418           FROM_HERE,
419           base::Bind(
420               &LayerTreeHostAnimationTestNoBackgroundTickingWithoutActiveTree::
421                    UnblockActivations,
422               base::Unretained(this),
423               host_impl),
424           4 * LowFrequencyAnimationInterval());
425     }
426   }
427
428   virtual void UnblockActivations(LayerTreeHostImpl* host_impl) {
429     host_impl->BlockNotifyReadyToActivateForTesting(false);
430   }
431
432   virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
433     active_tree_was_animated_ = false;
434
435     // Verify that commits are actually alternating with empty / non-empty
436     // trees.
437     int frame_number = host_impl->active_tree()->source_frame_number();
438     switch (frame_number) {
439       case 0:
440       case 2:
441         EXPECT_TRUE(host_impl->active_tree()->root_layer())
442             << "frame: " << frame_number;
443         break;
444       case 1:
445       case 3:
446         EXPECT_FALSE(host_impl->active_tree()->root_layer())
447             << "frame: " << frame_number;
448         break;
449     }
450
451     if (host_impl->active_tree()->source_frame_number() < 3) {
452       // Initiate the next commit after a delay to give us a chance to
453       // background tick if the active tree isn't empty.
454       base::MessageLoopProxy::current()->PostDelayedTask(
455           FROM_HERE,
456           base::Bind(
457               &LayerTreeHostAnimationTestNoBackgroundTickingWithoutActiveTree::
458                    InitiateNextCommit,
459               base::Unretained(this),
460               host_impl),
461           4 * LowFrequencyAnimationInterval());
462     }
463   }
464
465   virtual void WillAnimateLayers(LayerTreeHostImpl* host_impl,
466                                  base::TimeTicks monotonic_time) OVERRIDE {
467     EXPECT_TRUE(host_impl->active_tree()->root_layer());
468     active_tree_was_animated_ = true;
469   }
470
471   void InitiateNextCommit(LayerTreeHostImpl* host_impl) {
472     // Verify that we actually animated when we should have.
473     bool has_active_tree = host_impl->active_tree()->root_layer();
474     EXPECT_EQ(has_active_tree, active_tree_was_animated_);
475
476     // The next commit is blocked until we become visible again.
477     PostSetVisibleToMainThread(true);
478   }
479
480   virtual void AfterTest() OVERRIDE {}
481
482   bool active_tree_was_animated_;
483 };
484
485 SINGLE_AND_MULTI_THREAD_TEST_F(
486     LayerTreeHostAnimationTestNoBackgroundTickingWithoutActiveTree);
487
488 // Ensure that an animation's timing function is respected.
489 class LayerTreeHostAnimationTestAddAnimationWithTimingFunction
490     : public LayerTreeHostAnimationTest {
491  public:
492   LayerTreeHostAnimationTestAddAnimationWithTimingFunction() {}
493
494   virtual void SetupTree() OVERRIDE {
495     LayerTreeHostAnimationTest::SetupTree();
496     content_ = FakeContentLayer::Create(&client_);
497     content_->SetBounds(gfx::Size(4, 4));
498     layer_tree_host()->root_layer()->AddChild(content_);
499   }
500
501   virtual void BeginTest() OVERRIDE {
502     PostAddAnimationToMainThread(content_.get());
503   }
504
505   virtual void AnimateLayers(
506       LayerTreeHostImpl* host_impl,
507       base::TimeTicks monotonic_time) OVERRIDE {
508     LayerAnimationController* controller_impl =
509         host_impl->active_tree()->root_layer()->children()[0]->
510         layer_animation_controller();
511     Animation* animation =
512         controller_impl->GetAnimation(Animation::Opacity);
513     if (!animation)
514       return;
515
516     const FloatAnimationCurve* curve =
517         animation->curve()->ToFloatAnimationCurve();
518     float start_opacity = curve->GetValue(0.0);
519     float end_opacity = curve->GetValue(curve->Duration());
520     float linearly_interpolated_opacity =
521         0.25f * end_opacity + 0.75f * start_opacity;
522     double time = curve->Duration() * 0.25;
523     // If the linear timing function associated with this animation was not
524     // picked up, then the linearly interpolated opacity would be different
525     // because of the default ease timing function.
526     EXPECT_FLOAT_EQ(linearly_interpolated_opacity, curve->GetValue(time));
527
528     EndTest();
529   }
530
531   virtual void AfterTest() OVERRIDE {}
532
533   FakeContentLayerClient client_;
534   scoped_refptr<FakeContentLayer> content_;
535 };
536
537 SINGLE_AND_MULTI_THREAD_TEST_F(
538     LayerTreeHostAnimationTestAddAnimationWithTimingFunction);
539
540 // Ensures that main thread animations have their start times synchronized with
541 // impl thread animations.
542 class LayerTreeHostAnimationTestSynchronizeAnimationStartTimes
543     : public LayerTreeHostAnimationTest {
544  public:
545   LayerTreeHostAnimationTestSynchronizeAnimationStartTimes()
546       : main_start_time_(-1.0),
547         impl_start_time_(-1.0) {}
548
549   virtual void SetupTree() OVERRIDE {
550     LayerTreeHostAnimationTest::SetupTree();
551     content_ = FakeContentLayer::Create(&client_);
552     content_->SetBounds(gfx::Size(4, 4));
553     content_->set_layer_animation_delegate(this);
554     layer_tree_host()->root_layer()->AddChild(content_);
555   }
556
557   virtual void BeginTest() OVERRIDE {
558     PostAddAnimationToMainThread(content_.get());
559   }
560
561   virtual void NotifyAnimationStarted(
562       base::TimeTicks monotonic_time,
563       Animation::TargetProperty target_property) OVERRIDE {
564     LayerAnimationController* controller =
565         layer_tree_host()->root_layer()->children()[0]->
566         layer_animation_controller();
567     Animation* animation =
568         controller->GetAnimation(Animation::Opacity);
569     main_start_time_ =
570         (animation->start_time() - base::TimeTicks()).InSecondsF();
571     controller->RemoveAnimation(animation->id());
572
573     if (impl_start_time_ > 0.0)
574       EndTest();
575   }
576
577   virtual void UpdateAnimationState(
578       LayerTreeHostImpl* impl_host,
579       bool has_unfinished_animation) OVERRIDE {
580     LayerAnimationController* controller =
581         impl_host->active_tree()->root_layer()->children()[0]->
582         layer_animation_controller();
583     Animation* animation =
584         controller->GetAnimation(Animation::Opacity);
585     if (!animation)
586       return;
587
588     impl_start_time_ =
589         (animation->start_time() - base::TimeTicks()).InSecondsF();
590     controller->RemoveAnimation(animation->id());
591
592     if (main_start_time_ > 0.0)
593       EndTest();
594   }
595
596   virtual void AfterTest() OVERRIDE {
597     EXPECT_FLOAT_EQ(impl_start_time_, main_start_time_);
598   }
599
600  private:
601   double main_start_time_;
602   double impl_start_time_;
603   FakeContentLayerClient client_;
604   scoped_refptr<FakeContentLayer> content_;
605 };
606
607 SINGLE_AND_MULTI_THREAD_TEST_F(
608     LayerTreeHostAnimationTestSynchronizeAnimationStartTimes);
609
610 // Ensures that notify animation finished is called.
611 class LayerTreeHostAnimationTestAnimationFinishedEvents
612     : public LayerTreeHostAnimationTest {
613  public:
614   LayerTreeHostAnimationTestAnimationFinishedEvents() {}
615
616   virtual void BeginTest() OVERRIDE {
617     PostAddInstantAnimationToMainThread(layer_tree_host()->root_layer());
618   }
619
620   virtual void NotifyAnimationFinished(
621       base::TimeTicks monotonic_time,
622       Animation::TargetProperty target_property) OVERRIDE {
623     LayerAnimationController* controller =
624         layer_tree_host()->root_layer()->layer_animation_controller();
625     Animation* animation =
626         controller->GetAnimation(Animation::Opacity);
627     if (animation)
628       controller->RemoveAnimation(animation->id());
629     EndTest();
630   }
631
632   virtual void AfterTest() OVERRIDE {}
633 };
634
635 SINGLE_AND_MULTI_THREAD_TEST_F(
636     LayerTreeHostAnimationTestAnimationFinishedEvents);
637
638 // Ensures that when opacity is being animated, this value does not cause the
639 // subtree to be skipped.
640 class LayerTreeHostAnimationTestDoNotSkipLayersWithAnimatedOpacity
641     : public LayerTreeHostAnimationTest {
642  public:
643   LayerTreeHostAnimationTestDoNotSkipLayersWithAnimatedOpacity()
644       : update_check_layer_(FakeContentLayer::Create(&client_)) {
645   }
646
647   virtual void SetupTree() OVERRIDE {
648     update_check_layer_->SetOpacity(0.f);
649     layer_tree_host()->SetRootLayer(update_check_layer_);
650     LayerTreeHostAnimationTest::SetupTree();
651   }
652
653   virtual void BeginTest() OVERRIDE {
654     PostAddAnimationToMainThread(update_check_layer_.get());
655   }
656
657   virtual void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
658     LayerAnimationController* controller_impl =
659         host_impl->active_tree()->root_layer()->layer_animation_controller();
660     Animation* animation_impl =
661         controller_impl->GetAnimation(Animation::Opacity);
662     controller_impl->RemoveAnimation(animation_impl->id());
663     EndTest();
664   }
665
666   virtual void AfterTest() OVERRIDE {
667     // Update() should have been called once, proving that the layer was not
668     // skipped.
669     EXPECT_EQ(1u, update_check_layer_->update_count());
670
671     // clear update_check_layer_ so LayerTreeHost dies.
672     update_check_layer_ = NULL;
673   }
674
675  private:
676   FakeContentLayerClient client_;
677   scoped_refptr<FakeContentLayer> update_check_layer_;
678 };
679
680 SINGLE_AND_MULTI_THREAD_TEST_F(
681     LayerTreeHostAnimationTestDoNotSkipLayersWithAnimatedOpacity);
682
683 // Layers added to tree with existing active animations should have the
684 // animation correctly recognized.
685 class LayerTreeHostAnimationTestLayerAddedWithAnimation
686     : public LayerTreeHostAnimationTest {
687  public:
688   LayerTreeHostAnimationTestLayerAddedWithAnimation() {}
689
690   virtual void BeginTest() OVERRIDE {
691     PostSetNeedsCommitToMainThread();
692   }
693
694   virtual void DidCommit() OVERRIDE {
695     if (layer_tree_host()->source_frame_number() == 1) {
696       scoped_refptr<Layer> layer = Layer::Create();
697       layer->set_layer_animation_delegate(this);
698
699       // Any valid AnimationCurve will do here.
700       scoped_ptr<AnimationCurve> curve(new FakeFloatAnimationCurve());
701       scoped_ptr<Animation> animation(
702           Animation::Create(curve.Pass(), 1, 1,
703                                   Animation::Opacity));
704       layer->layer_animation_controller()->AddAnimation(animation.Pass());
705
706       // We add the animation *before* attaching the layer to the tree.
707       layer_tree_host()->root_layer()->AddChild(layer);
708     }
709   }
710
711   virtual void AnimateLayers(
712       LayerTreeHostImpl* impl_host,
713       base::TimeTicks monotonic_time) OVERRIDE {
714     EndTest();
715   }
716
717   virtual void AfterTest() OVERRIDE {}
718 };
719
720 SINGLE_AND_MULTI_THREAD_TEST_F(
721     LayerTreeHostAnimationTestLayerAddedWithAnimation);
722
723 class LayerTreeHostAnimationTestCancelAnimateCommit
724     : public LayerTreeHostAnimationTest {
725  public:
726   LayerTreeHostAnimationTestCancelAnimateCommit()
727       : num_begin_frames_(0), num_commit_calls_(0), num_draw_calls_(0) {}
728
729   virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); }
730
731   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
732     num_begin_frames_++;
733     // No-op animate will cancel the commit.
734     if (layer_tree_host()->source_frame_number() == 1) {
735       EndTest();
736       return;
737     }
738     layer_tree_host()->SetNeedsAnimate();
739   }
740
741   virtual void CommitCompleteOnThread(LayerTreeHostImpl* impl) OVERRIDE {
742     num_commit_calls_++;
743     if (impl->active_tree()->source_frame_number() > 1)
744       FAIL() << "Commit should have been canceled.";
745   }
746
747   virtual void DrawLayersOnThread(LayerTreeHostImpl* impl) OVERRIDE {
748     num_draw_calls_++;
749     if (impl->active_tree()->source_frame_number() > 1)
750       FAIL() << "Draw should have been canceled.";
751   }
752
753   virtual void AfterTest() OVERRIDE {
754     EXPECT_EQ(2, num_begin_frames_);
755     EXPECT_EQ(1, num_commit_calls_);
756     EXPECT_EQ(1, num_draw_calls_);
757   }
758
759  private:
760   int num_begin_frames_;
761   int num_commit_calls_;
762   int num_draw_calls_;
763   FakeContentLayerClient client_;
764   scoped_refptr<FakeContentLayer> content_;
765 };
766
767 MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestCancelAnimateCommit);
768
769 class LayerTreeHostAnimationTestForceRedraw
770     : public LayerTreeHostAnimationTest {
771  public:
772   LayerTreeHostAnimationTestForceRedraw()
773       : num_animate_(0), num_draw_layers_(0) {}
774
775   virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); }
776
777   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
778     if (++num_animate_ < 2)
779       layer_tree_host()->SetNeedsAnimate();
780   }
781
782   virtual void Layout() OVERRIDE {
783     layer_tree_host()->SetNextCommitForcesRedraw();
784   }
785
786   virtual void DrawLayersOnThread(LayerTreeHostImpl* impl) OVERRIDE {
787     if (++num_draw_layers_ == 2)
788       EndTest();
789   }
790
791   virtual void AfterTest() OVERRIDE {
792     // The first commit will always draw; make sure the second draw triggered
793     // by the animation was not cancelled.
794     EXPECT_EQ(2, num_draw_layers_);
795     EXPECT_EQ(2, num_animate_);
796   }
797
798  private:
799   int num_animate_;
800   int num_draw_layers_;
801 };
802
803 MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestForceRedraw);
804
805 class LayerTreeHostAnimationTestAnimateAfterSetNeedsCommit
806     : public LayerTreeHostAnimationTest {
807  public:
808   LayerTreeHostAnimationTestAnimateAfterSetNeedsCommit()
809       : num_animate_(0), num_draw_layers_(0) {}
810
811   virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); }
812
813   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
814     if (++num_animate_ <= 2) {
815       layer_tree_host()->SetNeedsCommit();
816       layer_tree_host()->SetNeedsAnimate();
817     }
818   }
819
820   virtual void DrawLayersOnThread(LayerTreeHostImpl* impl) OVERRIDE {
821     if (++num_draw_layers_ == 2)
822       EndTest();
823   }
824
825   virtual void AfterTest() OVERRIDE {
826     // The first commit will always draw; make sure the second draw triggered
827     // by the SetNeedsCommit was not cancelled.
828     EXPECT_EQ(2, num_draw_layers_);
829     EXPECT_GE(num_animate_, 2);
830   }
831
832  private:
833   int num_animate_;
834   int num_draw_layers_;
835 };
836
837 MULTI_THREAD_TEST_F(LayerTreeHostAnimationTestAnimateAfterSetNeedsCommit);
838
839 // Make sure the main thread can still execute animations when CanDraw() is not
840 // true.
841 class LayerTreeHostAnimationTestRunAnimationWhenNotCanDraw
842     : public LayerTreeHostAnimationTest {
843  public:
844   LayerTreeHostAnimationTestRunAnimationWhenNotCanDraw() : started_times_(0) {}
845
846   virtual void SetupTree() OVERRIDE {
847     LayerTreeHostAnimationTest::SetupTree();
848     content_ = FakeContentLayer::Create(&client_);
849     content_->SetBounds(gfx::Size(4, 4));
850     content_->set_layer_animation_delegate(this);
851     layer_tree_host()->root_layer()->AddChild(content_);
852   }
853
854   virtual void BeginTest() OVERRIDE {
855     layer_tree_host()->SetViewportSize(gfx::Size());
856     PostAddAnimationToMainThread(content_.get());
857   }
858
859   virtual void NotifyAnimationStarted(
860       base::TimeTicks monotonic_time,
861       Animation::TargetProperty target_property) OVERRIDE {
862     started_times_++;
863   }
864
865   virtual void NotifyAnimationFinished(
866       base::TimeTicks monotonic_time,
867       Animation::TargetProperty target_property) OVERRIDE {
868     EndTest();
869   }
870
871   virtual void AfterTest() OVERRIDE {
872     EXPECT_EQ(1, started_times_);
873   }
874
875  private:
876   int started_times_;
877   FakeContentLayerClient client_;
878   scoped_refptr<FakeContentLayer> content_;
879 };
880
881 SINGLE_AND_MULTI_THREAD_TEST_F(
882     LayerTreeHostAnimationTestRunAnimationWhenNotCanDraw);
883
884 // Make sure the main thread can still execute animations when the renderer is
885 // backgrounded.
886 class LayerTreeHostAnimationTestRunAnimationWhenNotVisible
887     : public LayerTreeHostAnimationTest {
888  public:
889   LayerTreeHostAnimationTestRunAnimationWhenNotVisible() : started_times_(0) {}
890
891   virtual void SetupTree() OVERRIDE {
892     LayerTreeHostAnimationTest::SetupTree();
893     content_ = FakeContentLayer::Create(&client_);
894     content_->SetBounds(gfx::Size(4, 4));
895     content_->set_layer_animation_delegate(this);
896     layer_tree_host()->root_layer()->AddChild(content_);
897   }
898
899   virtual void BeginTest() OVERRIDE {
900     visible_ = true;
901     PostAddAnimationToMainThread(content_.get());
902   }
903
904   virtual void DidCommit() OVERRIDE {
905     visible_ = false;
906     layer_tree_host()->SetVisible(false);
907   }
908
909   virtual void NotifyAnimationStarted(
910       base::TimeTicks monotonic_time,
911       Animation::TargetProperty target_property) OVERRIDE {
912     EXPECT_FALSE(visible_);
913     started_times_++;
914   }
915
916   virtual void NotifyAnimationFinished(
917       base::TimeTicks monotonic_time,
918       Animation::TargetProperty target_property) OVERRIDE {
919     EXPECT_FALSE(visible_);
920     EXPECT_EQ(1, started_times_);
921     EndTest();
922   }
923
924   virtual void AfterTest() OVERRIDE {}
925
926  private:
927   bool visible_;
928   int started_times_;
929   FakeContentLayerClient client_;
930   scoped_refptr<FakeContentLayer> content_;
931 };
932
933 SINGLE_AND_MULTI_THREAD_TEST_F(
934     LayerTreeHostAnimationTestRunAnimationWhenNotVisible);
935
936 // Animations should not be started when frames are being skipped due to
937 // checkerboard.
938 class LayerTreeHostAnimationTestCheckerboardDoesntStartAnimations
939     : public LayerTreeHostAnimationTest {
940   virtual void SetupTree() OVERRIDE {
941     LayerTreeHostAnimationTest::SetupTree();
942     content_ = FakeContentLayer::Create(&client_);
943     content_->SetBounds(gfx::Size(4, 4));
944     content_->set_layer_animation_delegate(this);
945     layer_tree_host()->root_layer()->AddChild(content_);
946   }
947
948   virtual void InitializeSettings(LayerTreeSettings* settings) OVERRIDE {
949     // Make sure that drawing many times doesn't cause a checkerboarded
950     // animation to start so we avoid flake in this test.
951     settings->timeout_and_draw_when_animation_checkerboards = false;
952   }
953
954   virtual void BeginTest() OVERRIDE {
955     prevented_draw_ = 0;
956     added_animations_ = 0;
957     started_times_ = 0;
958
959     PostSetNeedsCommitToMainThread();
960   }
961
962   virtual DrawResult PrepareToDrawOnThread(
963       LayerTreeHostImpl* host_impl,
964       LayerTreeHostImpl::FrameData* frame_data,
965       DrawResult draw_result) OVERRIDE {
966     if (added_animations_ < 2)
967       return draw_result;
968     if (TestEnded())
969       return draw_result;
970     // Act like there is checkerboard when the second animation wants to draw.
971     ++prevented_draw_;
972     if (prevented_draw_ > 2)
973       EndTest();
974     return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
975   }
976
977   virtual void DidCommitAndDrawFrame() OVERRIDE {
978     switch (layer_tree_host()->source_frame_number()) {
979       case 1:
980         // The animation is longer than 1 BeginFrame interval.
981         AddOpacityTransitionToLayer(content_.get(), 0.1, 0.2f, 0.8f, false);
982         added_animations_++;
983         break;
984       case 2:
985         // This second animation will not be drawn so it should not start.
986         AddAnimatedTransformToLayer(content_.get(), 0.1, 5, 5);
987         added_animations_++;
988         break;
989     }
990   }
991
992   virtual void NotifyAnimationStarted(
993       base::TimeTicks monotonic_time,
994       Animation::TargetProperty target_property) OVERRIDE {
995     if (TestEnded())
996       return;
997     started_times_++;
998   }
999
1000   virtual void AfterTest() OVERRIDE {
1001     // Make sure we tried to draw the second animation but failed.
1002     EXPECT_LT(0, prevented_draw_);
1003     // The first animation should be started, but the second should not because
1004     // of checkerboard.
1005     EXPECT_EQ(1, started_times_);
1006   }
1007
1008   int prevented_draw_;
1009   int added_animations_;
1010   int started_times_;
1011   FakeContentLayerClient client_;
1012   scoped_refptr<FakeContentLayer> content_;
1013 };
1014
1015 MULTI_THREAD_TEST_F(
1016     LayerTreeHostAnimationTestCheckerboardDoesntStartAnimations);
1017
1018 // Verifies that scroll offset animations are only accepted when impl-scrolling
1019 // is supported, and that when scroll offset animations are accepted,
1020 // scroll offset updates are sent back to the main thread.
1021 class LayerTreeHostAnimationTestScrollOffsetChangesArePropagated
1022     : public LayerTreeHostAnimationTest {
1023  public:
1024   LayerTreeHostAnimationTestScrollOffsetChangesArePropagated() {}
1025
1026   virtual void SetupTree() OVERRIDE {
1027     LayerTreeHostAnimationTest::SetupTree();
1028
1029     scroll_layer_ = FakeContentLayer::Create(&client_);
1030     scroll_layer_->SetScrollClipLayerId(layer_tree_host()->root_layer()->id());
1031     scroll_layer_->SetBounds(gfx::Size(1000, 1000));
1032     scroll_layer_->SetScrollOffset(gfx::Vector2d(10, 20));
1033     layer_tree_host()->root_layer()->AddChild(scroll_layer_);
1034   }
1035
1036   virtual void BeginTest() OVERRIDE {
1037     PostSetNeedsCommitToMainThread();
1038   }
1039
1040   virtual void DidCommit() OVERRIDE {
1041     switch (layer_tree_host()->source_frame_number()) {
1042       case 1: {
1043         scoped_ptr<ScrollOffsetAnimationCurve> curve(
1044             ScrollOffsetAnimationCurve::Create(
1045                 gfx::Vector2dF(500.f, 550.f),
1046                 EaseInOutTimingFunction::Create()));
1047         scoped_ptr<Animation> animation(Animation::Create(
1048             curve.PassAs<AnimationCurve>(), 1, 0, Animation::ScrollOffset));
1049         animation->set_needs_synchronized_start_time(true);
1050         bool animation_added = scroll_layer_->AddAnimation(animation.Pass());
1051         bool impl_scrolling_supported =
1052             layer_tree_host()->proxy()->SupportsImplScrolling();
1053         EXPECT_EQ(impl_scrolling_supported, animation_added);
1054         if (!impl_scrolling_supported)
1055           EndTest();
1056         break;
1057       }
1058       default:
1059         if (scroll_layer_->scroll_offset().x() > 10 &&
1060             scroll_layer_->scroll_offset().y() > 20)
1061           EndTest();
1062     }
1063   }
1064
1065   virtual void AfterTest() OVERRIDE {}
1066
1067  private:
1068   FakeContentLayerClient client_;
1069   scoped_refptr<FakeContentLayer> scroll_layer_;
1070 };
1071
1072 SINGLE_AND_MULTI_THREAD_TEST_F(
1073     LayerTreeHostAnimationTestScrollOffsetChangesArePropagated);
1074
1075 // Ensure that animation time is correctly updated when animations are frozen
1076 // because of checkerboarding.
1077 class LayerTreeHostAnimationTestFrozenAnimationTickTime
1078     : public LayerTreeHostAnimationTest {
1079  public:
1080   LayerTreeHostAnimationTestFrozenAnimationTickTime()
1081       : started_animating_(false), num_commits_(0), num_draw_attempts_(2) {}
1082
1083   virtual void InitializeSettings(LayerTreeSettings* settings) OVERRIDE {
1084     // Make sure that drawing many times doesn't cause a checkerboarded
1085     // animation to start so we avoid flake in this test.
1086     settings->timeout_and_draw_when_animation_checkerboards = false;
1087   }
1088
1089   virtual void BeginTest() OVERRIDE {
1090     PostAddAnimationToMainThread(layer_tree_host()->root_layer());
1091   }
1092
1093   virtual void BeginMainFrame(const BeginFrameArgs& args) OVERRIDE {
1094     last_main_thread_tick_time_ = args.frame_time;
1095   }
1096
1097   virtual void AnimateLayers(LayerTreeHostImpl* host_impl,
1098                              base::TimeTicks monotonic_time) OVERRIDE {
1099     if (TestEnded())
1100       return;
1101     if (!started_animating_) {
1102       started_animating_ = true;
1103       expected_impl_tick_time_ = monotonic_time;
1104     } else {
1105       EXPECT_EQ(expected_impl_tick_time_, monotonic_time);
1106       if (num_commits_ > 2)
1107         EndTest();
1108     }
1109   }
1110
1111   virtual DrawResult PrepareToDrawOnThread(LayerTreeHostImpl* host_impl,
1112                                            LayerTreeHostImpl::FrameData* frame,
1113                                            DrawResult draw_result) OVERRIDE {
1114     if (TestEnded())
1115       return draw_result;
1116     num_draw_attempts_++;
1117     if (num_draw_attempts_ > 2) {
1118       num_draw_attempts_ = 0;
1119       PostSetNeedsCommitToMainThread();
1120     }
1121     return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
1122   }
1123
1124   virtual void BeginCommitOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
1125     if (!started_animating_)
1126       return;
1127     expected_impl_tick_time_ =
1128         std::max(expected_impl_tick_time_, last_main_thread_tick_time_);
1129     num_commits_++;
1130   }
1131
1132   virtual void AfterTest() OVERRIDE {}
1133
1134  private:
1135   bool started_animating_;
1136   int num_commits_;
1137   int num_draw_attempts_;
1138   base::TimeTicks last_main_thread_tick_time_;
1139   base::TimeTicks expected_impl_tick_time_;
1140 };
1141
1142 // Only the non-impl-paint multi-threaded compositor freezes animations.
1143 MULTI_THREAD_NOIMPL_TEST_F(LayerTreeHostAnimationTestFrozenAnimationTickTime);
1144
1145 // When animations are simultaneously added to an existing layer and to a new
1146 // layer, they should start at the same time, even when there's already a
1147 // running animation on the existing layer.
1148 class LayerTreeHostAnimationTestAnimationsAddedToNewAndExistingLayers
1149     : public LayerTreeHostAnimationTest {
1150  public:
1151   LayerTreeHostAnimationTestAnimationsAddedToNewAndExistingLayers()
1152       : frame_count_with_pending_tree_(0) {}
1153
1154   virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); }
1155
1156   virtual void DidCommit() OVERRIDE {
1157     if (layer_tree_host()->source_frame_number() == 1) {
1158       AddAnimatedTransformToLayer(layer_tree_host()->root_layer(), 4, 1, 1);
1159     } else if (layer_tree_host()->source_frame_number() == 2) {
1160       AddOpacityTransitionToLayer(
1161           layer_tree_host()->root_layer(), 1, 0.f, 0.5f, true);
1162
1163       scoped_refptr<Layer> layer = Layer::Create();
1164       layer_tree_host()->root_layer()->AddChild(layer);
1165       layer->set_layer_animation_delegate(this);
1166       layer->SetBounds(gfx::Size(4, 4));
1167       AddOpacityTransitionToLayer(layer.get(), 1, 0.f, 0.5f, true);
1168     }
1169   }
1170
1171   virtual void BeginCommitOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
1172     host_impl->BlockNotifyReadyToActivateForTesting(true);
1173   }
1174
1175   virtual void CommitCompleteOnThread(LayerTreeHostImpl* host_impl) OVERRIDE {
1176     // For the commit that added animations to new and existing layers, keep
1177     // blocking activation. We want to verify that even with activation blocked,
1178     // the animation on the layer that's already in the active tree won't get a
1179     // head start.
1180     if (!host_impl->settings().impl_side_painting ||
1181         host_impl->pending_tree()->source_frame_number() != 2)
1182       host_impl->BlockNotifyReadyToActivateForTesting(false);
1183   }
1184
1185   virtual void WillBeginImplFrameOnThread(LayerTreeHostImpl* host_impl,
1186                                           const BeginFrameArgs& args) OVERRIDE {
1187     if (!host_impl->pending_tree() ||
1188         host_impl->pending_tree()->source_frame_number() != 2)
1189       return;
1190
1191     frame_count_with_pending_tree_++;
1192     if (frame_count_with_pending_tree_ == 2)
1193       host_impl->BlockNotifyReadyToActivateForTesting(false);
1194   }
1195
1196   virtual void UpdateAnimationState(LayerTreeHostImpl* host_impl,
1197                                     bool has_unfinished_animation) OVERRIDE {
1198     LayerAnimationController* root_controller_impl =
1199         host_impl->active_tree()->root_layer()->layer_animation_controller();
1200     Animation* root_animation =
1201         root_controller_impl->GetAnimation(Animation::Opacity);
1202     if (!root_animation || root_animation->run_state() != Animation::Running)
1203       return;
1204
1205     LayerAnimationController* child_controller_impl =
1206         host_impl->active_tree()->root_layer()->children()
1207             [0]->layer_animation_controller();
1208     Animation* child_animation =
1209         child_controller_impl->GetAnimation(Animation::Opacity);
1210     EXPECT_EQ(Animation::Running, child_animation->run_state());
1211     EXPECT_EQ(root_animation->start_time(), child_animation->start_time());
1212     root_controller_impl->AbortAnimations(Animation::Opacity);
1213     root_controller_impl->AbortAnimations(Animation::Transform);
1214     child_controller_impl->AbortAnimations(Animation::Opacity);
1215     EndTest();
1216   }
1217
1218   virtual void AfterTest() OVERRIDE {}
1219
1220  private:
1221   int frame_count_with_pending_tree_;
1222 };
1223
1224 SINGLE_AND_MULTI_THREAD_TEST_F(
1225     LayerTreeHostAnimationTestAnimationsAddedToNewAndExistingLayers);
1226
1227 class LayerTreeHostAnimationTestAddAnimationAfterAnimating
1228     : public LayerTreeHostAnimationTest {
1229  public:
1230   LayerTreeHostAnimationTestAddAnimationAfterAnimating()
1231       : num_swap_buffers_(0) {}
1232
1233   virtual void SetupTree() OVERRIDE {
1234     LayerTreeHostAnimationTest::SetupTree();
1235     content_ = Layer::Create();
1236     content_->SetBounds(gfx::Size(4, 4));
1237     layer_tree_host()->root_layer()->AddChild(content_);
1238   }
1239
1240   virtual void BeginTest() OVERRIDE { PostSetNeedsCommitToMainThread(); }
1241
1242   virtual void DidCommit() OVERRIDE {
1243     switch (layer_tree_host()->source_frame_number()) {
1244       case 1:
1245         // First frame: add an animation to the root layer.
1246         AddAnimatedTransformToLayer(layer_tree_host()->root_layer(), 0.1, 5, 5);
1247         break;
1248       case 2:
1249         // Second frame: add an animation to the content layer. The root layer
1250         // animation has caused us to animate already during this frame.
1251         AddOpacityTransitionToLayer(content_.get(), 0.1, 5, 5, false);
1252         break;
1253     }
1254   }
1255
1256   virtual void SwapBuffersOnThread(LayerTreeHostImpl* host_impl,
1257                                    bool result) OVERRIDE {
1258     // After both animations have started, verify that they have valid
1259     // start times.
1260     num_swap_buffers_++;
1261     AnimationRegistrar::AnimationControllerMap copy =
1262         host_impl->animation_registrar()->active_animation_controllers();
1263     if (copy.size() == 2u) {
1264       EndTest();
1265       EXPECT_GE(num_swap_buffers_, 3);
1266       for (AnimationRegistrar::AnimationControllerMap::iterator iter =
1267                copy.begin();
1268            iter != copy.end();
1269            ++iter) {
1270         int id = ((*iter).second->id());
1271         if (id == host_impl->RootLayer()->id()) {
1272           Animation* anim = (*iter).second->GetAnimation(Animation::Transform);
1273           EXPECT_GT((anim->start_time() - base::TimeTicks()).InSecondsF(), 0);
1274         } else if (id == host_impl->RootLayer()->children()[0]->id()) {
1275           Animation* anim = (*iter).second->GetAnimation(Animation::Opacity);
1276           EXPECT_GT((anim->start_time() - base::TimeTicks()).InSecondsF(), 0);
1277         }
1278       }
1279     }
1280   }
1281
1282   virtual void AfterTest() OVERRIDE {}
1283
1284  private:
1285   scoped_refptr<Layer> content_;
1286   int num_swap_buffers_;
1287 };
1288
1289 SINGLE_AND_MULTI_THREAD_TEST_F(
1290     LayerTreeHostAnimationTestAddAnimationAfterAnimating);
1291
1292 }  // namespace
1293 }  // namespace cc